# vector.p8

a simple and lightweight (in tokens) vector math library for PICO-8.

usage:

`load #vector_p8`

and save as such: vector.p8- remove all the demo code; it's in the second tab
`#include`

in any cart you want

## functions within:

> NOTE:

> vectors are just normal Lua tables with `x`

and `y`

fields, so you can pass any table that contains `x`

and `y`

to any of the functions and they will work regardless.

### creation and management

`vector(x,y)`

- the main function. `x`

and `y`

default to `0`

`v_polar(angle, length)`

- makes a new vector using polar coordinates

`v_rnd()`

- returns a normalized vector with a random direction

`v_copy(v)`

- returns a copy of `v`

`v_unpack(v)`

- returns the components of `v`

separately

`v_tostr(v)`

- turns a vector into a string, appropriate for both debugging and normal output. it looks like `[x, y]`

### actual math

`v_add(a,b)`

- returns `a`

+ `b`

`v_sub(a,b)`

- returns `a`

- `b`

`v_scale(v,n)`

- returns `v`

scaled by `n`

`v_mul(v,n)`

- alias for `v_scale`

`v_div(v,n)`

- returns `v`

scaled by the inverse of `n`

`v_dot(a,b)`

- returns the dot product of `a`

and `b`

`v_magsq(v)`

- returns the squared magnitude of `v`

`v_mag(v)`

- returns the magnitude of `v`

`v_distsq(a,b)`

- returns the squared distance between `a`

and `b`

`v_dist(a,b)`

- returns the distance between `a`

and `b`

`v_norm(v)`

- returns `v`

, normalized

`v_perp(v)`

- returns a vector clockwise-perpendicular to `v`

`v_proj(a,b)`

- returns the projection of `b`

onto `a`

`v_dir(a,b)`

- returns a normalized vector that points towards `b`

, with origin at `a`

.

`v_rot(v,t)`

- returns `v`

rotated to point towards angle `t`

.

`v_rotby(v,t)`

- returns `v`

rotated by `t`

.

`v_angle(v)`

- returns the angle denoted by `v`

### miscellaneous

`v_lerp(a,b,t)`

- linearly interpolates from `a`

to `b`

by `t`

`v_flr(v)`

- returns `v`

, with all its components floored

## constants

> **WARNING!**

> because of the way Lua tables work, do **NOT** use compound assignments to alter a variable if you directly assign one of these constants to it. either copy the constant using `v_cpy`

and then assign that to the variable or use one of the functions within the library to manipulate it.

`v_right`

- rightwards pointing vector.

`v_left`

- leftwards pointing vector.

`v_up`

- upwards pointing vector. Y points downward in 2D so this vector points towards -Y.

`v_down`

- downwards pointing vector. Y points downward in 2D so this vector points towards +Y.

`v_one`

- identity vector. all components are set to 1.

`v_center`

- utility vector pointing towards the center of the screen, i.e. [64,64].

## changelog

### format: dd-mm-yyyy

v2.3 (23-10-2024):

- fixed
`v_lerp`

using`v_scl`

instead of`v_scale`

or`v_mul`

`v_rot`

rotates*to*`t`

, not*by*`t`

; changed the docs of`v_rot`

to mention that, and added`v_rotby`

- post related update: removed the "rotation related functions" section; not exactly useful

v2.2 (02-10-2024):

- fixed undefined global call to
`v_dstsq`

in`v_dist`

(see v2.0 changelog) - added version number to cart title
- programmed a new demo! check the second tab in the editor (tab 1)

v2.1.1 (02-10-2024):

- accidentally switched x and y around in
`v_angle`

, sorry about that

v2.1 (02-10-2024):

- the calls to cos and sin in
`v_polar`

were swapped with each other - the formula for
`v_proj`

was taken from Wikipedia, and it projects b onto a, not a onto b; the docs were updated to reflect that

v2.0 (24-05-2024):

almost a 50% reduction on tokens, in exchange for various breaking changes:

- removed
`v_eq`

,`v_zero`

,`v_atwds`

,`v_isvec`

,`v_arr`

and`v_sprj`

- removed z component from all functions, the 3D constants and
`v_cross`

as in, this library no longer supports 3D math. sorry. it was oddly shoehorned in though, so I really wouldn't have relied on it that much. - added
`v_dir`

, taken from a mod of the library done by snale - optimized
`v_lerp`

,`v_sub`

and`v_rot`

`v_proj`

now uses the proper definition for vector projection- extended the names of some functions:
`v_cpy`

->`v_copy`

`v_unpck`

->`v_unpack`

`v_scl`

->`v_scale`

`v_ang`

->`v_angle`

`v_cntr`

->`v_center`

`v_dst`

->`v_dist`

`v_dstsq`

->`v_distsq`

v1.2.1 (11-03-2023):

- thought I had fixed all functions that used
`v_getd`

, but turns out one function I hadn't added to the docs,`v_flr`

, still used it - documented
`v_flr`

- improved explanation for
`v_atwds`

v1.2 (06-12-2022):

- fixed the math functions
`v_add`

,`v_sub`

,`v_scl`

,`v_div`

and`v_neg`

using the now-defunct`v_getd`

function

v1.1 (09-11-2022):

- removed all dimension related functions

Consequently, a parameter was added to v_tostr for it to know how to format the output - added
`v_sprj`

and`v_proj`

- renamed
`v_center`

to`v_cntr`

v1.0 (09-11-2022):

- initial release

oh yeah, right, the cart here has a demo, you gotta remove that code and then you can use the lib. I gotta put that in the post...

This is great, thank you!

Two questions:

- v_polar seems to invert x and y, shouldn't it be
`x=l*cos(a)`

and`y=l*sin(a)`

? - from my experiments, it looks like v_proj is projecting b on a, instead of a on b (as stated in the description)

It's been a while since I studied trig, so I may have gotten both completely wrong :)

funnily enough, you're right on both :)

v_polar is like that because when I wrote this library I wasn't aware sin and cos weren't interchangeable, so I used them in either order, and I guess I just forgot about it

and for v_proj, I guess I'll just swap a and b in the description

I'll push a single minor update to fix both of these, thanks for pointing out both errors!

I'm using your lib in my game and it's saving me a lot of time.

Hope you don't mind if I keep posting minor issues as I find them, sorry in advance for the spam:

`v_lerp`

calls`v_scl`

instead of`v_scale`

I also added three functions that I needed, feel free to add them if you like'em

function v_limit(v,n) local mgsq=v_magsq(v) if mgsq > n*n then return v_scale(v_div(v,sqrt(mgsq)),n) end return v end function v_bounce(v,n,br) --https://gamedev.stackexchange.com/a/35537 return v_sub(v,v_mul(n,(1+br)*v_dot(v,n))) end v_reflect=v_bounce function v_grow(v,n) local vm=v_mag(v) local norm=v_div(v,vm) return v_mul(norm,vm+n) end |

oop, didn't catch that one either, thanks!

about the extra functions:

`v_bounce`

is the vector reflection function, would be better if you called it`v_reflect`

`v_grow`

could be left off as it can be replicated in this way:local m = v_mag(v) local g = v_scale(v, (m+n)/m)

but it does look more intuitive as a function

`v_limit`

also sounds useful, but it's the kinda function you'd rather implement in code than in the library, though I'm probably biased

that being said, I'm not sure whether to add those functions... maybe if they're really commonly used but I don't usually check that kinda stuff

also again, thanks for reporting that bug, just released a patch version

[Please log in to post a comment]