How to add objectpicker and Camera to my entity in Qt3D? - qt3d

I need to render some lines and points that hold some data in a 3d scene.
And points need to be picked by mouse, and then get the data in the point.
I first try to define a class inherited from QQuickFramebufferObject, however i find it is difficult to do mouse picking.
I find that it has the ObjectPicker in Qt3D module, so i want to use Qt3D to deal with my work.
My test code below. I defined my GeometryRenderer Object, and set vertices data(just draw two triangles). Like this:
GeometryRenderer {
id: geometry
geometry: Geometry {
boundingVolumePositionAttribute: position
Attribute {
id: position
attributeType: Attribute.VertexAttribute
vertexBaseType: Attribute.Float
vertexSize: 3
count: 4
byteOffset: 0
byteStride: 6 * 4
name: "position"
buffer: vertexBuffer
}
Attribute {
id: color
attributeType: Attribute.VertexAttribute
vertexBaseType: Attribute.Float
vertexSize: 3
count: 4
byteOffset: 3 * 4
byteStride: 6 * 4
name: "color"
buffer: vertexBuffer
}
Attribute {
attributeType: Attribute.IndexAttribute
vertexBaseType: Attribute.UnsignedShort
vertexSize: 1
count: 6
buffer: indexBuffer
}
}
Buffer {
id: vertexBuffer
type: Buffer.VertexBuffer
data: new Float32Array(...)
}
Buffer {
id: indexBuffer
type: Buffer.IndexBuffer
data: new Uint16Array(...)
}
}
And then define a material object like this:
Material {
id: material
effect: Effect {
techniques: Technique {
graphicsApiFilter {
profile: GraphicsApiFilter.CoreProfile
}
renderPasses: RenderPass {
shaderProgram: ShaderProgram {
vertexShaderCode: loadSource("qrc:/shader/hellotriangle.vert")
fragmentShaderCode: loadSource("qrc:/shader/hellotriangle.frag")
}
}
}
}
}
And then in my root Entity:
Entity {
id: root
components: [
RenderSettings {
activeFrameGraph: colorBuffer
pickingSettings.pickMethod: PickingSettings.TrianglePicking
pickingSettings.pickResultMode: PickingSettings.NearestPick
},
InputSettings { }
]
ClearBuffers {
id: colorBuffer
clearColor: Qt.rgba(0.8, 0.8, 0.8, 0.6)
buffers: ClearBuffers.ColorDepthBuffer
RenderSurfaceSelector {
RenderStateSet {
renderStates: DepthTest {
depthFunction: DepthTest.Less
}
}
}
}
}
It works, rendering two triangle. And I want to add Qt3D Camera and ObjectPicker in my scene, How can i make it?
I find that if i use ForwardRenderer(but i couldn't find a way to render my own lines/points vertices) instead of ClearBuffers, the Camera and ObjectPicker works

Related

Mapbox show location Paris

I get correctly coordinate from this function in Map.ts:
populateForm() {
let pharmaId = this.route.snapshot.params["id"];
this.pharma.pharmagetbyid(pharmaId ).subscribe(
pharmadata=> {
if (pharmadata){
this.pharmadata= pharmadata;
}
}
);
}
In html I write this code in Map.html:
<Mapbox
accessToken="pk.xxxxxxxxxxxxxxx"
mapStyle="traffic_day"
[latitude]="pharmadata.latitude"
[longitude]="pharmadata.longitude"
zoomLevel="7"
delay="450"
showUserLocation="true"
hideCompass="false"
disableZoom="false"
disableRotation="false"
disableScroll="false"
disableTilt="false"
(mapReady)="onMapReady($event)">
</Mapbox>
And this onMapReady() have this code in Map.ts:
onMapReady(args): void {
this.map = args.map;
console.log(args.map)
this.map.addMarkers([
{
lat: this.pharmadata.longitude,
lng: this.pharmadata.latitude,
}
]
);
}
My coordinate are:
"longitude": 4.56, "latitude": 5.65
In map show firstly
and when I zoom map show Marks
Can you suggest me any idea how to show only Marks?
Your lat/long are flipped in your onMapReady function. Your code should look like this:
onMapReady(args): void {
this.map = args.map;
console.log(args.map)
this.map.addMarkers([
{
lat: this.pharmadata.latitude, // Flip these
lng: this.pharmadata.longitude, // two lines
}
]
);
}

MacOS dock-like component in QML

Using QtQuick, I have a row of 5 images in a repeater. I'd like to implement an animation on hover that's similar to the MacOS dock animation. Here's a picture for reference:
To further break it down, here's what I'm trying to accomplish. These images, on hover, should act as follows:
Hovered images expand
Neighboring images expand, but slightly less
Images don't overlap on expansion
Here is the code I have so far
Row {
spacing: 2
anchors.bottom: parent.bottom
anchors.bottomMargin: 30
anchors.horizontalCenter: parent.horizontalCenter
Repeater {
id: iconRepeater
model: iconColors()
Image {
source: "icons/" + modelData + ".png"
scale: mouseArea.containsMouse ? 1.5 : 1.0
MouseArea {
id: mouseArea
anchors.fill: parent
hoverEnabled: true
onClicked: endTimer()
}
Behavior on scale {
PropertyAnimation {
duration: 75
}
}
}
}
}
This expands the image you hover over, but I cannot seem to also effect the neighbors. Any advice is appreciated!
I'd suggest a little more robust solution, where you have control over the zoom factor and the spread and decay of influence:
Column {
Slider {
id: foff
from: 1
to: 5
stepSize: 1
value: 2
snapMode: Slider.SnapAlways
}
Slider {
id: sf
from: 0.5
to: 2.5
stepSize: 0.5
value: 0.5
snapMode: Slider.SnapAlways
}
Slider {
id: dmp
from: 1
to: 5
stepSize: 1
value: 1
snapMode: Slider.SnapAlways
}
}
Row {
id: row
anchors.bottom: parent.bottom
anchors.bottomMargin: 30
anchors.horizontalCenter: parent.horizontalCenter
property int falloff: foff.value // how many adjacent elements are affected
property int current: -1
property real scaleFactor: sf.value // that's how much extra it scales
property real damp: dmp.value // decay of influence
Repeater {
id: iconRepeater
model: 10
Rectangle {
width: 50 * pseudoScale
height: width
anchors.bottom: parent.bottom
color: "red"
border.color: "black"
property real pseudoScale: {
if (row.current == -1) return 1
else {
var diff = Math.abs(index - row.current)
diff = Math.max(0, row.falloff - diff)
var damp = row.falloff - Math.max(1, diff)
var sc = row.scaleFactor
if (damp) sc /= damp * row.damp
diff = diff / row.falloff * sc + 1
return diff
}
}
MouseArea {
id: mouseArea
anchors.fill: parent
hoverEnabled: true
onContainsMouseChanged: row.current = containsMouse ? index : -1
}
Behavior on pseudoScale {
PropertyAnimation {
duration: 150
}
}
}
}
}
It could be something along the lines of this:
Row {
anchors {
bottom: parent.bottom
left: parent.left
right: parent.right
}
Repeater {
id: rep
model: ['red', 'yellow', 'pink', 'green', 'teal', 'orchid', 'blue', 'orange']
property int currentIndex: -10
delegate: Rectangle {
anchors.bottom: parent.bottom
// Calculate the width depending on the currently hovered element
width: (rep.currentIndex === index ? 100 : ((rep.currentIndex - index) === 1 || (rep.currentIndex - index) === -1 ? 80 : 50))
height: width
radius: width / 2
color: modelData
MouseArea {
anchors.fill: parent
hoverEnabled: true
// onEntered/Exited did not react. This will work.
onContainsMouseChanged: {
if (containsMouse) rep.currentIndex = index
else rep.currentIndex = -10 // -10 is safe
}
}
// Makes the movement smooth
Behavior on width {
NumberAnimation {}
}
}
}
}
I tried to put in the necessary explainations as comment in the code.
The only thing that would need some tweeking is, that the dots will be initially shifted when the first resizing happens. Putting it on a flickable and some manual labour for the right position handeling could deal with that. Basically you need to shift the flickable by half the width change (in my case ~ 55 or so) to the left, when the mouse enters, and to the right when it leaves again.
You could also do so with a ListView, most likely, but due to the ever changing estimated size of the background, it might be more challanging to get the positioning right.

Particles with different images. [qml]

I am using particle systems. My particles come out from the center but I want different images to come out.
The file path of these images are stored in an array. I made a function to go through that arrangement and return what is in each position.
What returns is the path of each image to be sent to the source of the ImageParticle.
The problem is that if you scroll through the entire array but only return the path of the last image and logically I get a single image instead of the twenty that are stored in the array.
Someone could help me?
Help and suggestions are well accepted.
Here is my code:
import QtQuick 2.0
import QtQuick.Particles 2.0
Rectangle {
id: bg
width: 1920 //360
height: 1080 //360
color: "black"
ParticleSystem {
id: particleSys
}
Emitter{
id: particles
anchors.centerIn: parent
height: 1; width: 1
system: particleSys
emitRate: 30
lifeSpan: 4000
lifeSpanVariation: 500
maximumEmitted: 1000
size: 5
endSize: 200
velocity: TargetDirection{
targetX: 100; targetY: 100
targetVariation: 360
magnitude: 250
}
}
property var picturesList: [
"images/Image1.png", "images/Image2.png", "images/Image3.png", "images/Image4.png", "images/Image5.png", "images/Image6.png", "images/Image7.png", "images/Image8.png", "images/Image9.png", "images/Image10.png",
"images/Image11.png", "images/Image12.png", "images/Image13.png", "images/Image14.png", "images/Image15.png", "images/Image16.png", "images/Image17.png", "images/Image18.png", "images/Image19.png", "images/Image20.png"
]
function getImage(arr){
var flag = "";
for(var i = 0; i < arr.length ; i++){
flag = arr[i];
console.log("Image: " + arr[i] + " flag: " + flag ) //To check if array is traversing.
}
return flag;
}
ImageParticle{
property var link: getImage(picturesList)
source: link
system: particleSys
}
// To check which image is returned.
MouseArea {
anchors.fill: parent
onClicked: {
console.log(getImage(picturesList))
}
}
}
I am the person who asked the previous question and here I bring the answer.
I know very well that there can be several ways that solve the problem, if you know another way I invite you to share it.
Suggestions about the response are welcome.
Here I share the code:
import QtQuick 2.0
import QtQuick.Particles 2.0
Rectangle {
id: bg
width: 1920
height: 1080
color: "black"
ParticleSystem {
id: particleSys
}
Emitter{
id: particles
anchors.centerIn: parent
height: 1; width: 1
system: particleSys
emitRate: 30
lifeSpan: 4000
lifeSpanVariation: 500
maximumEmitted: 1000
size: 5
endSize: 200
velocity: TargetDirection{ //4
targetX: 100; targetY: 100
targetVariation: 360
magnitude: 250
}
}
property var picturesList: [
"images/Image1.png", "images/Image2.png", "images/Image3.png", "images/Image4.png", "images/Image5.png", "images/Image6.png", "images/Image7.png", "images/Image8.png", "images/Image9.png", "images/Image10.png",
"images/Image11.png", "images/Image12.png", "images/Image13.png", "images/Image14.png", "images/Image15.png", "images/Image16.png", "images/Image17.png", "images/Image18.png", "images/Image19.png", "images/Image20.png"
]
ItemParticle {
id: particle
system: particleSys
delegate: itemDelegate
}
Component {
id: itemDelegate
Rectangle {
id: container
width: 26*Math.ceil(Math.random()*3); height: width
color: 'white'
Image {
anchors.fill: parent
anchors.margins: 3
source: 'images/Image'+Math.ceil(Math.random()*20)+'.png'
}
}
}
}
As you can see, all the images in the folder will be output.
I simply change the "ImageParticle" to "ItemParticle" and I add a "Component" as a delegate where the desired image will be.
So we would not use the array (omit it in the previous code) since now only the path of the image is concatenated and a random number (to select the image).
I hope you serve them, and if you have a better implementation, please let them know.

QML timer combined with transition

import QtQuick 2.0
Rectangle {
id: rec
property int img_in:2
property int img_out:3
Image {
id: imgout
source: "pics/"+img_out+".jpg"
opacity: 1
anchors.fill: parent
}
Image {
id: imgin
source: "pics/"+img_in+".jpg"
opacity: 0
anchors.fill: imgout
}
Timer {
interval: 5000
repeat: true
running: true
onTriggered: {
img_in = img_in+1
img_out = img_out+1
anim.running = true;
}
}
states: State {
name: "state1"
PropertyChanges { target: imgout; opacity: 0}
PropertyChanges { target: imgin; opacity: 1}
}
SequentialAnimation {
id: anim
NumberAnimation { target: imgin; properties: "opacity"; easing.type: Easing.InOutQuad; duration: 1500 }
NumberAnimation { target: imgout; properties: "opacity"; easing.type: Easing.InOutQuad; duration: 1500 }
}
}
I would like to know if the problem is in opacity or in pics number change. Pics do change (suddenly) but there is no animation. Inside onTriggered I have tried to use these options: states, SequentialAnimation plus transition. No help.
So I took your code and customized it a bit. It basically starts at pics/1.jpg fades it out while fading pics/2.jpg in, then continues to the next images. You should be able to use it and change it to suit your needs.
Importantly there is no need to do this with States rather use Behaviour on the Image elements opacity
Hope this answers your question! It does make for a nice slideshow!
import QtQuick 2.0
Rectangle {
id: rec
// [1] First image is to be display is pics/1.jpg,
// followed by 2.jpg, 3.jpg, etc...
property int currentIndex: 1
property int nextIndex: 2
// [2] When swapping the image sources we need
// to block the animation behaviour.
// By default turn it on.
property bool allowBehaviour: true
// [3] When the 'rec' is loaded
// set the current image to fade out
// and the next image to fade in.
Component.onCompleted: {
currentImage.opacity = 0;
nextImage.opacity = 1;
}
Image {
id: currentImage
source: "pics/" + currentIndex + ".jpg"
opacity: 1
anchors.fill: parent
// [4] Here we define that whenever we change the
// opacity we want it to animate. Notice the enable
// is tied to `allowBehaviour`
Behavior on opacity {
enabled: allowBehaviour
NumberAnimation { easing.type: Easing.InOutQuad; duration: 2500 }
}
}
Image {
id: nextImage
source: "pics/" + nextIndex + ".jpg"
opacity: 0
anchors.fill: currentImage
// [5] See [4] above.
Behavior on opacity {
enabled: allowBehaviour
NumberAnimation { easing.type: Easing.InOutQuad; duration: 2500 }
}
}
Timer {
interval: 2500
repeat: true
running: true
onTriggered: {
// [6] Block the Behaviour animation.
allowBehaviour = false;
// [7] Advance the indices.
currentIndex = nextIndex;
++nextIndex;
// [8] This is key, set the current
// image to visible and the next
// image to invisible. This happens
// instantly as the Behaviour is off.
currentImage.opacity = 1;
nextImage.opacity = 0;
// [9] Turn the behaviour so the
// opacity change at [10] will
// cause an animation.
allowBehaviour = true;
// [10] Like [3] set the current
// image to fade out and the
// next image to fade in.
currentImage.opacity = 0;
nextImage.opacity = 1;
}
}
}

change button image

I have created a new custom button, can I set a different background image instead of 'circle' or 'triangle' ?
thanks
Chanan
exporting: {
enabled: true,
buttons: {
'realTimeButton': {
id: 'realTimeButton',
symbol: 'diamond',
x: -88,
symbolFill: realTimeColor,
hoverSymbolFill: realTimeColor,
_titleKey: "realTimeButtonTitle",
onclick: function(event) {
// handle change to real time
if ( enable_lastRoundsChart_realtime )
{
// disable real time flag
enable_lastRoundsChart_realtime = 0;
// re-create detail in real time mode disabled
createDetail(cache_last_rounds.last_rounds_data, window.show_top_round_ids);
// enable plotBand
if ( pb_master_chart )
{
pb_master_chart.options.chart.events.selection.enabled = 'true';
pb_master_chart.options.chart.zoomType = 'x';
}
}
else
{
// enable real time flag
enable_lastRoundsChart_realtime = 1;
// re-create detail in real time mode enabled
createDetail(cache_last_rounds.last_rounds_data, window.show_top_round_ids);
// update title
this.setTitle({text:"Players/Drops Per Round"}, {text:"Real Time"});
// if master found, remove plotBand and disable master selection
if ( pb_master_chart )
{
// remove plotBand
pb_master_chart.xAxis[0].removePlotBand('mask-before');
pb_master_chart.xAxis[0].removePlotBand('mask-after');
pb_master_chart.xAxis[0].addPlotBand({
id: 'mask-before',
from: -1,
to: 99999,
color: 'rgba(0, 0, 0, 0.2)'
})
// disable selection
pb_master_chart.options.chart.events.selection.enabled = 'false';
pb_master_chart.options.chart.zoomType = null;
}
}
}
},
According to the docs, the shapes are defined in the Highcharts.Renderer.symbols collection. Inspecting this object reveals the following available shapes:
Highcharts.Renderer.prototype.symbols:
arc: function (a,b,c,d,e){var f=e.start,c=e.r||c||d,g=e.end-1.0E-6,d=e.innerR,h=e.open,i=W(f),j=Z(f),k=W(g),g=Z(g),e=e.end-f<Aa?0:1;return["M",a+c*i,b+c*j,"A",c,c,
circle: function (a,b,c,d){var e=0.166*c;return["M",a+c/2,b,"C",a+c+e,b,a+c+e,b+d,
diamond: function (a,b,c,d){return["M",a+c/2,b,"L",a+c,b+d/2,a+c/2,b+d,a,b+d/2,"Z"]}
exportIcon: function (a,b,c,d){return y(["M",a,b+c,"L",a+c,b+d,a+c,b+d*0.8,a,b+d*0.8,"Z","M",a+c*0.5,b+d*0.8,"L",a+c*0.8,b+d*0.4,a+c*0.4,b+d*0.4,a+c*0.4,b,a+c*0.6,b,a+c*0.6,b+d*0.4,a+c*0.2,b+d*0.4,"Z"])}
printIcon: function (a,b,c,d){return y(["M",a,b+d*0.7,"L",a+c,b+d*0.7,a+c,b+d*0.4,a,b+d*0.4,"Z","M",a+c*0.2,b+d*0.4,"L",a+c*0.2,b,a+c*0.8,b,a+c*0.8,b+d*0.4,"Z","M",a+c*0.2,b+d*0.7,"L",a,b+d,a+
square: function (a,b,c,d){return["M",a,b,"L",a+c,b,a+c,b+d,a,b+d,"Z"]}
triangle: function (a,b,c,d){return["M",a+c/2,b,"L",a+c,b+d,a,b+d,"Z"]}
triangle-down: function (a,b,c,d){return["M",a,b,"L",a+c,b,a+c/2,b+d,"Z"]}
You can also add your own symbol by extending the collection. For example, drawing a simple X:
$.extend(Highcharts.Renderer.prototype.symbols, {
anX: function (a,b,c,d){return["M",a,b,"L",a+c,b+d,"M",a+c,b,"L",a,b+d]}
});
Produces:
Fiddle here.
You have ability to set image as icon
http://jsfiddle.net/Udgb3/
symbol: 'url(http://highcharts.com/demo/gfx/sun.png)',
symbolX:5,
symbolY:0

Resources