kkana's blog

新米コーダーの忘れそうなことメモ

nature of code:今日の練習「木(L-systemを使って)」

See the Pen tree(L-system) by kanaparty (@kanaparty) on CodePen.

L-systemを使って、藻みたいな描写をする課題。
L-system - Wikipedia

フラクタル構造を管理するメカニズム。必要な要素は3つあって、

  • アルファベット
  • 公理(初期状態)
  • 規則

作ったL-systemのところはこんな感じ

//L-system
class Lsystem {
  constructor(axiom, rule) {
      this.rule = rule;
      this.sentence = axiom;
      this.generation = 0;
    }
    //次の世代の文字列を作る
  generate() {
    var nextgen = "";
    for (var i = 0; i < this.sentence.length; i++) {
      var crr = this.sentence.charAt(i);
      for (var j = 0; j < this.rule.length; j++) {
        var a = this.rule[j].getA();
        if (a === crr) {
          nextgen += this.rule[j].getB();
        } else {
          nextgen += crr;
        }
      }
    }
    this.generation++;
    this.sentence = nextgen;
  }
  getSentence() {
    return this.sentence;
  }
  getGeneration() {
    return this.generation;
  }
}

//ルール
class Rule {
  constructor(chr, sentence) {
    this.a = chr;
    this.b = sentence;
  }
  getA() {
    return this.a;
  }
  getB() {
    return this.b;
  }
}

書いていくときにはタートルグラフィックという描画フレームワークを使うのが一般的。
F G + - [ ]などは亀(ポインタ)にだす直進、回転、などの指示のこと。
今回書いたのでいうとここのぶぶん

//描写
class Turtle {
  constructor(todo, length, theta) {
    this.sentence = todo;
    this.length = length;
    this.angle = theta;
  }
  draw() {
      for (var i = 0; i < this.sentence.length; i++) {
        var chr = this.sentence.charAt(i);
        switch (chr) {
          case 'F':
            ctx.beginPath();
            ctx.moveTo(0, 0);
            ctx.lineTo(0, -this.length);
            ctx.stroke();
            ctx.closePath();
            ctx.translate(0, -this.length);
            break;
          case '+':
            ctx.rotate(this.angle);
            break;
          case '-':
            ctx.rotate(-this.angle);
            break;
          case '[':
            ctx.save();
            break;
          case ']':
            ctx.restore();
            break;
          default:
        }
      }
    }
    //長さを変更
  changeLength(ratio) {
      this.length *= ratio;
    }
    //新しい文字列を取得
  updateSentense(axiom) {
    this.sentence = axiom;
  }
}

初めて知ったLOGO言語  

LOGO - Wikipedia www.wizforest.com

ポインタを亀にみたたて動かすっていうのが面白いなぁと思ったら もともと教育のための言語なんですね。 LOGO開発者 シーモア・パパート

オブジェクト指向がタートル・グラフィックスに起源を持つことはよく知られている」 らしい。そうなんだ!

そしてこの連載がかなり面白い。また読む。

早過ぎた孤独な予言者 − @IT自分戦略研究所