ID:754705
 
(See the best response by DarkCampainger.)
Problem description:
How to do this? I have pixel projectiles up and running thanks to PixelProjectiles by Shadowdarke. The problem is that it takes an Atom as a destination type and that atom appears to be static throughout the proc. If I used a mob (for example) as a destination, the proc wont work because it relies on that atoms pixel_x and pixel_y to calculate.

So,
My first question: How do I select a movable atom from a mob?

Next. I managed to change the destination x and y (vector increment) calculation so that it will follow the target.

Prior:
dx = (A.x - owner.x) * 32 + A.pixel_x - owner.pixel_x
dy = (A.y - owner.y) * 32 + A.pixel_y - owner.pixel_y

A - destination atom

Homing:
dx = (A.x - P.x) * 32 + A.pixel_x - P.pixel_x
dy = (A.y - P.y) * 32 + A.pixel_y - P.pixel_y

P-Projectile
(it recalculates every update cycle)
The problem is that the dx and dy values decrease as the projectile closes on its destination. So it slows down. (these values work as increments for the projectiles pixel_y and x)

Question: How to recalculate projectile's increment without losing speed?

Optional question: Is there a way to make icons slide between objects outside of tile boundaries without using pixel movement?

Thank you for your help. :)
Sometimes I use arctan2 to get the angle between two objects. With this angle, it is easy to make a vector using trigonometry:
vx = cos(theta) * speed
vy = sin(theta) * speed

The way you're doing it isn't bad either; you just need to get a unit vector and scale it to whatever speed you want it at.
//  Fixed by DC
var scale = speed / sqrt(dx * dx + dy * dy)
dx *= scale
dy *= scale
Thanks :) that might just work I will try it out.
Okay I reworked it to angles and stuff.
mob
dummy
Click()
FirePixelProjectile(usr,Angle(usr,src),/obj/projectile/minion)
icon='NPC.dmi'
HP=100
MaxHP=100

And it should all work perfectly. I just cant get over this runtime error...

runtime error: Cannot read 135.x
proc name: Angle (/proc/Angle)
usr: ViXWeT (/mob)
src: null
call stack:
Angle(ViXWeT (/mob), 135)
FirePixelProjectile(ViXWeT (/mob), 135, /obj/projectile/minion (/obj/projectile/minion))
In response to ViXWeT
FirePixelProjectile() should work by passing an angle as a destination, as the library's documentation states. Did you change anything in the library itself?

The issue is in the Angle() proc, as the run-time error says. It's confusing though, because the call stack shows the proper arguments in FirePixelProjectile() but not in Angle(). Are you calling Angle() anywhere else?

Also, it helps to debug when DEBUG mode is on. Enable it by checking the debugging preference in Build > Preferences. Run-time errors will provide a line number in the appropriate file.
I know exactly what is the problem. I just know dont know why it exists and how to fix it. If it helps:
proc
Angle(mob/origin,mob/destination)
var/dx=destination.x-origin.x*32
var/dy=destination.y-origin.y*32
var/angle=arccos(dx/sqrt(dx*dx+dy*dy))
return angle


The problem is that i pass a value (src) and get a runtime error that src doesnt exist OR doesnt have an x variable. Why? No idea. But basicly it acts as a var type conversion ... It loses src.loc (x,y,z) somewhere in the process of passing a function.

Thank you for fast replies. :) Sorry for bothering...
In response to Kaiochao
You should avoid trig when possible. It's much faster to normalize a vector than to compute the arctan, sine, and cosine. Also, you have to divide the components by the magnitude of the vector, not their individual values (it'll always be <±1,±1> otherwise)

var/scale = speed / sqrt(dx*dx + dy*dy) // We can normalize and resize the vector with one scalar
dx *= scale
dy *= scale


I don't think it is possible in this case as dx and dy are being recalculated every cycle and their values decrease as the projectile closes on its target. Which based on either my or your calculation causes the projectile itself to move slower the closer it is to its target. Please correct me if I am wrong. Speaking my thoughts here.

Anyways, any response to my runtime problem? I swear I can get it running the moment I can utilize src.x/y/z.
Best response
From the callstack, it looks like FirePixelProjectile() is calling Angle() again, and passing the angle you already calculated as the destination.

As to dx and dy decreasing as the projectile approaches the target, that's why you have to normalize the vector (aka rescale it to a length of 1) and then scale it up to the desired speed per tick.
YES! Thank you. All of you. Yes I was indeed passing the angle as a mob. Because I rewrote the proc and forgot about that segment I rewrote so logically I didn't think about that. It is all working now. Although on cos and sin. Nevermind, too happy now. If i get performance issues I will itterate on it :). Thank you both.