How to apply mouse Click event for 3D model - html

Added 3D collada (.dae) file in to a scene. The 'DAE' file contains geometry with the name "monster" and the id is "monster-mesh-skin". I tried to apply mouse click event to the geometry "monster". like,
var monster = dae.getChildByName("monster"); // get geometry
monster.addEventListener("click", meshClickHandler);
The click event is not working. And I tried THREE.Vector3() and THREE.Ray like,
var mouse3D = new THREE.Vector3();
mouse3D.x = event.clientX;
mouse3D.y = event.clientY;
mouse3D.z = 0.5;
var ray = new THREE.Ray(mouse3D);
var intersects = ray.intersectObjects(monster);
console.dir(intersects);
on document click handler. In intersects variable not contain any value.
Is there any solution to apply mouse event for 3D model and control it?

It appears you need to rethink the approach a bit. Any 3D object in your scene exists exclusively as a 2D "drawing" of an object and itself can not have standard DOM event handlers attached to it.
What you want is a general event listener on the document itself to capture mouse clicks, like so:
document.addEventListener( 'click', detectIntersect, false );
Now, there are a ton of example right in Three.js example directory that can show you exactly how to "click your object", but in 3D terms it's refered to as object picking or raycasting an object. These terms might help when searching for examples/help. Have a look at these examples:
http://threejs.org/examples/webgl_interactive_cubes.html
http://threejs.org/examples/canvas_interactive_cubes_tween.html
One last note, it appears your using r57 or earlier of the Three.js library. I would suggest upgrading to the latest build as getting support from the community is easier when were all on the same page :)
Hope that helps, take care.

Related

Draw polygon using ngmap

I'm trying to draw polygon on my map using ngmap. The map is displayed correctly as this example is showing, but when I finish the draw, this is what I'm getting:
ng-map.min.js:25 Uncaught TypeError: Cannot read property 'onMapOverlayCompleted' of undefined
I used the same code of the example.
My questions:
1- How can I solve this error?
2- If I want to let the user draw only polygon form, I have tried to set the value of drawingMode to "polygon" but I'm always having the other draw options (circle...). How can let only the polygon draw?
3- How can I let the user clear the drawn polygon?
4- Is it possible to detect the action of putting (drawing) every points. I mean that to draw a line in the polygon for example I need at least two points. Can I detect when the user draw the first point then the second and get its coordinates?
Edit
This is the whole error that I see when I include ng-map.js instead of ng-map.min.js :
Uncaught TypeError: Cannot read property 'onMapOverlayCompleted' of undefined
at index (http://localhost:8080/bower_components/ngmap/build/scripts/ng-map.js:2690:44)
at Array.reduce (native)
at Uw.<anonymous> (http://localhost:8080/bower_components/ngmap/build/scripts/ng-map.js:2691:39)
at P4._.z.trigger (https://maps.google.com/maps/api/js?key=MY_API_KEY&libraries=placeses,visualization,drawing,geometry,places:99:121)
at P4.<anonymous> (https://maps.google.com/maps/api/js?key=MY_API_KEY&libraries=placeses,visualization,drawing,geometry,places:37:81)
at C4._.z.trigger (https://maps.google.com/maps/api/js?key=MY_API_KEY&libraries=placeses,visualization,drawing,geometry,places:99:121)
at C4.<anonymous> (https://maps.google.com/maps/api/js?key=MY_API_KEY&libraries=placeses,visualization,drawing,geometry,places:37:81)
at Object._.z.trigger (https://maps.google.com/maps/api/js?key=MY_API_KEY&libraries=placeses,visualization,drawing,geometry,places:99:121)
at F4 (https://maps.google.com/maps-api-v3/api/js/28/14/drawing_impl.js:7:70)
at G4 (https://maps.google.com/maps-api-v3/api/js/28/14/drawing_impl.js:4:249)
Edit 2
I solved the first question:
My problem was that I'm using routes in the app.js. So the html and the controller are linked in it. To solve the problem, I put $scope.onMapOverlayCompleted instead of
var vm = this;
vm.onMapOverlayCompleted because I don't write the the ng-controller="DrawingManagerCtrl as vm" in my HTML. Then in the HTML I put on-overlaycomplete="onMapOverlayCompleted()" and it works.
I solved also the second question by using:
drawing-control-options="{position: 'TOP_CENTER',drawingModes:['polygon']}"
I'm want now to solve the other problems.
Any help please?
3
As the example you referenced shows, the overlaycomplete callback function receives e (Event) as the first parameter. This OverlayCompleteEvent object contains reference to the drawn overlay at Event.overlay (see docs of the original Google Maps JS API more info, since ng-map is only wrapper of the original API after all, specifically "OverlayCompleteEvent object specification" section).
Using that you can get the reference to the created overlay, store it and then later call .setMap(null) on it to delete it from map. E.g:
$scope.myDrawnOverlays = []; //array where you store drawn overlays
$scope.onMapOverlayCompleted(e){
...
myDrawnOverlays.push(e.overlay); //store reference to the drawn overlay after it's drawn
}
$scope.deleteAllDrawnOverlays(){
for(var i = 0; i < myDrawnOverlays.length; i++){
myDrawnOverlays[i].setMap(null); //remove overlays from map one by one
}
myDrawnOverlays = [];
}
Then whenever you want to delete all overlays, just call the function $scope.deleteAllDrawnOverlays (you can tie it to some button using ng-click or do whatever you want with it).
4
This is NOT possible using google.maps.drawing.DrawingManager which is used in your example. The reason is that DrawingManager doesn't support events for clicking at the map while drawing (see docs again for possible events, section "DrawingManager class").
So except hacky workarounds which could break any time with new api release, the only possible solution is to implement drawing of polygon yourself and not use DrawingManager. Check for example this SO answer, specifically the referenced example (right-clicks on map). They don't use ng-map, but basically what would you have to do is to add on-click="mapClickHandler" to your ng-map, in the mapClickHandler get position where you clicked on map, draw Marker there which would look like a dot and if you have more dots connect them with lines.
This is however too much for one question, you would have to probably read up on ng-map and relevant sections of Google Maps Js Api yourself.

Is it possible to independently drag & drop multiple objects on a FabricJS canvas at the same time?

I'm working on a touch-based app w/ Fabric.js. Out of the box, the drag & drop support is phenomenal. Unfortunately, you can only drag one object at a time - the rest of the canvas is essentially 'locked' until the current object's drag has ended.
Is it possible to concurrently drag more than one object at a time? How could it be accomplished? My use case is this: imagine a canvas with multiple puzzle pieces you can touch/drag around. I'd like to be able to independently touch and drag at least 2 pieces (each with a different finger) at the same time.
I'm using the standard drag event handler. I don't see any obvious way to accomplish this.
canvas.on('object:moving', function (e) { ... });
You can group your objects.
var mygroup = new fabric.Group([ obj1, obj2, obj3 ], { left: 200, top: 200 });
canvas.add(group);
You can pre-group your objects or let user select which objects to group. A group can be draggable alltogether.
This method works after version 1.3.12

mouseX/mouseY Actionscript function equivalent in Cocos2D

This might be irritating simple. I am trying to convert some code from actionscript to cocos2d. I am quite new to actionscript and would like to know if there is a cocos2d function for mouseX/mouseY. If not, what would be the equivalent. Can someone please help me.
In Kobold2D (which is based on cocos2d-iphone) you can use the mouseLocation:
CGPoint mousePos = [KKInput sharedInput].mouseLocation;
KKInput captures the mouse location every time it receives an event. If mouse moved events are enabled, mouse location gives the accurate location of the mouse.
The alternative is to use the NSWindow method mouseLocationOutsideOfEventStream.

Clearing canvas causes the old content to re-appear on the next draw

I have a clear button which seems to work..but actually its not. When I click back on the canvas I can see the drawing.
There is no problem in the way you are clearing the canvas, the problem lies in your logic.
Everytime you click or move the mouse the addClick method is called, which populates the arrays clickX, clickY and clickDrag with the coordinates; and then the redraw method is called which plots the points on the canvas.
So when you clear the canvas you are failing to reset these arrays, so when the redraw method is called again (after clearing the canvas), the old points get plotted too.
So try emptying the arrays clickX, clickY and clickDrag as shown below, when you clear your canvas; so that the old points are not considered when you start fresh.
clickX = [];
clickY = [];
clickDrag = [];

AS3: Making a SimpleButton from library sprites: Possible?

I'm working on a small project in AS3, and I need to make some interface buttons. I had them as separate classes at first, but then realized that it was probably overkill, and on top of that, figured out a way to simplify the event calls by making them buttons and assigning the event dispatches to their parent.
ANYWAY,
I tried remaking them using the SimpleButton class, but I can't figure out how to give the buttons any sort of design. Every tutorial on the web uses SimpleButton to make only the most bare-bones Actionscript graphics by actually drawing them with the code (why anybody would want to do that is beyond me), and my attempt at assigning a library item to the upState:
_deletebutton = new SimpleButton();
_deletebutton.upState = mc_deleteButtonUp; <--- exists in my library
doesn't do anything.
The Adobe docs say that the various states take DisplayObjects, which mean they take Sprites and MovieClips, so you should be able to do this. Does anyone know how?
THANK YOU
+1 weltraumpirat
the example in the doc generates the states by code but you can assign whatever displayObject to the different states of the button.
var btn:SimpleButton = new SimpleButton();
btn.downState = new clipFromLibDown();
btn.overState = new clipFromLibOver();
btn.upState = new clipFromLibUp();
btn.hitTestState = new clipFromLibHit();
btn.useHandCursor = true;
addChild( btn );
assuming you have 4 states called : clipFromLibDown, clipFromLibOver ... in your library, this works
You have to instantiate an item from your library in order to use it with ActionScript. To do this, click "Export for ActionScript" and assign a class or base class to mc_deleteButtonUp in the properties panel. Then use the new operator with the assigned class to instantiate it. You can start your button by using the example from Adobe's documentation, then change things to fit your own program.
You're probably not setting the hitTestState property of your SimpleButton instances. This property is a DisplayObject that defines where the user has to move the mouse to get mouse events on the SimpleButton. You will never see the DisplayObject that you set this to. I would suggest just using one of the DisplayObjects you are already using for another state.
http://help.adobe.com/en_US/FlashPlatform/reference/actionscript/3/flash/display/SimpleButton.html#hitTestState
Also you will need to use the new operator as weltraumpirat and nicoptere have already said.