使用 Decentraland 的 ECS 延迟操作

Delaying actions using Decentraland's ECS

如何使操作延迟发生,但在超时后发生?

setTimeout()功能在Decentraland场景下不可用,请问有没有替代方案?

例如,我希望某个实体在单击后等待 300 毫秒,然后再将其从引擎中删除。

要实现这一点,您必须创建:

  • 用于跟踪时间的自定义组件
  • 一个组件组,用于跟踪场景中具有延迟的所有实体
  • 更新定时器的系统包含所有这些 每帧上的组件。

听起来很复杂,但是一旦你创建了一个延迟,实现另一个延迟只需要一行。

组件:

@Component("timerDelay")
export class Delay implements ITimerComponent{
    elapsedTime: number;
    targetTime: number;
    onTargetTimeReached: (ownerEntity: IEntity) => void;
    private onTimeReachedCallback?: ()=> void

    /**
     * @param millisecs amount of time in milliseconds
     * @param onTimeReachedCallback callback for when time is reached
     */
    constructor(millisecs: number, onTimeReachedCallback?: ()=> void){
        this.elapsedTime = 0
        this.targetTime = millisecs / 1000
        this.onTimeReachedCallback = onTimeReachedCallback
        this.onTargetTimeReached = (entity)=>{
            if (this.onTimeReachedCallback) this.onTimeReachedCallback()
            entity.removeComponent(this)
        }
    }
}

组件组:

export const delayedEntities = engine.getComponentGroup(Delay)

系统:

// define system

class TimerSystem implements ISystem {   

        update(dt: number){
            for (let entity of delayedEntities.entities) {
                let timerComponent = entity.getComponent(component)
                timerComponent.elapsedTime += dt
                if (timerComponent.elapsedTime >= timerComponent.targetTime){
                    timerComponent.onTargetTimeReached(entity)
                }
            })
        }    
    }

// instance system
engine.addSystem(new TimerSystem())

所有这些部分就绪后,您只需执行以下操作即可延迟场景中的执行:

const myEntity = new Entity()

myEntity.addComponent(new Delay(1000, () => {
    log("time ran out")
}))

engine.addEntity(myEntity)

使用 utils 库中的 utils.Delay() 函数。 这个函数只是把延迟时间以毫秒为单位,和你要执行的函数。

这里是完整的文档,解释了如何添加库+如何使用这个函数,包括示例代码:

https://www.npmjs.com/package/decentraland-ecs-utils