Matrix2D(p5.js)


部分ごと

データとコンストラクタ


class Matrix2D {
  constructor(m00, m01, m10, m11) {
    this.M00 = m00;
    this.M01 = m01;
    this.M10 = m10;
    this.M11 = m11;
  }

  static makeFromRow(row1, row2) {
    return new Matrix2D(row1.x, row1.y, row2.x, row2.y);
  }

  static makeFromColumn(col1, col2) {
    return new Matrix2D(col1.x, col2.x, col1.y, col2.y);
  }

  getElement(i, j) {
    if (i == 0 && j == 0) { return this.M00; }
    if (i == 0 && j == 1) { return this.M01; }

    if (i == 1 && j == 0) { return this.M10; }
    if (i == 1 && j == 1) { return this.M11; }

    throw new Error("Index out of range");
  }

  rowVector(i) {
    if (i == 0) { return createVector(this.M00, this.M01); }
    if (i == 1) { return createVector(this.M10, this.M11); }

    throw new Error("Index out of range");
  }

  columnVector(j) {
    if (j == 0) { return createVector(this.M00, this.M10); }
    if (j == 1) { return createVector(this.M01, this.M11); }

    throw new Error("Index out of range");
  }
}

基本操作

class Matrix2D {
  // 既存のコンストラクタとメソッドは省略します…

  static get Unit() {
    return new Matrix2D(1, 0, 0, 1);
  }

  get Transpose() {
    return new Matrix2D(this.M00, this.M10, this.M01, this.M11);
  }

  get Determinant() {
    return this.M00 * this.M11 - this.M01 * this.M10;
  }

  get CofactorMatrix() {
    return new Matrix2D(this.M11, -this.M10, -this.M01, this.M00);
  }

  get AdjugateMatrix() {
    return this.CofactorMatrix.Transpose;
  }

  get Inverse() {
    let det = this.Determinant;
    if (det == 0) {
      throw new Error("This matrix cannot be inverted because its determinant is zero.");
    } else {
      let adj = this.AdjugateMatrix;
      return new Matrix2D(adj.M00 / det, adj.M01 / det, adj.M10 / det, adj.M11 / det);
    }
  }

  get Homogeneous() {
    return new Matrix3D(this.M00, this.M01, 0, this.M10, this.M11, 0, 0, 0, 1);
  }
}

基本演算


現状行列の積は
右からしか受けてないし
ベクトルも受けてない

class Matrix2D {
  // 既存のコンストラクタとメソッドは省略します…

  add(m2) {
    return new Matrix2D(
      this.M00 + m2.M00,
      this.M01 + m2.M01,
      this.M10 + m2.M10,
      this.M11 + m2.M11
    );
  }

  subtract(m2) {
    return new Matrix2D(
      this.M00 - m2.M00,
      this.M01 - m2.M01,
      this.M10 - m2.M10,
      this.M11 - m2.M11
    );
  }

  multiply(f) {
    if (f instanceof Matrix2D) {
      let m2 = f;
      return new Matrix2D(
        this.M00 * m2.M00 + this.M01 * m2.M10,
        this.M00 * m2.M01 + this.M01 * m2.M11,
        this.M10 * m2.M00 + this.M11 * m2.M10,
        this.M10 * m2.M01 + this.M11 * m2.M11
      );
    } else {
      return new Matrix2D(
        this.M00 * f, this.M01 * f,
        this.M10 * f, this.M11 * f
      );
    }
  }

  divide(f) {
    return new Matrix2D(
      this.M00 / f, this.M01 / f,
      this.M10 / f, this.M11 / f
    );
  }

  equals(m2) {
    return this.M00 === m2.M00 && this.M01 === m2.M01 && this.M10 === m2.M10 && this.M11 === m2.M11;
  }
}

// Usage example
let m1 = new Matrix2D(1, 2, 3, 4);
let m2 = new Matrix2D(5, 6, 7, 8);
let m3 = m1.add(m2);

アフィン変換

class Matrix2D {
  // ...既存のコンストラクタとメソッドを省略...

  static scale(scaleX, scaleY) {
    return new Matrix2D(
      scaleX, 0,
      0, scaleY
    );
  }

  static rotate(radians) {
    let cos = Math.cos(radians);
    let sin = Math.sin(radians);
    return new Matrix2D(
      cos, -sin,
      sin, cos
    );
  }

  static reflectX() {
    return new Matrix2D(
      1, 0,
      0, -1
    );
  }

  static reflectY() {
    return new Matrix2D(
      -1, 0,
      0, 1
    );
  }

  static skew(sx, sy) {
    return new Matrix2D(
      1, sx,
      sy, 1
    );
  }
}

// Usage example
let scaleX = 2;
let scaleY = 3;
let scaleMatrix = Matrix2D.scale(scaleX, scaleY);

全部(コピペ用)

class Matrix2D {
  constructor(m00, m01, m10, m11) {
    this.M00 = m00;
    this.M01 = m01;
    this.M10 = m10;
    this.M11 = m11;
  }

  static makeFromRow(row1, row2) {
    return new Matrix2D(row1.x, row1.y, row2.x, row2.y);
  }

  static makeFromColumn(col1, col2) {
    return new Matrix2D(col1.x, col2.x, col1.y, col2.y);
  }

  getElement(i, j) {
    if (i == 0 && j == 0) { return this.M00; }
    if (i == 0 && j == 1) { return this.M01; }

    if (i == 1 && j == 0) { return this.M10; }
    if (i == 1 && j == 1) { return this.M11; }

    throw new Error("Index out of range");
  }

  rowVector(i) {
    if (i == 0) { return createVector(this.M00, this.M01); }
    if (i == 1) { return createVector(this.M10, this.M11); }

    throw new Error("Index out of range");
  }

  columnVector(j) {
    if (j == 0) { return createVector(this.M00, this.M10); }
    if (j == 1) { return createVector(this.M01, this.M11); }

    throw new Error("Index out of range");
  }
  
  static get Unit() {
    return new Matrix2D(1, 0, 0, 1);
  }

  get Transpose() {
    return new Matrix2D(this.M00, this.M10, this.M01, this.M11);
  }

  get Determinant() {
    return this.M00 * this.M11 - this.M01 * this.M10;
  }

  get CofactorMatrix() {
    return new Matrix2D(this.M11, -this.M10, -this.M01, this.M00);
  }

  get AdjugateMatrix() {
    return this.CofactorMatrix.Transpose;
  }

  get Inverse() {
    let det = this.Determinant;
    if (det == 0) {
      throw new Error("This matrix cannot be inverted because its determinant is zero.");
    } else {
      let adj = this.AdjugateMatrix;
      return new Matrix2D(adj.M00 / det, adj.M01 / det, adj.M10 / det, adj.M11 / det);
    }
  }

  get Homogeneous() {
    return new Matrix3D(this.M00, this.M01, 0, this.M10, this.M11, 0, 0, 0, 1);
  } 
  
  add(m2) {
    return new Matrix2D(
      this.M00 + m2.M00,
      this.M01 + m2.M01,
      this.M10 + m2.M10,
      this.M11 + m2.M11
    );
  }

  subtract(m2) {
    return new Matrix2D(
      this.M00 - m2.M00,
      this.M01 - m2.M01,
      this.M10 - m2.M10,
      this.M11 - m2.M11
    );
  }

  multiply(f) {
    if (f instanceof Matrix2D) {
      let m2 = f;
      return new Matrix2D(
        this.M00 * m2.M00 + this.M01 * m2.M10,
        this.M00 * m2.M01 + this.M01 * m2.M11,
        this.M10 * m2.M00 + this.M11 * m2.M10,
        this.M10 * m2.M01 + this.M11 * m2.M11
      );
    } else {
      return new Matrix2D(
        this.M00 * f, this.M01 * f,
        this.M10 * f, this.M11 * f
      );
    }
  }

  divide(f) {
    return new Matrix2D(
      this.M00 / f, this.M01 / f,
      this.M10 / f, this.M11 / f
    );
  }

  equals(m2) {
    return this.M00 === m2.M00 && this.M01 === m2.M01 && this.M10 === m2.M10 && this.M11 === m2.M11;
  }
  
  static scale(scaleX, scaleY) {
    return new Matrix2D(
      scaleX, 0,
      0, scaleY
    );
  }

  static rotate(radians) {
    let cos = Math.cos(radians);
    let sin = Math.sin(radians);
    return new Matrix2D(
      cos, -sin,
      sin, cos
    );
  }

  static reflectX() {
    return new Matrix2D(
      1, 0,
      0, -1
    );
  }

  static reflectY() {
    return new Matrix2D(
      -1, 0,
      0, 1
    );
  }

  static skew(sx, sy) {
    return new Matrix2D(
      1, sx,
      sy, 1
    );
  }  
  
}

この記事が気に入ったらサポートをしてみませんか?