Bu muhtemelen çok basit bir şeydir, ama güldüm. Bu, çok daha büyük bir şeyin bir parçası olduğundan, kod yalnızca bir parçacıktır. Particle
etrafında düzenlenmiş yeşil dairelerin her biri Gate
'dur. Fare, Particle
etrafında hareket ettiğinde, en yakın Gate
, artık özgür olmadığını göstermek için kırmızıya dönmelidir. En yakın Gate
, Gate
'un PVector heading
'u, cosin kuralı kullanılarak PVector(mouseX,mouseY)
karşı karşılaştırılarak bulunur.Kosinüs kuralı ile PVektörler nasıl karşılaştırılır?
Particle p;
void setup()
{
size(1000, 1000);
p = new Particle(25);
p.setLoc(width/2, height/2);
}
void draw()
{
background(0);
p.update();
PVector mouse = new PVector(mouseX, mouseY);
p.gm.getGate(mouse).notFree();
p.display();
}
class Particle {
GateManager gm;
PVector loc;
float size;
float n_size;
float r;//radius;
float topspeed;
boolean clicked;
color MAIN = color(200, 200, 0);
color HIGHLIGHT = color(255, 0, 0);
color COLOUR = color(200, 200, 0);
String name;
Particle(int size_) {
loc = new PVector(0,0);
this.n_size = size_;
this.size = n_size*30000;
r = sqrt(size/PI);
topspeed = 2000/size;
gm = new GateManager(this);
}
void setLoc(float x, float y) {
loc.set(x, y);
}
void display()
{
gm.display();
}
Gate getGate(PVector pv)
{
PVector pv_ = PVector.sub(pv, loc);
return gm.getGate(pv_);
}
void update() {
gm.update();
}
}///Particle
class Gate {
float size = 5;
PVector loc;
PVector locP;
float angle;
boolean free;
//Edge edge;
PVector heading; ///which way is it pointing?
GateManager parent;
float x, y;
color COLOUR;
color FREE = color(0, 255, 0);
color NOTFREE = color(255, 0, 0);
Gate(GateManager gm, float angle_) {
this.parent = gm;
this.angle = angle_;
this.x = parent.parent.r * .5 * cos(angle);
this.y = parent.parent.r * .5 * sin(angle);
locP = new PVector(x, y);
loc = new PVector(x, y);
free = true;
}
boolean isFree() {
return free;
}
void notFree()
{
free = false;
COLOUR = NOTFREE;
}
void free()
{
COLOUR = FREE;
free = true;
}
void update()
{
free();
heading = PVector.sub(loc, parent.parent.loc);
heading.normalize();
loc.set(parent.parent.loc.x +locP.x, parent.parent.loc.y+locP.y);
}
void display()
{
noStroke();
fill(COLOUR);
ellipse(loc.x, loc.y, size, size);
}
}
class GateManager {
ArrayList<Gate> gates;
int capacity;
Particle parent;
float angle;
GateManager(Particle p)
{
capacity = int(p.n_size*8);
this.parent = p;
gates = new ArrayList<Gate>();
angle = TWO_PI/capacity;
for (int i = 0; i<capacity; i++)
{
gates.add(new Gate(this, angle*i));
}
}
Gate getGate(PVector pv)
{
float tolerance = -1;
int i_val=-1;
boolean found = false;
for (int i = 0; i<capacity; i++)
{
if (gates.get(i).isFree()) {
float temp = cosineSimilarity(pv, gates.get(i).heading);
if ((temp>tolerance))
{
tolerance = temp;
i_val = i;
found = true;
}
}
}
i_val = constrain(i_val, 0, capacity);
text(i_val, 100, height-100);
return gates.get(i_val);
}
void free()
{
for (Gate g : gates)
{
g.free();
}
}
void update() {
for (Gate g : gates)
{
g.update();
}
}
void display() {
for (Gate g : gates)
{
g.display();
}
}
}//GateManager
float cosineSimilarity(PVector vA, PVector vB) {
float dotProduct = 0.0;
float normA = 0.0;
float normB = 0.0;
dotProduct += vA.x * vB.x;
dotProduct += vA.y * vB.y;
normA += Math.pow(vA.x, 2);
normA += Math.pow(vA.y, 2);
normB += Math.pow(vB.x, 2);
normB += Math.pow(vB.y, 2);
return dotProduct/(sqrt(normA) * sqrt(normB));
}