Rev 1695 |
Rev 1713 |
Go to most recent revision |
Blame |
Compare with Previous |
Last modification |
View Log
| RSS feed
/*
* gravity.cc
* DIN Is Noise is copyright (c) 2006-2021 Jagannathan Sampath
* For more information, please visit https://dinisnoise.org/
*/
#include "gravity.h"
#include "font.h"
#include "vector2d.h"
#include "drone.h"
#include "console.h"
#include <fstream>
using namespace std;
extern int mousex, mouseyy;
extern void make_arrow (float* A, int k, float x, float y, float ux, float uy, float vx, float vy, float u, float v);
gravity_t::gravity_t () {
handle_size = 5;
strength = 0;
hitt = NOTHING;
lmb_clicked = 0;
tracked_drone = 0;
mag0 = 50;
mag = 0;
keep_size = 0;
bzero.set_text ("Zero");
breset.set_text ("Reset");
keepsize.set_text ("Keep size");
LISTEN(fold,this)
LISTEN(bzero,this)
LISTEN(breset,this)
}
void gravity_t::calc (int calc_mag) {
direction (base2tip, base, tip);
perpendicular (p_base2tip, base2tip);
bottomleft (base.x - handle_size, base.y - handle_size);
topright (base.x + handle_size, base.y + handle_size);
fold.set_pos (topright.x + 5, bottomleft.y);
textpos (fold.extents.right + 5, bottomleft.y);
bzero.set_pos (textpos.x, textpos.y - line_height);
breset.set_pos (textpos.x, bzero.extents.bottom - line_height);
keepsize.set_pos (breset.extents.right + 8, breset.extents.bottom);
gx = strength * base2tip.x; gy = strength * base2tip.y;
gl_base[0]=bottomleft.x; gl_base[1]=bottomleft.y;
gl_base[2]=topright.x; gl_base[3]=gl_base[1];
gl_base[4]=gl_base[2];gl_base[5]=topright.y;
gl_base[6]=gl_base[0];gl_base[7]=gl_base[5];
make_arrow (gl_arrow, 0, base.x, base.y, base2tip.x, base2tip.y, p_base2tip.x, p_base2tip.y, 0.6f, 0.2f);
if (calc_mag) mag = magnitude (base2tip);
}
void gravity_t::set (point<int>& what, int mx, int my, int calc_mag) {
what.x = mx;
what.y = my;
calc (calc_mag);
}
void gravity_t::set_strength (float s) {
strength = s;
gx = strength * base2tip.x;
gy = strength * base2tip.y;
}
int gravity_t::hit (const point<int>& what, int mx, int my) {
double m = magnitude (what.x, what.y, mx, my);
if (m <= handle_size) return 1; else return 0;
}
int gravity_t::handle_input () {
HANDLEINPUT(fold)
else if (fold.dir == arrow_button::down) {
HANDLEINPUT (bzero)
else HANDLEINPUT (breset)
else HANDLEINPUT (keepsize)
}
if (is_lmb (this)) {
if (lmb_clicked == 0) {
lmb_clicked = 1;
if (hitt != NOTHING) {
hitt = NEXT_TO_NOTHING;
} else {
if (hit (tip, mousex, mouseyy)) {
hitt = TIP; // edit tip
is_lmb.tie = this;
} else
if (hit (base, mousex, mouseyy)) {
hitt = BASE; // edit base
is_lmb.tie = this;
}
}
}
} else {
if (hitt == NOTHING) {
}
else
if (hitt == NEXT_TO_NOTHING) {
stop_editing ();
} else if (hitt == TIP) { // update tip
set (tip, mousex, mouseyy);
} else if (hitt == BASE) { // update base
set (tip, mousex + base2tip.x, mouseyy + base2tip.y, 0);
set (base, mousex, mouseyy, 0);
}
lmb_clicked = 0;
}
return hitt;
}
void gravity_t::load (ifstream& file) {
string ignore;
int bx, by, tx, ty; file >> ignore >> bx >> by >> tx >> ty;
set (base, bx, by);
set (tip, tx, ty);
file >> strength >> visible >> keep_size;
}
void gravity_t::save (ofstream& file) {
file << "gravity " << base.x << spc << base.y << spc << tip.x << spc << tip.y << spc << strength << spc << visible << spc << keep_size << endl;
}
void gravity_t::draw () {
fold.draw ();
if (fold.dir == arrow_button::down) {
bzero.draw ();
breset.draw ();
keepsize.draw ();
}
glColor3f (1, 0.6, 0.5);
draw_string ("Gravity", textpos.x, textpos.y);
glVertexPointer (2, GL_INT, 0, gl_base);
glDrawArrays (GL_LINE_LOOP, 0, 4);
glVertexPointer (2, GL_FLOAT, 0, gl_arrow);
glDrawArrays (GL_LINES, 0, 6);
}
void gravity_t::reset (int ks) {
keep_size = ks;
double m;
if (keep_size) m = mag; else m = mag0;
tip.x = base.x;
tip.y = base.y - m;
calc (0);
mag = m;
}
void gravity_t::zero () {
tip.x = base.x;
tip.y = base.y;
mag = 0;
calc (0);
}
void gravity_t::dir (float x, float y) {
tip.x = base.x + mag * x;
tip.y = base.y + mag * y;
calc (0);
}
void gravity_t::track () {}
int gravity_t::stop_editing () {
if (hitt != NOTHING) {
hitt = NOTHING;
is_lmb.clear (this);
return 1;
}
return 0;
}
void gravity_t::clicked (button& b) {
if (&b == &fold) {
if (fold.dir == arrow_button::right) {
fold.set_dir(arrow_button::down);
} else {
fold.set_dir(arrow_button::right);
}
} else if (&b == &bzero) {
zero ();
clicked (fold);
} else if (&b == &breset) {
reset (keepsize.state);
clicked (fold);
}
}