Skip to content

Commit

Permalink
尝试增加用于检查事件options的类型代码
Browse files Browse the repository at this point in the history
  • Loading branch information
Silvigarabis committed Aug 16, 2023
1 parent 8cb7920 commit 86c8836
Show file tree
Hide file tree
Showing 7 changed files with 85 additions and 9 deletions.
8 changes: 7 additions & 1 deletion src/example.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
// 实际上类似于这样,并且还要求文件的位置位于 scripts/ 目录下。
//import { Scoreboard, Objective, YoniUtils, YoniScheduler, YoniPlayer, world } from "yoni/index.js";
import { Scoreboard, Objective, YoniUtils, YoniScheduler, YoniPlayer, world } from "yoni-mcscripts-lib";
import { EventHandler, Minecraft, Scoreboard, Objective, YoniUtils, YoniScheduler, YoniPlayer, world } from "yoni-mcscripts-lib";

// 简单示范了 Scoreboard 的用法,这个类是对原版的记分板
// 访问 API 的重新封装,并添加了一些没有的方法。
Expand Down Expand Up @@ -41,3 +41,9 @@ YoniScheduler.runDelayTickTask(function doSome(){
}, 1200);
//延迟一分钟再执行(1*60*20=1200)

class MainClass{

@EventHandler({event: Minecraft.EntityHealthChangedAfterEvent, options: {}})
onEvent(event: Minecraft.EntityHealthChangedAfterEvent){
}
}
2 changes: 2 additions & 0 deletions src/yoni/event.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,5 @@ export { EventListener } from "./event/v2/decorators/EventListener.js";

export { EventSignalListeningAdapter } from "./event/v2/adapter/EventSignalListeningAdapter.js";

export { EventOptionType, EventOptionDefinitions } from "./event/v2/GetEventOptions"

3 changes: 2 additions & 1 deletion src/yoni/event/v2/EventRegistry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { manager } from "./EventManager.js";
import { defaultOptionResolver } from "./lib/defaultOptionResolver.js";
import { EventPriority, EventPriorityIds } from "./EventPriority.js";
import { getExtendedClassesInList } from "./lib/getExtendedClassesInList.js";
import { EventOptionType } from "./GetEventOptions";

export class EventRegistry<TEvent extends Function> {
#displayName?: string | undefined;
Expand Down Expand Up @@ -145,6 +146,6 @@ export interface EventRegisterOptions<TEvent extends Function> {
displayName?: string
}

export type ExtraOptionResolver<TEvent extends Function> = <TP extends {}>(event: TEvent["prototype"], option: TP) => boolean
export type ExtraOptionResolver<TEvent extends Function> = (event: TEvent["prototype"], option: EventOptionType<TEvent["prototype"]>) => boolean

type Prototype<TFunction extends Function> = TFunction["prototype"];
35 changes: 30 additions & 5 deletions src/yoni/event/v2/GetEventOptions.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,33 @@
/*declare module "yoni-mcscripts-lib" {
interface EventOptions extends InnerEventOptions {
}
import Minecraft from "../../minecraft.js";
import { Equals, UnionToTuple, DumpTupleRecordEntriesToUnion } from "../../lib/types";

export interface EventOptionDefinitions extends MinecraftEventsOptions, InnerEventsOptions {
}

interface MinecraftEventsOptions {
"Minecraft.EntityRemovedAfterEvent": [Minecraft.EntityRemovedAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EntityHurtAfterEvent": [Minecraft.EntityHurtAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EntityHitEntityAfterEvent": [Minecraft.EntityHitEntityAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EntityHitBlockAfterEvent": [Minecraft.EntityHitBlockAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EntityHealthChangedAfterEvent": [Minecraft.EntityHealthChangedAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EntityDieAfterEvent": [Minecraft.EntityDieAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.EffectAddAfterEvent": [Minecraft.EffectAddAfterEvent, Minecraft.EntityEventOptions]
"Minecraft.DataDrivenEntityTriggerAfterEvent": [Minecraft.DataDrivenEntityTriggerAfterEvent, Minecraft.EntityDataDrivenTriggerEventOptions]
"Minecraft.DataDrivenEntityTriggerBeforeEvent": [Minecraft.DataDrivenEntityTriggerBeforeEvent, Minecraft.EntityDataDrivenTriggerEventOptions]
}

interface InnerEventOptions {
interface InnerEventsOptions {
}
*/

type AllEventOptionsEntries = UnionToTuple<DumpTupleRecordEntriesToUnion<EventOptionDefinitions>>;

type _GetEventOptionsOfEvent<Event, EventOptionsEntries> =
EventOptionsEntries extends [infer FirstSelection, ...infer LessSelections]
? FirstSelection extends [infer SelectedEvent, infer SelectedOptions]
? Equals<SelectedEvent, Event> extends true
? SelectedOptions
: _GetEventOptionsOfEvent<Event, LessSelections>
: _GetEventOptionsOfEvent<Event, LessSelections>
: any

export type EventOptionType<Event> = _GetEventOptionsOfEvent<Event, AllEventOptionsEntries>;
6 changes: 4 additions & 2 deletions src/yoni/event/v2/decorators/EventHandler.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
import { sEventListenerData } from "./EventListener.js";
import { EventPriority } from "../EventPriority.js";
import IEventListener from "../interfaces/EventListener";
import { EventOptionType } from "../GetEventOptions";

interface EventHandlerOptions<TEvent> {
interface EventHandlerOptions<TEvent extends Function> {
event: TEvent,
priority?: EventPriority
ignoreCancelled?: boolean
options?: any,
options?: EventOptionType<TEvent["prototype"]>,
}

export function EventHandler<
Expand Down Expand Up @@ -49,3 +50,4 @@ type TypedObjectMethod<
> = {
[k in K]: (...args: P) => R
}

36 changes: 36 additions & 0 deletions src/yoni/lib/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
//根据 https://github.com/type-challenges/type-challenges/issues/9814 改写
export type DumpTupleRecordEntriesToUnion<T> = {
[id in keyof T]-?: T[id] extends [infer Event, infer EventOpt] ? T[id] : never
}[keyof T]

//来源:https://segmentfault.com/q/1010000042243980
//展开只是想知道这个东西干了什么
type UnionToIntersection<U> =
(U extends any
? (a: (k: U) => void) => void
: never
) extends (a: infer I) => void
? I
: never;

type UnionLast<U> =
UnionToIntersection<U> extends (a: infer I) => void
? I
: never;

export type UnionToTuple<U> =
[U] extends [never]
? []
: [...UnionToTuple<
Exclude<
U,
UnionLast<U>
>
>,
UnionLast<U>
];

//来源:https://github.com/microsoft/TypeScript/issues/27024#issuecomment-421529650
export type Equals<X, Y> =
(<T>() => T extends X ? 1 : 2) extends
(<T>() => T extends Y ? 1 : 2) ? true : false;
4 changes: 4 additions & 0 deletions src/yoni/scoreboard/ScoreboardEntry.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ import { UnknownEntryError } from "./ScoreboardError.js";

/**
* 代表一个可以在记分板上持有分数的分数持有者。
*
* 对于运行时的实体与玩家,这个对象是唯一的。
*
* 对于虚拟玩家,不能保证对应的对象的唯一性。
*/
export class ScoreboardEntry {
static #entityMap = new WeakMap<Minecraft.Entity, ScoreboardEntry>;
Expand Down

0 comments on commit 86c8836

Please sign in to comment.