【问题标题】:Typescript conditional inheritance打字稿条件继承
【发布时间】:2021-04-26 05:37:47
【问题描述】:

目标是创建一个可以扩展不同类的原型。 我需要创建一个扩展 Mesh 或 Points of THREE.js 的类。对于这两种情况,我创建的子类都是相同的。不能是接口。

class PointsElement extends THREE.Points {
  public name: string
  protected width: number
  protected height: number

  constructor (protected target: THREE.Scene | THREE.Group, protected properties: IElementProperties) {
    super()
    this.name = this.properties.name
    AutoBind(this)
  }

  public async preload () {
  }

  public async show () {
    this.target.add(this)
  }

  public async hide () {
    this.target.remove(this)
  }
}

class MeshElement extends THREE.Mesh {
  public name: string
  protected width: number
  protected height: number

  constructor (protected target: THREE.Scene | THREE.Group, protected properties: IElementProperties) {
    super()
    this.name = this.properties.name
    AutoBind(this)
  }

  public async preload () {
  }

  public async show () {
    this.target.add(this)
  }

  public async hide () {
    this.target.remove(this)
  }
}

我想要做的是通过排除“元素”来减少代码,因为 MeshElement 和 PointsElement 中的主体是相同的,但是这些类中的每一个都扩展了不同的类

【问题讨论】:

  • 条件继承被普遍称为工厂模式
  • 如果我必须返回带有附加参数的新网格或点,工厂模式会很有帮助。我需要创建具有元素属性和网格或点的类。像 'class MeshElement extends THREE.Mesh { ...Element.prototype }' 和 'class PoinstElement extends THREE.Points { ...Element.prototype }'。

标签: javascript typescript three.js


【解决方案1】:

它有点快速和肮脏,但希望你明白我所说的工厂模式是什么意思。

你所描述的只是一种做工厂的方法,而不是唯一的。

enum Geometrics {
  Mesh = "Mesh",
  Points = "Points"
}

class Element {
  public isElement = true;
}

class Mesh extends Element {
  public type = Geometrics.Mesh;
}

class Point extends Element {
  public type = Geometrics.Points;
}

class GeometricsFactory<T extends Geometrics> {
  private shapesMap = new Map<Geometrics, typeof Mesh | typeof Point>([
    [Geometrics.Mesh, class Shape extends Mesh {}],
    [Geometrics.Points, class Shape extends Point {}]
  ]);

  constructor(private type: Geometrics) {}

  public getShape(): T extends Geometrics.Mesh ? typeof Mesh : typeof Point {
    const shape = this.shapesMap.get(this.type);
    if (shape) {
      return <T extends Geometrics.Mesh ? typeof Mesh : typeof Point>shape;
    }
    throw new Error(`Invalid shape type ${this.type}`);
  }
}

const MyMesh = new (new GeometricsFactory<Geometrics.Mesh>(Geometrics.Mesh).getShape())();
console.log(MyMesh.type);

const MyPoints = new (new GeometricsFactory<Geometrics.Points>(Geometrics.Points).getShape())();
console.log(MyPoints.type);

【讨论】:

  • THREE.Mesh 类已经带有 its own properties and methodsTHREE.Points 也是如此。这些会被上述方法继承吗?
  • 在这种情况下,我可以获得扩展网格或点的形状类,但我无法预定义“形状”到底是什么。就我而言,我必须创建 Shape 类,然后决定要扩展哪个类。我将编辑问题以使其更易于理解。
  • 早点添加更多类。形状只是最后的回报
  • @AliHabibzadeh 我真的不明白你的意思......你能把我的例子变成工厂吗?
猜你喜欢
  • 2017-12-04
  • 2017-07-14
  • 1970-01-01
  • 2017-04-10
  • 1970-01-01
  • 1970-01-01
  • 2020-05-07
  • 2017-09-11
  • 1970-01-01
相关资源
最近更新 更多