Counterbalance

I started with 4 squares in the center of the frame and at the corners to suggest visually the diagonals. Then, as in the down-right corner, I increased five times the size of the squares to reach the middle points of the diagonals. The rest is playing around with the orientations to break the repetitive pattern. I stopped when the result looked visually balanced and aesthetically pleasing to me.

Log in to post a comment.

Canvas.setpenopacity(1);

// Création de tortues positionnées centralement
const createTurtlesAt = (count, x = 0, y = 0, dx = 0, dy = 0) => {
    const turtles = [];
    for (let i = 0; i < count; i++) {
        const t = new Turtle();
        t.penup();
        t.goto(x + i * dx, y + i * dy);
        t.pendown();
        turtles.push(t);
    }
    return turtles;
};

// 4 Tortues centrales
const centerTurtles = createTurtlesAt(4, 0, 0);

// Création de tortues positionnées aux coins et comme des clones
const createClonesAt = (sourceTurtle, positions) => {
    return positions.map(([x, y]) => {
        const clone = sourceTurtle.clone();
        clone.penup();
        clone.goto(x, y);
        clone.pendown();
        return clone;
    });
};
const cornerPositions = [
    [100, 100],
    [100, -100],
    [-100, 100],
    [-100, -100],
];
// 4 Tortues aux coins
const [rightDown, rightUp, leftDown, leftUp] = createClonesAt(centerTurtles[0], cornerPositions);

// 5 Tortues intermédiaires en bas à droite
const diagonalTurtlesRD = createTurtlesAt(5, 50, 50, 10, 10);
const [rightMidDown1, rightMidDown2, rightMidDown3, rightMidDown4, rightMidDown5] = diagonalTurtlesRD;
// 5 Tortues intermédiaires en haut à droite
const diagonalTurtlesRU = createTurtlesAt(5, 50, -50, 10, 10);
const [rightMidUp1, rightMidUp2, rightMidUp3, rightMidUp4, rightMidUp5] = diagonalTurtlesRU;
// 5 Tortues intermédiaires en bas à gauche
const diagonalTurtlesLD = createTurtlesAt(5, -50, 50, 10, 10);
const [leftMidDown1, leftMidDown2, leftMidDown3, leftMidDown4, leftMidDown5] = diagonalTurtlesLD;
// 5 Tortues intermédiaires en haut à gauche
const diagonalTurtlesLU = createTurtlesAt(5, -50, -50, 10, 10);
const [leftMidUp1, leftMidUp2, leftMidUp3, leftMidUp4, leftMidUp5] = diagonalTurtlesLU;


// Fonction appelée à chaque frame
function walk(i) {
    //Deux façons de tracer
    const moveAndTurn = (turtle, distance, orientation) => {
        turtle.forward(distance);
        turtle.left(orientation);
    };
    const moveAndTurnBack = (turtle, distance, orientation) => {
        turtle.backward(distance);
        turtle.left(orientation);
    };

    // Tortues centrales et coins
    moveAndTurn(centerTurtles[0], 10, 90);
    moveAndTurn(leftDown, 10, 90);
    
    [leftMidDown1, leftMidDown2, leftMidDown3, leftMidDown4, leftMidDown5].forEach((t, idx) => {
        moveAndTurn(t, 50 + idx * 10, 90);
    });
    

    moveAndTurn(centerTurtles[1], 10, -90);
    moveAndTurn(leftUp, 10, -90);
    
    [rightMidDown1, rightMidDown2, rightMidDown3, rightMidDown4, rightMidDown5].forEach((t, idx) => {
        moveAndTurn(t, 50 + idx * 10, -90);
    });
    

    moveAndTurnBack(centerTurtles[2], 10, -90);
    moveAndTurnBack(rightDown, 10, -90);

    [rightMidUp1, rightMidUp2, rightMidUp3, rightMidUp4, rightMidUp5].forEach((t, idx) => {
        moveAndTurn(t, -50 + idx * 10, 90);
    });

    moveAndTurnBack(centerTurtles[3], 10, 90);
    moveAndTurnBack(rightUp, 10, 90);
    
    [leftMidUp1, leftMidUp2, leftMidUp3, leftMidUp4, leftMidUp5].forEach((t, idx) => {
        moveAndTurn(t, -50 - idx * 10, -90);
    });

    return i < 4;
}