-
Notifications
You must be signed in to change notification settings - Fork 0
/
scene.ts
131 lines (112 loc) · 4.26 KB
/
scene.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
namespace affine {
const INPUT_PRIORITY = 10;
const UPDATE_PRIORITY = 20;
const DRAW_PRIORITY = 30;
const GPU_PRIORITY = 90;
const SCREEN_PRIORITY = 100;
export class Scene {
public static SCENE_OFFSET = Screen.SCREEN_HALF_SIZE;
private static mgr_: SceneManager;
private xfrm_: Transform;
private color_: number;
public get xfrm() { return this.xfrm_; }
public get color() { return this.color_; }
public set color(v) { this.color_ = v; }
private static _staticInit = (() => Scene.mgr_ = new SceneManager())();
constructor() {
this.xfrm_ = new Transform();
this.color_ = 12;
}
/* virtual */ update(dt: number) {
}
/* virtual */ draw() {
}
/* virtual */ startup() {
// Called when the scene is pushed to the scene manaager.
// ** Will be called at most one time during the scene's lifetime. **
}
/* virtual */ shutdown() {
// Called when the scene is popped from the scene manager.
// ** Will be called at most one time during the scene's lifetime. **
}
/* virtual */ activate() {
// Called when the scene becomes the current scene, either by
// being pushed or the previously current scene popped.
// ** Can be called multiple times during the scene's lifetime. **
}
/* virtual */ deactivate() {
// Called when the scene is no longer the active scene, either
// by being popped or a new scene pushed.
// ** Can be called multiple times during the scene's lifetime. **
}
__init() {
// Hook into the runtime for frame callbacks.
control.eventContext().registerFrameHandler(INPUT_PRIORITY, () => {
controller.__update(control.eventContext().deltaTime);
});
control.eventContext().registerFrameHandler(UPDATE_PRIORITY, () => {
this.update(control.eventContext().deltaTime);
});
control.eventContext().registerFrameHandler(DRAW_PRIORITY, () => {
this.draw();
});
control.eventContext().registerFrameHandler(GPU_PRIORITY, () => {
screen.fill(this.color_);
Gpu.exec();
});
control.eventContext().registerFrameHandler(SCREEN_PRIORITY, () => {
control.__screen.update();
});
}
// SceneManager API
public static currScene(add = false): Scene { return Scene.mgr_.currScene(add); }
public static replaceScene(scene: Scene): Scene { return Scene.mgr_.replaceScene(scene); }
public static pushScene(scene: Scene): Scene { return Scene.mgr_.pushScene(scene); }
public static popScene(): Scene { return Scene.mgr_.popScene(); }
}
class SceneManager {
private scenes: Scene[];
constructor() {
this.scenes = [];
}
public currScene(add = false): Scene {
if (this.scenes.length) {
return this.scenes[this.scenes.length - 1];
} else if (add) {
return this.pushScene(new Scene());
}
return undefined;
}
public replaceScene(scene: Scene): Scene {
if (this.scenes.length) {
this.popScene();
}
return this.pushScene(scene);
}
public pushScene(scene: Scene): Scene {
const currScene = this.currScene();
if (currScene) {
currScene.deactivate();
}
control.pushEventContext();
this.scenes.push(scene);
scene.__init();
scene.startup();
scene.activate();
return scene;
}
public popScene(): Scene {
const prevScene = this.scenes.pop();
if (prevScene) {
prevScene.deactivate();
prevScene.shutdown();
control.popEventContext();
}
const currScene = this.currScene();
if (currScene) {
currScene.activate();
}
return currScene;
}
}
}