@leafer-ui/app 1.0.0-alpha.2 → 1.0.0-alpha.23

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,11 +1,13 @@
1
1
  {
2
2
  "name": "@leafer-ui/app",
3
- "version": "1.0.0-alpha.2",
3
+ "version": "1.0.0-alpha.23",
4
4
  "description": "@leafer-ui/app",
5
5
  "author": "Chao (Leafer) Wan",
6
6
  "license": "MIT",
7
7
  "main": "src/index.ts",
8
- "files": ["src"],
8
+ "files": [
9
+ "src"
10
+ ],
9
11
  "repository": {
10
12
  "type": "git",
11
13
  "url": "https://github.com/leaferjs/ui.git"
@@ -13,16 +15,15 @@
13
15
  "homepage": "https://github.com/leaferjs/ui/tree/main/packages/app",
14
16
  "bugs": "https://github.com/leaferjs/ui/issues",
15
17
  "keywords": [
16
- "leaferui",
17
18
  "leafer-ui",
18
19
  "leaferjs"
19
20
  ],
20
21
  "dependencies": {
21
- "@leafer/core": "1.0.0-alpha.1",
22
- "@leafer-ui/display": "1.0.0-alpha.2"
22
+ "@leafer/core": "1.0.0-alpha.23",
23
+ "@leafer-ui/display": "1.0.0-alpha.23"
23
24
  },
24
25
  "devDependencies": {
25
- "@leafer/interface": "1.0.0-alpha.1",
26
- "@leafer-ui/interface": "1.0.0-alpha.1"
26
+ "@leafer/interface": "1.0.0-alpha.23",
27
+ "@leafer-ui/interface": "1.0.0-alpha.23"
27
28
  }
28
29
  }
package/src/App.ts ADDED
@@ -0,0 +1,109 @@
1
+ import { ILeaferConfig, IResizeEvent, ILeaferCanvas, IRenderOptions, IApp, __Value } from '@leafer/interface'
2
+ import { DataHelper, LayoutEvent, RenderEvent, defineLeafAttr } from '@leafer/core'
3
+
4
+ import { Leafer } from './Leafer'
5
+
6
+
7
+ export class App extends Leafer implements IApp {
8
+
9
+ public get isApp(): boolean { return true }
10
+
11
+ public view: unknown
12
+
13
+ public virtualCanvas: boolean
14
+
15
+ public children: Leafer[] = []
16
+
17
+ @hitType(true)
18
+ public hittable: boolean
19
+
20
+ protected __setApp(): void {
21
+ if (this.config.view === this.canvas.view) {
22
+ this.virtualCanvas = true
23
+ } else {
24
+ this.canvas.unloadView()
25
+ this.view = this.canvas.parentView
26
+ }
27
+ }
28
+
29
+ public start(): void {
30
+ if (!this.running) {
31
+ this.children.forEach(leafer => { leafer.start() })
32
+ this.renderer.start()
33
+ this.running = true
34
+ }
35
+ }
36
+
37
+ public stop(): void {
38
+ if (this.running) {
39
+ this.children.forEach(leafer => { leafer.stop() })
40
+ this.renderer.stop()
41
+ this.running = false
42
+ }
43
+ }
44
+
45
+ public addLeafer(merge?: ILeaferConfig): Leafer {
46
+ const leafer = new Leafer(merge)
47
+ this.add(leafer)
48
+ return leafer
49
+ }
50
+
51
+ public add(leafer: Leafer): void {
52
+ if (!leafer.view) leafer.init(this.__getChildConfig(leafer.userConfig), this)
53
+ super.add(leafer)
54
+
55
+ if (this.virtualCanvas) {
56
+ const { renderer } = this
57
+ this.__eventIds.push(
58
+ leafer.on__(LayoutEvent.END, this.__onChildLayoutEnd, this),
59
+ leafer.on__(RenderEvent.END, renderer.update, renderer),
60
+ this.on__(LayoutEvent.REQUEST, renderer.mergeBlocks, renderer)
61
+ )
62
+ }
63
+ }
64
+
65
+ protected __onChildLayoutEnd(event: LayoutEvent): void {
66
+ const { renderer } = this
67
+ if ((event.current as Leafer).config.usePartRender) {
68
+ event.data.map(item => renderer.addBlock(item.updatedBounds))
69
+ } else {
70
+ renderer.addBlock(renderer.canvas.bounds)
71
+ }
72
+ }
73
+
74
+ public __render(canvas: ILeaferCanvas, _options: IRenderOptions): void {
75
+ this.children.forEach(leafer => { canvas.copyWorld(leafer.canvas) })
76
+ }
77
+
78
+ public __onResize(event: IResizeEvent): void {
79
+ this.emitEvent(event)
80
+ this.children.forEach(leafer => { leafer.resize(event) })
81
+ }
82
+
83
+ protected __getChildConfig(userConfig?: ILeaferConfig): ILeaferConfig {
84
+ let old = { ...this.config }
85
+ userConfig = userConfig ? DataHelper.default(userConfig, old) : old
86
+ userConfig.view = this.virtualCanvas ? null : this.canvas.parentView
87
+ userConfig.virtualCanvas = null
88
+ if (this.autoLayout) {
89
+ userConfig.width = this.width
90
+ userConfig.height = this.height
91
+ userConfig.pixelRatio = this.pixelRatio
92
+ }
93
+ return userConfig
94
+ }
95
+
96
+ }
97
+
98
+ export function hitType(defaultValue?: __Value) {
99
+ return (target: IApp, key: string) => {
100
+ defineLeafAttr(target, key, defaultValue, {
101
+ set(value: __Value) {
102
+ this.__setAttr(key, value)
103
+ this.children.forEach(item => {
104
+ item.hittable = value as boolean
105
+ })
106
+ }
107
+ })
108
+ }
109
+ }
package/src/Leafer.ts CHANGED
@@ -1,21 +1,23 @@
1
- import { ILayouter, ILeafer, ILeaferCanvas, IRenderer, ICreator, ISelector, IWatcher, IInteraction, ILeaferConfig, ICanvasManager, IHitCanvasManager, IImageManager, IAutoBounds, IScreenSizeData, IResizeEvent, IObject, ILeaf, IEventListenerId, ITransformEventData } from '@leafer/interface'
2
- import { registerUI, AutoBounds, LayoutEvent, ResizeEvent, MoveEvent, ZoomEvent, CanvasManager, HitCanvasManager, ImageManager, DataHelper, LeafHelper, Creator } from '@leafer/core'
1
+ import { IApp, ILeafer, ILeaferCanvas, IRenderer, ILayouter, ICreator, ISelector, IWatcher, IInteraction, ILeaferConfig, ICanvasManager, IHitCanvasManager, IImageManager, IAutoBounds, IScreenSizeData, IResizeEvent, IObject, ILeaf, IEventListenerId, ITransformEventData, ILeaferType, IBounds } from '@leafer/interface'
2
+ import { AutoBounds, LayoutEvent, ResizeEvent, MoveEvent, ZoomEvent, LeaferEvent, CanvasManager, HitCanvasManager, ImageManager, DataHelper, LeafHelper, Creator, Run, RenderEvent } from '@leafer/core'
3
3
 
4
4
  import { Group } from '@leafer-ui/display'
5
5
 
6
- import { SuperLeafer } from './SuperLeafer'
6
+ import { App } from './App'
7
7
 
8
8
 
9
- @registerUI()
10
9
  export class Leafer extends Group implements ILeafer {
11
10
 
12
11
  public creator: ICreator
13
12
 
14
- public get isSupperLeafer(): boolean { return false }
13
+ public get isApp(): boolean { return false }
15
14
 
16
- public parent?: SuperLeafer
15
+ public parent?: App
17
16
 
18
17
  public running: boolean
18
+ public ready: boolean
19
+
20
+ public startTimer: number
19
21
 
20
22
  @resizeType()
21
23
  public width: number
@@ -26,17 +28,20 @@ export class Leafer extends Group implements ILeafer {
26
28
  @resizeType()
27
29
  public pixelRatio: number
28
30
 
31
+ public get bounds(): IBounds { return this.canvas.bounds }
32
+
33
+ public userConfig: ILeaferConfig
29
34
  public config: ILeaferConfig = {
30
- zoom: true,
31
- move: true,
35
+ type: 'design',
32
36
  start: true,
33
- pixelRatio: devicePixelRatio
37
+ hittable: true
34
38
  }
35
39
 
36
40
  public autoLayout?: IAutoBounds
37
41
 
38
- // manager
42
+ public view: unknown
39
43
 
44
+ // manager
40
45
  public canvas: ILeaferCanvas
41
46
  public renderer: IRenderer
42
47
 
@@ -56,87 +61,142 @@ export class Leafer extends Group implements ILeafer {
56
61
 
57
62
  protected __eventIds: IEventListenerId[] = []
58
63
 
59
- constructor(userConfig?: ILeaferConfig, parentLeafer?: ILeafer) {
60
- super()
61
64
 
62
- this.creator = Creator
63
65
 
64
- const { config } = this
66
+ constructor(userConfig?: ILeaferConfig) {
67
+ super()
68
+ this.userConfig = userConfig
69
+ if (userConfig?.view) this.init(userConfig)
70
+ }
65
71
 
66
- this.__setAsLeafer()
72
+ public init(userConfig?: ILeaferConfig, app?: IApp): void {
73
+ this.__setLeafer(this)
67
74
  this.__setConfig(userConfig)
68
75
 
76
+ const { config } = this
77
+ this.creator = Creator
78
+ this.hittable = config.hittable
79
+
69
80
  // render
70
81
  this.canvas = Creator.canvas(config)
71
82
  this.renderer = Creator.renderer(this, this.canvas, config)
83
+ this.view = this.canvas.view
72
84
 
73
- // layout
74
- if (this.isSupperLeafer) {
75
- this.__level = 1
85
+ if (this.isApp) {
86
+ this.__setApp()
76
87
  } else {
77
-
88
+ // layout
78
89
  this.watcher = Creator.watcher(this)
79
90
  this.layouter = Creator.layouter(this)
80
-
81
91
  }
82
92
 
83
93
  this.__checkAutoLayout(config)
84
94
 
85
95
  // interaction / manager
86
- if (parentLeafer) {
87
-
88
- parentLeafer.selector?.defaultPath.unshift(this)
89
-
90
- this.selector = parentLeafer.selector
91
- this.interaction = parentLeafer.interaction
92
-
93
- this.canvasManager = parentLeafer.canvasManager
94
- this.hitCanvasManager = parentLeafer.hitCanvasManager
95
- this.imageManager = parentLeafer.imageManager
96
-
97
- if (parentLeafer.running) setTimeout(this.start.bind(this))
98
-
96
+ if (app) {
97
+ this.__bindApp(app)
99
98
  } else {
100
-
101
99
  this.selector = Creator.selector(this)
102
- this.interaction = Creator.interaction(this, this.canvas, this.selector, config)
100
+ if (config.hittable) this.interaction = Creator.interaction(this, this, this.selector, config)
103
101
 
104
- this.canvasManager = new CanvasManager(this)
105
- this.hitCanvasManager = new HitCanvasManager(this)
102
+ this.canvasManager = new CanvasManager()
103
+ this.hitCanvasManager = new HitCanvasManager()
106
104
  this.imageManager = new ImageManager(this, config)
107
105
 
108
- if (config.start) setTimeout(this.start.bind(this))
109
-
106
+ if (config.start) this.startTimer = setTimeout(this.start.bind(this))
110
107
  }
111
108
 
112
109
  this.canvasManager.add(this.canvas)
113
- this.__listenEvents()
114
110
 
111
+ this.__listenEvents()
115
112
  }
116
113
 
117
114
  protected __listenEvents(): void {
118
- this.once(LayoutEvent.END, this.__setAsRoot.bind(this))
115
+ Run.start('FirstCreate')
116
+ this.once(LeaferEvent.START, () => {
117
+ Run.endOfName('FirstCreate')
118
+ Run.start('FirstLayout')
119
+ })
120
+
121
+ this.once(LayoutEvent.END, () => {
122
+ Run.endOfName('FirstLayout')
123
+ Run.start('FirstRender')
124
+
125
+ this.ready = true
126
+
127
+ this.emit(LeaferEvent.BEFORE_READY)
128
+ this.emit(LeaferEvent.READY)
129
+ this.emit(LeaferEvent.AFTER_READY)
130
+ })
131
+
132
+ this.once(RenderEvent.END, () => {
133
+ Run.endOfName('FirstRender')
134
+ this.emit(LeaferEvent.VIEW_READY)
135
+ })
119
136
  }
120
137
 
121
138
  protected __removeListenEvents(): void {
122
139
  this.off__(this.__eventIds)
123
140
  }
124
141
 
142
+ protected __setApp(): void { }
143
+
144
+ protected __bindApp(app: IApp): void {
145
+ app.selector?.defaultPath.unshift(this)
146
+
147
+ this.selector = app.selector
148
+ if (this.config.hittable) this.interaction = app.interaction
149
+
150
+ this.canvasManager = app.canvasManager
151
+ this.hitCanvasManager = app.hitCanvasManager
152
+ this.imageManager = app.imageManager
153
+
154
+ if (app.running) this.startTimer = setTimeout(this.start.bind(this))
155
+ }
156
+
157
+
158
+ public __setLeafer(leafer: ILeafer): void {
159
+ this.leafer = leafer
160
+ this.isLeafer = !!leafer
161
+ this.__level = 1
162
+ }
163
+
125
164
  protected __setConfig(userConfig?: ILeaferConfig): void {
126
- if (userConfig) this.config = DataHelper.default(userConfig, this.config)
165
+ if (userConfig) {
166
+ this.config = DataHelper.default(userConfig, this.config)
167
+ this.__setAppType(this.config.type)
168
+ }
169
+ }
170
+
171
+ protected __setAppType(type: ILeaferType): void {
172
+ if (type === 'user') {
173
+ const { config } = this
174
+ if (!config.pointer) config.pointer = {}
175
+ config.pointer.autoMoveDistance = 0
176
+ }
127
177
  }
128
178
 
129
179
  protected __checkAutoLayout(config: ILeaferConfig): void {
130
180
  if (!config.width || !config.height) {
131
181
  this.autoLayout = new AutoBounds(config)
132
- this.canvas.autoLayout(this.autoLayout, this.__onResize.bind(this))
182
+ this.canvas.startAutoLayout(this.autoLayout, this.__onResize.bind(this))
133
183
  }
134
184
  }
135
185
 
136
186
  public start(): void {
137
187
  if (!this.running) {
138
- this.__interactiveWindow()
139
- this.interaction?.start()
188
+
189
+ if (this.ready) {
190
+ this.emit(LeaferEvent.RESTART)
191
+ } else {
192
+ this.emit(LeaferEvent.START)
193
+ }
194
+
195
+ if (this.interaction) {
196
+ this.__interactiveWindow()
197
+ this.interaction.start()
198
+ }
199
+
140
200
  this.renderer.start()
141
201
  this.layouter.start()
142
202
  this.watcher.start()
@@ -146,21 +206,21 @@ export class Leafer extends Group implements ILeafer {
146
206
 
147
207
  public stop(): void {
148
208
  if (this.running) {
149
- this.interaction?.stop()
209
+ if (this.interaction) this.interaction.stop()
150
210
  this.watcher.stop()
151
211
  this.layouter.stop()
152
212
  this.renderer.stop()
153
213
  this.running = false
214
+ this.emit(LeaferEvent.STOP)
154
215
  }
155
216
  }
156
217
 
157
218
  protected __interactiveWindow(): void {
158
- const { zoom, move } = this.config
159
- if (move) {
219
+ if (this.config.type !== 'user') {
160
220
  const { MOVE } = MoveEvent
161
221
  const { ZOOM } = ZoomEvent
162
- if (!this.hasEvent(MOVE)) this.__eventIds.push(this.on__(MOVE, (e: MoveEvent) => { LeafHelper.moveByWorld(this, e.moveX, e.moveY) }))
163
- if (zoom && !this.hasEvent(ZOOM)) this.__eventIds.push(this.on__(ZOOM, (e: ZoomEvent) => { LeafHelper.zoomByWorld(this, e.scale, e) }))
222
+ if (!this.hasEvent(MOVE)) this.__eventIds.push(this.on__(MOVE, (e: MoveEvent) => { LeafHelper.move(this, e.moveX, e.moveY) }))
223
+ if (!this.hasEvent(ZOOM)) this.__eventIds.push(this.on__(ZOOM, (e: ZoomEvent) => { LeafHelper.zoomOf(this, e, e.scale) }))
164
224
  }
165
225
  }
166
226
 
@@ -179,45 +239,49 @@ export class Leafer extends Group implements ILeafer {
179
239
 
180
240
  public destory(): void {
181
241
  if (this.canvas) {
182
- super.destroy()
183
242
 
243
+ clearTimeout(this.startTimer)
244
+ this.emit(LeaferEvent.END)
245
+
246
+ this.stop()
184
247
  this.__removeListenEvents()
185
248
 
186
- if (!this.parent) {
187
- this.interaction?.destroy()
188
- this.selector.destroy()
189
249
 
190
- this.renderer.destroy()
191
- this.watcher.destroy()
192
- this.layouter.destroy()
250
+ this.interaction?.destroy()
251
+ this.selector.destroy()
193
252
 
194
- this.canvasManager.destory()
195
- this.hitCanvasManager.destory()
196
- this.imageManager.destory()
197
- }
253
+ this.renderer.destroy()
254
+ this.watcher?.destroy()
255
+ this.layouter?.destroy()
256
+
257
+ this.canvasManager.destory()
258
+ this.hitCanvasManager.destory()
259
+ this.imageManager.destory()
198
260
 
199
261
  this.canvas.destroy()
200
- this.canvas = undefined
262
+ this.canvas = null
201
263
 
202
- this.creator = undefined
203
- this.config = undefined
264
+ this.creator = null
265
+ this.config = null
204
266
 
205
- this.interaction = undefined
206
- this.selector = undefined
267
+ this.interaction = null
268
+ this.selector = null
207
269
 
208
270
 
209
- this.renderer = undefined
210
- this.watcher = undefined
211
- this.layouter = undefined
271
+ this.renderer = null
272
+ this.watcher = null
273
+ this.layouter = null
212
274
 
213
- this.canvasManager = undefined
214
- this.hitCanvasManager = undefined
215
- this.imageManager = undefined
275
+ this.canvasManager = null
276
+ this.hitCanvasManager = null
277
+ this.imageManager = null
216
278
 
217
- this.zoomLayer = undefined
279
+ this.zoomLayer = null
218
280
  this.moveLayer = undefined
219
281
 
220
282
  this.parent = undefined
283
+
284
+ super.destroy()
221
285
  }
222
286
  }
223
287
  }
package/src/index.ts CHANGED
@@ -1,2 +1,2 @@
1
1
  export { Leafer } from './Leafer'
2
- export { SuperLeafer } from './SuperLeafer'
2
+ export { App } from './App'
@@ -1,68 +0,0 @@
1
- import { ILeaferConfig, IResizeEvent, ILeaferCanvas, IRenderOptions } from '@leafer/interface'
2
- import { registerUI, DataHelper, RenderEvent } from '@leafer/core'
3
-
4
- import { IGroup } from '@leafer-ui/interface'
5
-
6
- import { Leafer } from './Leafer'
7
-
8
-
9
- @registerUI()
10
- export class SuperLeafer extends Leafer implements IGroup {
11
-
12
- public get isSupperLeafer(): boolean { return true }
13
-
14
- public children: Leafer[] = []
15
-
16
- public start(): void {
17
- if (!this.running) {
18
- this.children.forEach(leafer => { leafer.start() })
19
- this.running = false
20
- }
21
- }
22
-
23
- public stop(): void {
24
- if (this.running) {
25
- this.children.forEach(leafer => { leafer.stop() })
26
- this.running = false
27
- }
28
- }
29
-
30
- public addLeafer(merge?: ILeaferConfig): Leafer {
31
- const leafer = new Leafer(this.__getChildConfig(merge), this)
32
- this.add(leafer)
33
- this.__eventIds.push(leafer.on__(RenderEvent.END, this.renderer.start, this.renderer))
34
- return leafer
35
- }
36
-
37
- public __render(canvas: ILeaferCanvas, options: IRenderOptions): void {
38
- this.children.forEach(leafer => { canvas.copy(leafer.canvas) })
39
- }
40
-
41
- public __onResize(event: IResizeEvent): void {
42
- this.emitEvent(event)
43
- this.children.forEach(leafer => { leafer.resize(event) })
44
- }
45
-
46
- protected __getChildConfig(userConfig?: ILeaferConfig): ILeaferConfig {
47
- let old = { ...this.config }
48
- userConfig = userConfig ? DataHelper.default(userConfig, old) : old
49
- userConfig.view = undefined
50
- if (this.autoLayout) {
51
- userConfig.width = this.width
52
- userConfig.height = this.height
53
- userConfig.pixelRatio = this.pixelRatio
54
- }
55
- return userConfig
56
- }
57
-
58
- public destory(): void {
59
- if (this.children.length) {
60
- super.destory()
61
- this.children.forEach(leafer => {
62
- leafer.destory()
63
- })
64
- this.children.length = 0
65
- }
66
- }
67
-
68
- }