对ECS系统进行注释、移除JobSystem
This commit is contained in:
@@ -1,51 +1,35 @@
|
||||
///<reference path="./EntitySystem.ts"/>
|
||||
module es {
|
||||
/**
|
||||
* 追踪每个实体的冷却时间,当实体的计时器耗尽时进行处理
|
||||
*
|
||||
* 一个示例系统将是ExpirationSystem,该系统将在特定生存期后删除实体。
|
||||
* 你不必运行会为每个实体递减timeLeft值的系统
|
||||
* 而只需使用此系统在寿命最短的实体时在将来执行
|
||||
* 然后重置系统在未来的某一个最短命实体的时间运行
|
||||
*
|
||||
* 另一个例子是一个动画系统
|
||||
* 你知道什么时候你必须对某个实体进行动画制作,比如300毫秒内。
|
||||
* 所以你可以设置系统以300毫秒为单位运行来执行动画
|
||||
*
|
||||
* 这将在某些情况下节省CPU周期
|
||||
* 这个类是一个实体系统的基类,其可以被子类继承并在子类中实现具体的实体处理逻辑。
|
||||
* 该类提供了实体的添加、删除、更新等基本操作,并支持设置系统的更新时序、检查系统是否需要处理实体、获取系统的场景等方法
|
||||
*/
|
||||
export abstract class DelayedIteratingSystem extends EntitySystem {
|
||||
/**
|
||||
* 一个实体应被处理的时间
|
||||
*/
|
||||
private delay: number = 0;
|
||||
/**
|
||||
* 如果系统正在运行,并倒计时延迟
|
||||
*/
|
||||
private running: boolean = false;
|
||||
/**
|
||||
* 倒计时
|
||||
*/
|
||||
private acc: number = 0;
|
||||
private delay = 0;
|
||||
private running = false;
|
||||
private acc = 0;
|
||||
|
||||
constructor(matcher: Matcher) {
|
||||
super(matcher);
|
||||
}
|
||||
|
||||
protected process(entities: Entity[]) {
|
||||
let processed = entities.length;
|
||||
if (processed == 0) {
|
||||
const processed = entities.length;
|
||||
|
||||
if (processed === 0) {
|
||||
this.stop();
|
||||
return;
|
||||
}
|
||||
|
||||
this.delay = Number.MAX_VALUE;
|
||||
for (let i = 0; processed > i; i++) {
|
||||
let e = entities[i];
|
||||
this.processDelta(e, this.acc);
|
||||
let remaining = this.getRemainingDelay(e);
|
||||
|
||||
for (let i = 0; i < processed; i++) {
|
||||
const entity = entities[i];
|
||||
this.processDelta(entity, this.acc);
|
||||
const remaining = this.getRemainingDelay(entity);
|
||||
|
||||
if (remaining <= 0) {
|
||||
this.processExpired(e);
|
||||
this.processExpired(entity);
|
||||
} else {
|
||||
this.offerDelay(remaining);
|
||||
}
|
||||
@@ -59,6 +43,7 @@ module es {
|
||||
this.acc += Time.deltaTime;
|
||||
return this.acc >= this.delay;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -67,7 +52,7 @@ module es {
|
||||
* 如果系统已经停止(不运行),那么提供的延迟将被用来重新启动系统,无论其值如何
|
||||
* 如果系统已经在倒计时,并且提供的延迟大于剩余时间,系统将忽略它。
|
||||
* 如果提供的延迟时间短于剩余时间,系统将重新启动,以提供的延迟时间运行。
|
||||
* @param offeredDelay
|
||||
* @param offeredDelay 提供的延迟时间,单位为秒
|
||||
*/
|
||||
public offerDelay(offeredDelay: number) {
|
||||
if (!this.running) {
|
||||
@@ -78,22 +63,6 @@ module es {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 处理本系统感兴趣的实体
|
||||
* 从实体定义的延迟中抽象出accumulativeDelta
|
||||
* @param entity
|
||||
* @param accumulatedDelta 本系统最后一次执行后的delta时间
|
||||
*/
|
||||
protected abstract processDelta(entity: Entity, accumulatedDelta: number);
|
||||
|
||||
protected abstract processExpired(entity: Entity);
|
||||
|
||||
/**
|
||||
* 返回该实体处理前的延迟时间
|
||||
* @param entity
|
||||
*/
|
||||
protected abstract getRemainingDelay(entity: Entity): number;
|
||||
|
||||
/**
|
||||
* 获取系统被命令处理实体后的初始延迟
|
||||
*/
|
||||
@@ -102,9 +71,9 @@ module es {
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取系统计划运行前的时间
|
||||
* 如果系统没有运行,则返回零
|
||||
*/
|
||||
* 获取系统计划运行前的时间
|
||||
* 如果系统没有运行,则返回零
|
||||
*/
|
||||
public getRemainingTimeUntilProcessing(): number {
|
||||
if (this.running) {
|
||||
return this.delay - this.acc;
|
||||
@@ -127,5 +96,25 @@ module es {
|
||||
this.running = false;
|
||||
this.acc = 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* 处理给定实体的延迟时间的一部分,抽象出累积的 Delta 值。
|
||||
* @param entity 要处理的实体
|
||||
* @param accumulatedDelta 本系统最后一次执行后的累积 delta 时间
|
||||
*/
|
||||
protected abstract processDelta(entity: Entity, accumulatedDelta: number);
|
||||
|
||||
/**
|
||||
* 处理已到期的实体。
|
||||
* @param entity 要处理的实体
|
||||
*/
|
||||
protected abstract processExpired(entity: Entity);
|
||||
|
||||
/**
|
||||
* 获取给定实体剩余的延迟时间。
|
||||
* @param entity 要检查的实体
|
||||
* @returns 剩余的延迟时间(以秒为单位)
|
||||
*/
|
||||
protected abstract getRemainingDelay(entity: Entity): number;
|
||||
}
|
||||
}
|
||||
@@ -1,53 +1,76 @@
|
||||
///<reference path="./EntitySystem.ts" />
|
||||
module es {
|
||||
/**
|
||||
* 基本实体处理系统。将其用作处理具有特定组件的许多实体的基础
|
||||
*
|
||||
* 按实体引用遍历实体订阅成员实体的系统
|
||||
* 当你需要处理与Matcher相匹配的实体,并且你更喜欢使用Entity的时候,可以使用这个功能。
|
||||
* 定义一个处理实体的抽象类,继承自 EntitySystem 类。
|
||||
* 子类需要实现 processEntity 方法,用于实现具体的实体处理逻辑。
|
||||
*/
|
||||
export abstract class EntityProcessingSystem extends EntitySystem {
|
||||
/**
|
||||
* 是否启用系统,默认为启用。
|
||||
*/
|
||||
public enabled: boolean = true;
|
||||
|
||||
/**
|
||||
* 构造函数,初始化实体匹配器。
|
||||
* @param matcher 实体匹配器
|
||||
*/
|
||||
constructor(matcher: Matcher) {
|
||||
super(matcher);
|
||||
}
|
||||
|
||||
/**
|
||||
* 处理单个实体,由子类实现。
|
||||
* @param entity 待处理的实体
|
||||
*/
|
||||
public abstract processEntity(entity: Entity): void;
|
||||
|
||||
/**
|
||||
* 处理特定的实体
|
||||
* @param entity
|
||||
* 在晚于 update 的时间更新实体,由子类实现。
|
||||
* @param entity 待处理的实体
|
||||
*/
|
||||
public abstract processEntity(entity: Entity);
|
||||
|
||||
public lateProcessEntity(entity: Entity) {
|
||||
|
||||
public lateProcessEntity(entity: Entity): void {
|
||||
// do nothing
|
||||
}
|
||||
|
||||
/**
|
||||
* 遍历这个系统的所有实体并逐个处理它们
|
||||
* @param entities
|
||||
* 遍历系统的所有实体,逐个进行实体处理。
|
||||
* @param entities 实体数组
|
||||
*/
|
||||
protected process(entities: Entity[]) {
|
||||
if (entities.length == 0)
|
||||
// 如果实体数组为空,则直接返回
|
||||
if (entities.length === 0) {
|
||||
return;
|
||||
|
||||
for (let i = 0, s = entities.length; i < s; ++ i) {
|
||||
let entity = entities[i];
|
||||
}
|
||||
|
||||
// 遍历实体数组,逐个进行实体处理
|
||||
for (let i = 0, len = entities.length; i < len; i++) {
|
||||
const entity = entities[i];
|
||||
this.processEntity(entity);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 在晚于 update 的时间更新实体。
|
||||
* @param entities 实体数组
|
||||
*/
|
||||
protected lateProcess(entities: Entity[]) {
|
||||
if (entities.length == 0)
|
||||
// 如果实体数组为空,则直接返回
|
||||
if (entities.length === 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (let i = 0, s = entities.length; i < s; ++ i) {
|
||||
let entity = entities[i];
|
||||
// 遍历实体数组,逐个进行实体处理
|
||||
for (let i = 0, len = entities.length; i < len; i++) {
|
||||
const entity = entities[i];
|
||||
this.lateProcessEntity(entity);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断系统是否需要进行实体处理。
|
||||
* 如果启用了系统,则需要进行实体处理,返回 true;
|
||||
* 否则不需要进行实体处理,返回 false。
|
||||
*/
|
||||
protected checkProcessing(): boolean {
|
||||
return this.enabled;
|
||||
}
|
||||
|
||||
@@ -1,40 +1,63 @@
|
||||
module es {
|
||||
/**
|
||||
* 实体系统以一定的时间间隔进行处理
|
||||
* 定义一个按时间间隔处理的抽象类,继承自 EntitySystem 类。
|
||||
* 子类需要实现 process 方法,用于实现具体的处理逻辑。
|
||||
*/
|
||||
export abstract class IntervalSystem extends EntitySystem {
|
||||
/**
|
||||
* 累积增量以跟踪间隔
|
||||
*/
|
||||
protected acc: number = 0;
|
||||
private acc: number = 0;
|
||||
|
||||
/**
|
||||
* 更新之间需要等待多长时间
|
||||
*/
|
||||
private readonly interval: number = 0;
|
||||
private intervalDelta: number = 0;
|
||||
private readonly interval: number;
|
||||
|
||||
/**
|
||||
* 时间间隔的余数,用于计算下一次需要等待的时间
|
||||
*/
|
||||
private intervalRemainder: number = 0;
|
||||
|
||||
/**
|
||||
* 构造函数,初始化时间间隔。
|
||||
* @param matcher 实体匹配器
|
||||
* @param interval 时间间隔
|
||||
*/
|
||||
constructor(matcher: Matcher, interval: number) {
|
||||
super(matcher);
|
||||
this.interval = interval;
|
||||
}
|
||||
|
||||
protected checkProcessing() {
|
||||
/**
|
||||
* 判断是否需要进行处理。
|
||||
* 如果需要进行处理,则更新累积增量和时间间隔余数,返回 true;
|
||||
* 否则返回 false。
|
||||
*/
|
||||
protected checkProcessing(): boolean {
|
||||
// 更新累积增量
|
||||
this.acc += Time.deltaTime;
|
||||
if (this.acc >= this.interval) {
|
||||
this.acc -= this.interval;
|
||||
this.intervalDelta = (this.acc - this.intervalDelta);
|
||||
|
||||
// 如果累积增量超过时间间隔,则进行处理
|
||||
if (this.acc >= this.interval) {
|
||||
// 更新时间间隔余数
|
||||
this.intervalRemainder = this.acc - this.interval;
|
||||
// 重置累积增量
|
||||
this.acc = 0;
|
||||
// 返回 true,表示需要进行处理
|
||||
return true;
|
||||
}
|
||||
|
||||
// 返回 false,表示不需要进行处理
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取本系统上次处理后的实际delta值
|
||||
* 获取本系统上次处理后的实际 delta 值。
|
||||
* 实际 delta 值等于时间间隔加上时间间隔余数。
|
||||
*/
|
||||
protected getIntervalDelta() {
|
||||
return this.interval + this.intervalDelta;
|
||||
protected getIntervalDelta(): number {
|
||||
return this.interval + this.intervalRemainder;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,102 +0,0 @@
|
||||
module es {
|
||||
/**
|
||||
* JobSystem使用实体的子集调用Execute(entities),并在指定数量的线程上分配工作负载。
|
||||
*/
|
||||
export abstract class JobSystem extends EntitySystem {
|
||||
public readonly _threads: number;
|
||||
public readonly _jobs: Job[];
|
||||
public readonly _executeStr: string;
|
||||
|
||||
constructor(matcher: Matcher, threads: number) {
|
||||
super(matcher);
|
||||
|
||||
this._threads = threads;
|
||||
this._jobs = new Array(threads);
|
||||
for (let i = 0; i < this._jobs.length; i++) {
|
||||
this._jobs[i] = new Job();
|
||||
}
|
||||
this._executeStr = JSON.stringify(this.execute, function (key, val) {
|
||||
if (typeof val === 'function') {
|
||||
return val + '';
|
||||
}
|
||||
return val;
|
||||
});
|
||||
}
|
||||
|
||||
protected process(entities: Entity[]) {
|
||||
let remainder = entities.length & this._threads;
|
||||
let slice = entities.length / this._threads + (remainder == 0 ? 0 : 1);
|
||||
for (let t = 0; t < this._threads; t++) {
|
||||
let from = t * slice;
|
||||
let to = from + slice;
|
||||
if (to > entities.length) {
|
||||
to = entities.length;
|
||||
}
|
||||
|
||||
let job = this._jobs[t];
|
||||
job.set(entities, from, to, this._executeStr, this);
|
||||
if (from != to) {
|
||||
const worker = WorkerUtils.makeWorker(this.queueOnThread);
|
||||
const workerDo = WorkerUtils.workerMessage(worker);
|
||||
workerDo(job).then((message) => {
|
||||
let job = message as Job;
|
||||
this.resetJob(job);
|
||||
worker.terminate();
|
||||
}).catch((err) => {
|
||||
job.err = err;
|
||||
worker.terminate();
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private queueOnThread() {
|
||||
onmessage = ({ data: { jobId, message } }) => {
|
||||
let job = message[0] as Job;
|
||||
let executeFunc: Function = JSON.parse(job.execute, function (k, v) {
|
||||
if (v.indexOf && v.indexOf('function') > -1) {
|
||||
return eval("(function(){return " + v + " })()")
|
||||
}
|
||||
|
||||
return v;
|
||||
});
|
||||
for (let i = job.from; i < job.to; i++) {
|
||||
executeFunc.call(job.context, job.entities[i]);
|
||||
}
|
||||
|
||||
postMessage({ jobId, result: message }, null);
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* 当操作完成时,改变的值需要用户进行手动传递
|
||||
* 由于worker数据无法共享,所以这块需要特殊处理
|
||||
* @example this.test = job[0].context.test;
|
||||
* @param job
|
||||
*/
|
||||
protected abstract resetJob(job: Job);
|
||||
/**
|
||||
* 对指定实体进行多线程操作
|
||||
* @param entity
|
||||
*/
|
||||
protected abstract execute(entity: Entity);
|
||||
}
|
||||
|
||||
class Job {
|
||||
public entities: Entity[];
|
||||
public from: number;
|
||||
public to: number;
|
||||
public worker: Worker;
|
||||
public execute: string;
|
||||
public err: string;
|
||||
public context;
|
||||
|
||||
public set(entities: Entity[], from: number, to: number, execute: string, context: any) {
|
||||
this.entities = entities;
|
||||
this.from = from;
|
||||
this.to = to;
|
||||
this.execute = execute;
|
||||
this.context = context;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,11 +1,21 @@
|
||||
module es {
|
||||
/**
|
||||
* 定义一个被动的实体系统,继承自 EntitySystem 类。
|
||||
* 被动的实体系统不会对实体进行任何修改,只会被动地接收实体的变化事件。
|
||||
*/
|
||||
export abstract class PassiveSystem extends EntitySystem {
|
||||
public onChanged(entity: Entity) {
|
||||
|
||||
}
|
||||
/**
|
||||
* 当实体发生变化时,不进行任何操作。
|
||||
* @param entity 发生变化的实体
|
||||
*/
|
||||
public onChanged(entity: Entity) { }
|
||||
|
||||
/**
|
||||
* 不进行任何处理,只进行开始和结束计时。
|
||||
* @param entities 实体数组,未被使用
|
||||
*/
|
||||
protected process(entities: Entity[]) {
|
||||
// 我们用我们自己的不考虑实体的基本实体系统来代替
|
||||
// 调用 begin 和 end 方法,开始和结束计时
|
||||
this.begin();
|
||||
this.end();
|
||||
}
|
||||
|
||||
@@ -1,17 +1,30 @@
|
||||
/** 用于协调其他系统的通用系统基类 */
|
||||
module es {
|
||||
/**
|
||||
* 定义一个处理实体的抽象类,继承自 EntitySystem 类。
|
||||
* 子类需要实现 processSystem 方法,用于实现具体的处理逻辑。
|
||||
*/
|
||||
export abstract class ProcessingSystem extends EntitySystem {
|
||||
public onChanged(entity: Entity) {
|
||||
|
||||
}
|
||||
|
||||
/** 处理我们的系统 每帧调用 */
|
||||
public abstract processSystem();
|
||||
/**
|
||||
* 当实体发生变化时,不进行任何操作。
|
||||
* @param entity 发生变化的实体
|
||||
*/
|
||||
public onChanged(entity: Entity) { }
|
||||
|
||||
/**
|
||||
* 处理实体,每帧调用 processSystem 方法进行处理。
|
||||
* @param entities 实体数组,未被使用
|
||||
*/
|
||||
protected process(entities: Entity[]) {
|
||||
// 调用 begin 和 end 方法,开始和结束计时
|
||||
this.begin();
|
||||
// 调用子类实现的 processSystem 方法进行实体处理
|
||||
this.processSystem();
|
||||
this.end();
|
||||
}
|
||||
|
||||
/**
|
||||
* 处理实体的具体方法,由子类实现。
|
||||
*/
|
||||
public abstract processSystem(): void;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,39 +1,51 @@
|
||||
module es {
|
||||
interface IdentityHashMap {
|
||||
[key: string]: ComponentType;
|
||||
}
|
||||
|
||||
/**
|
||||
* 组件类型工厂,用于生成和管理组件类型。
|
||||
* 维护了一个类型映射表,将组件类型与其唯一索引相对应,以便在运行时高效地检查实体是否包含特定的组件类型。
|
||||
*/
|
||||
export class ComponentTypeFactory {
|
||||
private componentTypes_: IdentityHashMap;
|
||||
/** 组件类型与其唯一索引的映射表 */
|
||||
private componentTypes: Record<string, ComponentType> = {};
|
||||
/** 组件类型列表,按索引访问组件类型 */
|
||||
public readonly types: Bag<ComponentType> = new Bag<ComponentType>();
|
||||
/** 当前组件类型的计数器 */
|
||||
private componentTypeCount = 0;
|
||||
|
||||
private componentTypeCount_ = 0;
|
||||
|
||||
public types: Bag<ComponentType>;
|
||||
|
||||
constructor() {
|
||||
this.componentTypes_ = {};
|
||||
this.types = new Bag<ComponentType>();
|
||||
/**
|
||||
* 获取给定组件类型的唯一索引。
|
||||
* 如果该组件类型尚未存在于类型映射表中,则创建一个新的组件类型,并将其添加到映射表和类型列表中。
|
||||
* @param c 要查找或创建的组件类型
|
||||
* @returns 组件类型的唯一索引
|
||||
*/
|
||||
public getIndexFor(c: new (...args: any[]) => any): number {
|
||||
return this.getTypeFor(c).getIndex();
|
||||
}
|
||||
|
||||
public getTypeFor(c): ComponentType {
|
||||
if ("number" === typeof c) {
|
||||
/**
|
||||
* 获取给定组件类型的ComponentType对象。
|
||||
* 如果该组件类型尚未存在于类型映射表中,则创建一个新的ComponentType对象,并将其添加到映射表和类型列表中。
|
||||
* @param c 要查找或创建的组件类型
|
||||
* @returns 组件类型的ComponentType对象
|
||||
*/
|
||||
public getTypeFor(c: new (...args: any[]) => any): ComponentType {
|
||||
// 如果给定的组件类型是一个已有的索引,则直接返回对应的ComponentType对象
|
||||
if (typeof c === "number") {
|
||||
return this.types.get(c);
|
||||
}
|
||||
|
||||
let type: ComponentType = this.componentTypes_[getClassName(c)];
|
||||
// 获取给定组件类型对应的类名
|
||||
const className = getClassName(c);
|
||||
|
||||
if (type == null) {
|
||||
const index: number = this.componentTypeCount_++;
|
||||
type = new ComponentType(c, index);
|
||||
this.componentTypes_[getClassName(c)] = type;
|
||||
// 如果类型映射表中不存在该组件类型,则创建一个新的ComponentType对象
|
||||
if (!this.componentTypes[className]) {
|
||||
const index = this.componentTypeCount++;
|
||||
const type = new ComponentType(c, index);
|
||||
this.componentTypes[className] = type;
|
||||
this.types.set(index, type);
|
||||
}
|
||||
|
||||
return type;
|
||||
}
|
||||
|
||||
public getIndexFor(c): number {
|
||||
return this.getTypeFor(c).getIndex();
|
||||
// 返回对应的ComponentType对象
|
||||
return this.componentTypes[className];
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,12 +1,28 @@
|
||||
module es {
|
||||
/**
|
||||
* 组件类型管理器,维护了一个组件类型和它们对应的位掩码之间的映射关系。
|
||||
* 用于实现实体匹配器中组件类型的比较操作,以确定实体是否符合给定的匹配器条件。
|
||||
*/
|
||||
export class ComponentTypeManager {
|
||||
/** 存储组件类型和它们对应的位掩码的Map */
|
||||
private static _componentTypesMask: Map<any, number> = new Map<any, number>();
|
||||
|
||||
/**
|
||||
* 将给定的组件类型添加到组件类型列表中,并分配一个唯一的位掩码。
|
||||
* @param type 要添加的组件类型
|
||||
*/
|
||||
public static add(type) {
|
||||
if (!this._componentTypesMask.has(type))
|
||||
if (!this._componentTypesMask.has(type)) {
|
||||
this._componentTypesMask.set(type, this._componentTypesMask.size);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取给定组件类型的位掩码。
|
||||
* 如果该组件类型还没有分配位掩码,则将其添加到列表中,并分配一个唯一的位掩码。
|
||||
* @param type 要获取位掩码的组件类型
|
||||
* @returns 组件类型的位掩码
|
||||
*/
|
||||
public static getIndexFor(type) {
|
||||
let v = -1;
|
||||
if (!this._componentTypesMask.has(type)) {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
module es {
|
||||
/**
|
||||
* 定义一个实体匹配器类。
|
||||
*/
|
||||
export class Matcher {
|
||||
protected allSet: (new (...args: any[]) => Component)[] = [];
|
||||
protected exclusionSet: (new (...args: any[]) => Component)[] = [];
|
||||
@@ -25,59 +28,61 @@ module es {
|
||||
}
|
||||
|
||||
public isInterested(components: Bits) {
|
||||
if (this.allSet.length != 0) {
|
||||
for (let i = 0, s = this.allSet.length; i < s; ++ i) {
|
||||
let type = this.allSet[i];
|
||||
if (!components.get(ComponentTypeManager.getIndexFor(type)))
|
||||
if (this.allSet.length !== 0) {
|
||||
for (let i = 0; i < this.allSet.length; i++) {
|
||||
const type = this.allSet[i];
|
||||
if (!components.get(ComponentTypeManager.getIndexFor(type))) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (this.exclusionSet.length != 0) {
|
||||
for (let i = 0, s = this.exclusionSet.length; i < s; ++ i) {
|
||||
let type = this.exclusionSet[i];
|
||||
if (components.get(ComponentTypeManager.getIndexFor(type)))
|
||||
if (this.exclusionSet.length !== 0) {
|
||||
for (let i = 0; i < this.exclusionSet.length; i++) {
|
||||
const type = this.exclusionSet[i];
|
||||
if (components.get(ComponentTypeManager.getIndexFor(type))) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (this.oneSet.length != 0) {
|
||||
for (let i = 0, s = this.oneSet.length; i < s; ++ i) {
|
||||
let type = this.oneSet[i];
|
||||
if (components.get(ComponentTypeManager.getIndexFor(type)))
|
||||
if (this.oneSet.length !== 0) {
|
||||
for (let i = 0; i < this.oneSet.length; i++) {
|
||||
const type = this.oneSet[i];
|
||||
if (components.get(ComponentTypeManager.getIndexFor(type))) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public all(...types: any[]): Matcher {
|
||||
let t;
|
||||
for (let i = 0, s = types.length; i < s; ++ i) {
|
||||
t = types[i];
|
||||
this.allSet.push(t);
|
||||
}
|
||||
|
||||
/**
|
||||
* 添加所有包含的组件类型。
|
||||
* @param types 所有包含的组件类型列表
|
||||
*/
|
||||
public all(...types: (new (...args: any[]) => Component)[]): Matcher {
|
||||
this.allSet.push(...types);
|
||||
return this;
|
||||
}
|
||||
|
||||
public exclude(...types: any[]) {
|
||||
let t;
|
||||
for (let i = 0, s = types.length; i < s; ++ i) {
|
||||
t = types[i];
|
||||
this.exclusionSet.push(t);
|
||||
}
|
||||
|
||||
/**
|
||||
* 添加排除包含的组件类型。
|
||||
* @param types 排除包含的组件类型列表
|
||||
*/
|
||||
public exclude(...types: (new (...args: any[]) => Component)[]): Matcher {
|
||||
this.exclusionSet.push(...types);
|
||||
return this;
|
||||
}
|
||||
|
||||
public one(...types: any[]) {
|
||||
for (let i = 0, s = types.length; i < s; ++ i) {
|
||||
const t = types[i];
|
||||
this.oneSet.push(t);
|
||||
}
|
||||
|
||||
/**
|
||||
* 添加至少包含其中之一的组件类型。
|
||||
* @param types 至少包含其中之一的组件类型列表
|
||||
*/
|
||||
public one(...types: (new (...args: any[]) => Component)[]): Matcher {
|
||||
this.oneSet.push(...types);
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,38 +0,0 @@
|
||||
module es {
|
||||
/**
|
||||
* 开辟一个新线程
|
||||
* 注意:它无法获得主线程中的上下文
|
||||
*/
|
||||
export class WorkerUtils {
|
||||
/** 正在执行的队列 */
|
||||
private static readonly pendingJobs = {};
|
||||
private static jobIdGen = 0;
|
||||
|
||||
/**
|
||||
* 创建一个worker
|
||||
* @param doFunc worker所能做的事情
|
||||
*/
|
||||
public static makeWorker(doFunc: Function) {
|
||||
const worker = new Worker(URL.createObjectURL(new Blob([`(${doFunc.toString()})()`])));
|
||||
|
||||
return worker;
|
||||
}
|
||||
|
||||
public static workerMessage(worker: Worker) {
|
||||
worker.onmessage = ({ data: { result, jobId } }) => {
|
||||
if (typeof this.pendingJobs[jobId] == 'function')
|
||||
this.pendingJobs[jobId](result);
|
||||
|
||||
delete this.pendingJobs[jobId];
|
||||
};
|
||||
|
||||
return (...message: any[]) => {
|
||||
return new Promise(resolve => {
|
||||
const jobId = this.jobIdGen++;
|
||||
this.pendingJobs[jobId] = resolve;
|
||||
worker.postMessage({ jobId, message });
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user