Rotating a canvas object around the mouse cursor - html

I am trying to replicate this effect: http://hakim.se/experiments/html5/trail/03/
I have this as a Particle constructor:
function Particle(x, y) {
this.x = x;
this.y = y;
this.radius = 4;
this.color = '#f0f';
this.speed = 15;
this.angle = 0;
}
And I'm using this loop to animate all particle instances:
for (var i = 0, len = particles.length; i < len; i++) {
var dx = mouse.x - particles[i].x,
dy = mouse.y - particles[i].y,
angle = Math.atan2(dy, dx);
particles[i].vx = Math.cos(angle) * particles[i].speed;
particles[i].vy = Math.sin(angle) * particles[i].speed;
particles[i].x += particles[i].vx;
particles[i].y += particles[i].vy;
particles[i].draw(ctx);
}
The particles follow the mouse, but reach the cursor and start flickering around it, which is not a desired behaviour. I'd like to circle around the cursor, as in the example.. The interesting part is that if I set the particle.speed to something like 30 and add 1000 to the angle, the particles rotate around the cursor, but really fast and ruin the effect...
You can see a live example here: http://codepen.io/gbnikolov/pen/EwafI
All suggestions are more then welcome, thanks in advance!
P.S. I know that the code for the pointed example is easily findable, but I'm relatively new to javascript and I'm not that good at reading other people code and can't quite understand the logic behind it..

Currently the target of your particles is the mouse cursor. But that's not the target you want. You want a target that's moving around your cursor. And you want for every particle a different target, so they don't hover all at the same place.
There are also some other things that the original does and you don't:
in the original, the particle speed depends on the distance to the target
it seems they can't change the direction instantly, but change the direction of their movement relatively slowly.

Related

how to make a bullet shoot diagonally in flash as3

I have been having this problem for ages and haven't found a solution for this.
Well in flash I have a character who's gun position is similar to this
http://us.123rf.com/400wm/400/400/chudtsankov/chudtsankov1004/chudtsankov100400927/6906625-cartoon-character-mobster-carries-weapon.jpg
I have been having difficulties in try to shoot the bullet in the same angle as the gun is pointing. I've tried working with angles but it just doesn't seem to be working.
Right now, the bullet is shooting straight up but i want it to shoot in an angle.
So far I have this
function shootBullet():void {
var fire:myBullet2 = new myBullet2();
fire.x = GirlHero.x;
fire.y = GirlHero.y;
addChild(fire);
fire.addEventListener(Event.ENTER_FRAME, moveBullet);
}
Any help would be much appreciated! Thank you! :) By the way, my character is controlled by the left,right and up key, The up key is to shoot and the left is to walk left and right to walk right.
There's a good example of this at:-
http://rhuno.com/flashblog/2011/11/18/calculating-angles-and-moving-objects-accordingly/
You want to do something like
var angle:int = 270;
var rads:Number = angle*Math.PI/180;
var speed:int = 2;
function moveBullet(e:Event)
{
e.currentTarget.x += Math.cos(rads) * speed;
e.currentTarget.y += Math.sin(rads) * speed;
}
You'll need to set angle accordingly depending on which way the character is facing (if it flips)

how to move polygon points depending on movement of one point?

i have polygon say (Hexagonal with 6 lines) this Hexagonal connected from center with 6 point That make 6 triangles
I need when move any point(cause to move triangles) ,, other points move like this point i mean if the left point move to lift other points move to the left and so on
the code I want like this ptcP1.x and ptcP1.y the point that i moving it other point move depend on ptcP1 movement note that, this equations work fine in square shape ,, put in Penta and hexa ..etc this equations in valid so can any one help me
function button1_triggeredHandler( event:Event ):void
{
mode="mode2";
//trace(list.selectedIndex);
if(list.selectedIndex==1)
{
DrawSqure.ptcP1.x = Math.random() + 50;
DrawSqure.ptcP1.y = Math.random() + 50;
DrawSqure.ptcP2.y = 50-DrawSqure.ptcP1.x;
DrawSqure.ptcP2.x = DrawSqure.ptcP1.y;
DrawSqure.ptcP3.x = 50-DrawSqure.ptcP1.y;
DrawSqure.ptcP3.y = DrawSqure.ptcP1.x;
DrawSqure.ptcP4.x = 50-DrawSqure.ptcP1.x;
DrawSqure.ptcP4.y = 50-DrawSqure.ptcP1.y;
}
As stated in the comments, storing the vertices/points into a container (Array or Vector) and then adjusting those positions when you move is the best way to do it. Here is an example of how that might work:
//setup array or vector of vertices
var polygonVertices:Array = [DrawPolygon.ptcP1, DrawPolygon.ptcP2, DrawPolygon.ptcP3, DrawPolygon.ptcP4];
This method will take all the vertices and apply the translation:
//function for adjusting all the vertices based on the distance you pass
function moveShape( vertices:Array, dx:Number, dy:Number ) {
var i:int;
for ( ; i < vertices.length; i++ ) {
vertices[i].x += dx;
vertices[i].y += dy;
}
}
Then you would just need to know your distance X & Y your shape has moved and you can call moveShape( polygonVertices, 100, 100 );
I inserted 100,100 as the distance parameters as an example, but this should give you the results you are looking for.

AS3 - Finding the Y position of a rotated object if X is known

I am trying to find out the Y position of a rotated object on stage, when only the X position is known. I am not extremely formiliar with how I'd go about doing this, but I know it'll be related to the Rotation of the border object.
What I need to do is know that based on the below X position that is worked out, what the exact maximum Y position can be before it hits the black border that is onscreen. I know that the original position is 280, but I am not sure at all how I then work out what the Y position is further down the line.
I have attached the code to find the X (all be it, it doesn't take into account any rotation as on this level it isn't needed), as well as a screenshot so you can understand clearly.
Thank you for your time.
private function init(e:Event = null):void{
var maxX:int = stage.width
var freeSpace:int = 300
var startX:int = Math.ceil(Math.random() * (maxX - (freeSpace+this.width))) + freeSpace;
this.x = startX
}
I'm not entirely sure on your question but hopefully these suggestions will help:
You can use the localToGlobal() function on a display object to return a rotated, translated, and scaled point within that display container to the stage. Example, $p:Point = myMovieClip.localToGlobal(new Point(10, 10));
A Matrix is also a nice and easy way to rotate a point. Example, var $mtx:Matrix = new Matrix(); $mtx.tx = 10; $mtx.ty = 10; $mtx.rotate(); and now $mtx.tx and $mtx.ty have the rotated result
Those probably won't answer your question, but I figured I'd mention them just in case and before I get into something more complex. Like wvxvw said you can't really solve the equation you're trying to do without some other variables. I wrote some code that shows how to find Y when comparing X to a point in a line segment:
import flash.display.Shape;
import flash.geom.Point;
import flash.display.Graphics;
import flash.events.MouseEvent;
var $s:Shape = new Shape();
addChild($s);
var borderStart:Point = new Point(stage.stageWidth/2, stage.stageHeight/2);
var borderRotation:Number = 45;
var borderLength:Number = 800;
var borderRad:Number = borderRotation * (Math.PI/180);
var borderEnd:Point = new Point(borderStart.x + Math.cos(borderRad) * borderLength, borderStart.y + Math.sin(borderRad) * borderLength);
stage.addEventListener(MouseEvent.MOUSE_MOVE, update);
function update(e:MouseEvent):void{
var $g:Graphics = $s.graphics;
$g.clear();
//Drawing the rotated border
$g.lineStyle(3, 0xff0000, .5);
$g.moveTo(borderStart.x, borderStart.y);
$g.lineTo(borderEnd.x, borderEnd.y);
//Finding if and where mouseX collides with our border
if (stage.mouseX >= Math.min(borderStart.x, borderEnd.x) && stage.mouseX <= Math.max(borderStart.x, borderEnd.x)){
var $x:Number = stage.mouseX;
//SOLVING HERE : Solve collision with X
var $percent:Number = ($x - borderStart.x)/(borderLength * Math.cos(borderRad));
var $y:Number = borderStart.y + Math.sin(borderRad) * borderLength * $percent;
//Drawing to our collision
$g.lineStyle(1, 0xffff00, .6);
$g.moveTo($x, 0);
$g.lineTo($x, $y);
$g.lineStyle(2, 0xffff00, 1);
$g.drawCircle($x, $y, 3);
trace("----\nCollision #\t" + "x: " + $x + "\ty:" + Math.round($y));
}
}
Hopefully this will give some insight on how to solve your particular issue.
I'm not sure if I'm answering the right question, because as you worded it, it's impossible to solve, or rather you would have to accept that Y can be just anything... (In order to be able to find a point in a vector space over R^2 you need a basis of two vectors of a form (x,y), but you only have a vector in R^1).
But it looks like you want to find an intersection of the "black line on the screen" - i.e. an arbitrary line and a vertical line through the lowest point of the "shape" which you want to fit. It's hard to tell from the question, what shape are you trying to fit, but if it is a rectangle, which is not rotated, then it would be either its bottom right or bottom left corner. You can then find which point to choose by comparing the angle between a horizontal line and the "black line" and the horizontal line and the bottom of the rectangle.
Next, you would need to find an intersection between these two lines, the formula can be found here: http://en.wikipedia.org/wiki/Line_intersection

Problem rotating image with MOUSE_MOVE

Hey gang. Stumped on something.
I have a disc I am rotating with the mouse with event.MOUSE_MOVE, like a jog wheel on some audio equipment. Everything almost works as expected, but the problem I am experiencing is that the disc always jumps to the point where the user clicks on the disc. I need the point on the disc that the user clicks on to remain under the mouse while the user spins the disc but I can't seem to come up with the correct math to make it happen. Here's the code i am using:
var xd = (_knob.x - _stageRef.stage.mouseX);
var yd = (_knob.y - _stageRef.stage.mouseY);
var radAngle = Math.atan2(yd, xd);
_knob.rotation = int(radAngle * 360/(Math.PI * 2) - 90);
_knob is a vector circle wrapped in a movieclip, with the circle centered on the movieclip's reg point. _stageRef represents the main stage.
Any help would be awesome. I've scoured the interweb and can't come up with anything.
Thx!
You are setting _knob rotation to the angle between _knob and mouse cursor. So if rotation was 0, and angle 45, rotation becomes 45, therefore it jumps. What you need is measure changes in this angle, not setting it instantly:
var _mouseAngle:Number;
function getMouseAngle():Number
{
var xd = (_knob.x - _stageRef.stage.mouseX);
var yd = (_knob.y - _stageRef.stage.mouseY);
return Math.atan2(yd, xd);
}
function onMouseDown(event:MouseEvent):void
{
_mouseAngle = getMouseAngle();
}
function onMouseMove(event:MouseEvent):void
{
var newAngle:Number = getMouseAngle();
_knob.rotation += (newAngle - _mouseAngle) * 180.0 / Math.PI; //EDIT: forgot to convert into degrees
_mouseAngle = newAngle;
}
(Code not tested)

Billboard orientation toward camera (point) without normals

So I have a circle of planes which get constructed as:
plane.x = Math.cos(angle) * radius;
plane.z = Math.sin(angle) * radius;
plane.rotationY = (-360 / numItems) * i - 90;
which calculates how many angular slices there are for total number of planes (rotationY) and places each plane into it's place on a circle of radius.
then to update their rotation around the circle I have:
var rotateTo:Number = (-360 / numItems) * currentItem + 90;
TweenLite.to(planesHolder, 1, { rotationY:rotateTo, ease:Quint.easeInOut } );
as you can see planes are circling and each is oriented 90 degrees out from the circle.
I'm using this as a reference - it's pretty much that: http://papervision2.com/a-simple-papervision-carousel/
Now, what I'd like to find out is how could I calculate degree of orientation for each individual plane to always face camera without normal, if it's possible at all. I've tried plane.LookAt(camera), but that doesn't work. Basically every plane should have orientation as the one facing camera in the middle.
Somehow I think I can't modify that example from link to do that.
edit: OK I answered my own question after I wrote it. Helps to read your own thoughts written. So as I'm orienting planes individually and rotating them all as a group, what I did after tween of the group in code above, was to loop through each plane and orient it to the Y orientation of the forward plane as so:
for (var i:int = 0; i < planes.length; i++) {
TweenLite.to(planes[i], 1, { rotationY:(-360 / numItems * rotoItem - 90), ease:Quint.easeInOut } );
}
rotoItem is the one at the front. Case closed.
OK I answered my own question after I wrote it. Helps to read your own thoughts written. So as I'm orienting planes individually and rotating them all as a group, what I did after tween of the group in code above, was to loop through each plane and orient it to the Y orientation of the forward plane as so:
for (var i:int = 0; i < planes.length; i++) {
TweenLite.to(planes[i], 1, { rotationY:(-360 / numItems * rotoItem - 90), ease:Quint.easeInOut } );
}
rotoItem is the one at the front. Case closed.