how to trace a relatively defined point?

If you run the code below, you will see a red dot moving around circles. I want to trace the red point so that the trace creates some kind of curve. I tried to define a global variable "result" and save all positions of red points. However, as the red points are defined relatively (in terms of the center of the parent circle), I got undesired result... Can you help with this code? Thanks in advance.

var circles = [];
var pen;
// var result = [];


function setup() {
    createCanvas(640, 640);

    circles[0] = {
        c: createVector(0, 0),
        r: 150,
        t: 0.01
    };

    for (var i = 0; i < 1; i++) {
        circles.push(new Circle(circles[i].c, circles[i].r, circles[i].t));
    };
    pen = new Pen(circles[circles.length - 1].c, circles[circles.length - 1].r, circles[circles.length - 1].t);
}

function draw() {
    background(255);
    translate(width / 2, height / 2);

    stroke(0);
    noFill();
    ellipse(circles[0].c.x, circles[0].c.y, 2 * circles[0].r);


    for (var i = 1; i < circles.length; i++) {
        circles[i].update();
        circles[i].show();
    };
    pen.update();
    pen.show();

//  stroke(255, 0, 0);
//  noFill();
//  beginShape();
//  for (var j = 0; j < result.length; j += 2) {
//      vertex(result[j], result[j + 1]);
//  };
//  endShape();
}

function Circle(c, r, t) {
    this.r = r / 3;
    this.c = createVector(r + this.r, c.y);
    this.t = -2 * t;

    this.show = function() {
        translate(c.x, c.y);
        stroke(0);
        noFill();
        ellipse(this.c.x, this.c.y, 2 * this.r);
    };

    this.update = function() {
        this.c.rotate(this.t);
    };
}

function Pen(c, r, t) {
    this.c = createVector(r, c.y);
    this.t = 4 * t;

    this.show = function() {
        noStroke();
        fill(255, 0, 0);
        translate(c.x, c.y);
        ellipse(this.c.x, this.c.y, 5);
    };

    this.update = function() {
//      result.push(this.c.x);
//      result.push(this.c.y);
        this.c.rotate(this.t);
    };
}

Answers

  • edited July 2017

    @jjycjn Check this code. This could be improved by using a vector....

    @GoToLoop I tried to implement an idea on line 80 and I couldn't get it to work. Can you give me hints why it was so?

    Kf

    var circles = [];
    var pen;
    var resultx1 = [];
    var resulty1 = [];
    var resultx2 = [];
    var resulty2 = [];
    
    
    function setup() {
        createCanvas(640, 640);
    
        circles[0] = {
            c: createVector(0, 0),
            r: 150,
            t: 0.01
        };
    
        for (var i = 0; i < 1; i++) {
            circles.push(new Circle(circles[i].c, circles[i].r, circles[i].t));
        };
        pen = new Pen(circles[circles.length - 1].c, circles[circles.length - 1].r, circles[circles.length - 1].t);
    }
    
    function draw() {
        background(255);
    
        translate(width / 2, height / 2);
        push();
        stroke(0);
        noFill();
        ellipse(circles[0].c.x, circles[0].c.y, 2 * circles[0].r);
    
    
        for (var i = 1; i < circles.length; i++) {
            circles[i].update();
            circles[i].show();
        };
        //pen.update();
        pen.show();
        pen.showPtList();
    
        pop();
    
        fill(0,0,250);
        for(var pp=0;pp<resultx1.length;pp++){            
            ellipse(resultx1[pp]+resultx2[pp], resulty1[pp]+resulty2[pp], 5);          
        }
    
    //  stroke(255, 0, 0);
    //  noFill();
    //  beginShape();
    //  for (var j = 0; j < result.length; j += 2) {
    //      vertex(result[j], result[j + 1]);
    //  };
    //  endShape();
    }
    
    function Circle(c, r, t) {
        this.r = r / 3;
        this.c = createVector(r + this.r, c.y);
        this.t = -2 * t;
    
        this.show = function() {
            translate(c.x, c.y);
            stroke(0);
            noFill();
            ellipse(this.c.x, this.c.y, 2 * this.r);
        };
    
        this.update = function() {
            resultx1.push(this.c.x);
            resulty1.push(this.c.y);
            this.c.rotate(this.t);
        };
    }
    
    function Pen(c, r, t) {
        this.c = createVector(r, c.y);
        this.t = 4 * t;
        //this.ptListx=[];
    
        this.show = function() {
            noStroke();
            fill(255, 0, 0);
            this.update();
            translate(c.x, c.y);
            ellipse(this.c.x, this.c.y, 5);
            //this.ptListx.push(this.c.x);
        };
    
        this.showPtList=function(){
            fill(0, 0, 255);
            //for(var pp=0;pp<this.ptListx.length;pp++){            
            //  ellipse(this.ptList[pp], this.ptList[pp], 5);          
            //}
        }
    
        this.update = function() {
          resultx2.push(this.c.x);
          resulty2.push(this.c.y);
          this.c.rotate(this.t);
        };
    }
    

    Kf

  • Don't you just need to add the coords of the centre point to the relative point when storing them? This should make them absolute.

    (I haven't run the code)

  • Look at modelX maybe and use its values to store?

  • @kfrajer Thank you so much for your improvement. Your code works perfectly for two circles, but doesn't work quite well for more than two circles.. Anyway, I will try to implement the code from yours. Thanks again!

    @koogs Can you explain it in detail, please? Let me rephrase my question. I have a vector, say (100, 100), then I translate(100, 100) and again translate(50, 100). Then the vector will be drawn at (250, 200). Now, Is there a way to store the vector (or points) (250, 200) without knowing all information about previous transformations?

    @Chrisir What is modelX? Sorry, I just started learning p5.js since two weeks ago and don't have any other coding background... (I know matlab and LaTeX, if I can count them as a computer language). I found model(); code in p5.js reference. Does it what you mean?

  • If you get stuck, ask away.

    Kf

  • Sorry, modelX gives you the absolute position after using translate etc. in processing- I don't know whether we have ot in p5

  • no screenX / Y in p5.js

    that point is just the centre of the circle plus the distance from the centre of the circle, just add them together.

    c.x + this.c.x, c.y + this.c.y
    

    you don't help yourself by the choice of variable names tbh.

    if you have more circles, as you suggest, then show your code. each circle will need to know its parent and you'll need to iterate through them to find the absolute position.

  • When you have more than two circles, how do they interact with each other? I mean, if you have one master circle at the center and the other circles moving around this master circle, then the implementation will need to be adjusted. However, if the circles are circling in a nested pattern, the implementation will require a different approach. The concept here, as mentioned by @koogs, is to accumulate the circle's position at different stages when they are drawn, taking into account the parent's position. It is indeed a simple addition problem as Processing(P5.js) is taking care of all the translations and rotations for you.

    Kf

Sign In or Register to comment.