@rpgjs/client 4.0.2 → 4.0.4

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.
Files changed (46) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/browser/React-ab9e74c2.js +127 -0
  3. package/browser/manifest.json +5 -0
  4. package/browser/rpg.client.js +435 -362
  5. package/browser/rpg.client.umd.cjs +573 -375
  6. package/lib/Components/Component.js +6 -0
  7. package/lib/Components/Component.js.map +1 -1
  8. package/lib/GameEngine.d.ts +1 -0
  9. package/lib/GameEngine.js +6 -2
  10. package/lib/GameEngine.js.map +1 -1
  11. package/lib/{RpgGui.d.ts → Gui/Gui.d.ts} +27 -20
  12. package/lib/Gui/Gui.js +497 -0
  13. package/lib/Gui/Gui.js.map +1 -0
  14. package/lib/Gui/React.d.ts +14 -0
  15. package/lib/Gui/React.js +89 -0
  16. package/lib/Gui/React.js.map +1 -0
  17. package/lib/Gui/Vue.d.ts +13 -0
  18. package/lib/{RpgGuiCompiled.js → Gui/Vue.js} +64 -11
  19. package/lib/Gui/Vue.js.map +1 -0
  20. package/lib/Renderer.js +6 -4
  21. package/lib/Renderer.js.map +1 -1
  22. package/lib/RpgClientEngine.js +1 -1
  23. package/lib/RpgClientEngine.js.map +1 -1
  24. package/lib/Scene/Scene.d.ts +26 -1
  25. package/lib/Scene/Scene.js +32 -3
  26. package/lib/Scene/Scene.js.map +1 -1
  27. package/lib/index.d.ts +2 -1
  28. package/lib/index.js +2 -1
  29. package/lib/index.js.map +1 -1
  30. package/package.json +21 -6
  31. package/rpg.toml +1 -1
  32. package/src/Components/Component.ts +6 -0
  33. package/src/GameEngine.ts +7 -3
  34. package/src/Gui/Gui.ts +556 -0
  35. package/src/Gui/React.ts +116 -0
  36. package/src/Gui/Vue.ts +137 -0
  37. package/src/Renderer.ts +8 -4
  38. package/src/RpgClientEngine.ts +1 -1
  39. package/src/Scene/Scene.ts +35 -4
  40. package/src/index.ts +2 -1
  41. package/lib/RpgGui.js +0 -499
  42. package/lib/RpgGui.js.map +0 -1
  43. package/lib/RpgGuiCompiled.d.ts +0 -3
  44. package/lib/RpgGuiCompiled.js.map +0 -1
  45. package/src/RpgGui.ts +0 -553
  46. package/src/RpgGuiCompiled.ts +0 -43
package/src/RpgGui.ts DELETED
@@ -1,553 +0,0 @@
1
- import RpgGuiCompiled from './RpgGuiCompiled'
2
- import { App, ComponentPublicInstance, createApp } from 'vue'
3
- import { RpgCommonPlayer } from '@rpgjs/common'
4
- import { map } from 'rxjs'
5
- import { RpgSound } from './Sound/RpgSound'
6
- import { RpgClientEngine, RpgResource } from './index'
7
- import { RpgRenderer } from './Renderer'
8
- import { GameEngineClient } from './GameEngine'
9
- import { SceneMap } from './Scene/Map'
10
-
11
- interface GuiOptions {
12
- data: any,
13
- attachToSprite: boolean
14
- display: boolean,
15
- name: string
16
- }
17
-
18
- interface GuiList {
19
- [guiName: string]: GuiOptions
20
- }
21
-
22
- interface VueInstance extends ComponentPublicInstance {
23
- gui: GuiList,
24
- tooltips: RpgCommonPlayer[]
25
- }
26
-
27
- class Gui {
28
- private renderer: RpgRenderer
29
- private gameEngine: GameEngineClient
30
- private clientEngine: RpgClientEngine
31
- private app: App
32
- private vm: VueInstance
33
- private socket
34
- private gui: GuiList = {}
35
-
36
- /** @internal */
37
- _initalize(clientEngine: RpgClientEngine) {
38
-
39
- this.clientEngine = clientEngine
40
- this.renderer = clientEngine.renderer
41
- this.gameEngine = clientEngine.gameEngine
42
-
43
- const self = this
44
- const { gui } = this.renderer.options
45
- const selectorGui = this.renderer.guiEl
46
-
47
- const obj = {
48
- /* template: `
49
- <div
50
- @pointerdown="propagate('pointerdown', $event)"
51
- @pointermove="propagate('pointermove', $event)"
52
- @pointerleave="propagate('pointerleave', $event)"
53
- @pointerover="propagate('pointerover', $event)"
54
- @pointercancel="propagate('pointercancel', $event)"
55
- @pointerup="propagate('pointerup', $event)"
56
- >
57
- <template v-for="ui in fixedGui">
58
- <component :is="ui.name" v-bind="ui.data" v-if="ui.display"></component>
59
- </template>
60
- <div id="tooltips" style="position: absolute; top: 0; left: 0;">
61
- <template v-for="ui in attachedGui">
62
- <template v-if="ui.display">
63
- <div v-for="tooltip of tooltipFilter(tooltips, ui)" :style="tooltipPosition(tooltip.position)">
64
- <component :is="ui.name" v-bind="{ ...ui.data, spriteData: tooltip }" :ref="ui.name"></component>
65
- </div>
66
- </template>
67
- </template>
68
- </div>
69
- </div>
70
- `,*/
71
- render: RpgGuiCompiled,
72
- data() {
73
- return {
74
- gui,
75
- tooltips: []
76
- }
77
- },
78
- provide: () => {
79
- return {
80
- /**
81
- * Recovery of the current scene
82
- *
83
- * ```js
84
- * export default {
85
- * inject: ['rpgScene'],
86
- * mounted() {
87
- * const scene = this.rpgScene()
88
- * scene.stopInputs()
89
- * }
90
- * }
91
- * ```
92
- *
93
- * @prop {Function returns RpgScene} [rpgScene]
94
- * @memberof VueInject
95
- * */
96
- rpgScene: this.renderer.getScene.bind(this.renderer),
97
-
98
- /**
99
- * Retrieve the main container of the game
100
- *
101
- * ```js
102
- * export default {
103
- * inject: ['rpgStage'],
104
- * mounted() {
105
- * const blur = new PIXI.BlurFilter()
106
- this.rpgStage.filters = [blur]
107
- * }
108
- * }
109
- * ```
110
- *
111
- * @prop {PIXI.Container} [rpgStage]
112
- * @memberof VueInject
113
- * */
114
- rpgStage: this.renderer.stage,
115
-
116
- /**
117
- * Listen to all the objects present in the room (events and players)
118
- *
119
- * ```js
120
- * export default {
121
- * inject: ['rpgObjects'],
122
- * mounted() {
123
- * this.obs = this.rpgObjects.subscribe((objects) => {
124
- * for (let id in objects) {
125
- * const obj = objects[id]
126
- * console.log(obj.object, obj.paramsChanged)
127
- * }
128
- * })
129
- * },
130
- * unmounted() {
131
- * this.obs.unsubscribe()
132
- * }
133
- * }
134
- * ```
135
- *
136
- * > remember to unsubscribe for memory leaks
137
- *
138
- * It is an observable that returns an object:
139
- *
140
- * * the key is the object identifier
141
- * * The value is an object comprising:
142
- * * `object`: The entire object
143
- * * `paramsChanged`: Only the representation of the properties that have been changed on this object
144
- *
145
- * @prop {Observable<{ [objectId]: { object: object, paramsChanged: object } }>} [rpgObjects]
146
- * @memberof VueInject
147
- * */
148
- rpgObjects: this.clientEngine.objects,
149
-
150
- /**
151
- * Recovers and listens to the current player
152
- *
153
- * ```js
154
- * export default {
155
- * inject: ['rpgCurrentPlayer'],
156
- * mounted() {
157
- * this.obs = this.rpgCurrentPlayer.subscribe((obj) => {
158
- * console.log(obj.object, obj.paramsChanged)
159
- * })
160
- * },
161
- * unmounted() {
162
- * this.obs.unsubscribe()
163
- * }
164
- * }
165
- * ```
166
- *
167
- * * `object`: The whole player
168
- * * `paramsChanged`: Only the representation of the properties that have been changed on this player
169
- *
170
- * @prop {Observable<{ object: object, paramsChanged: object }>} [rpgCurrentPlayer]
171
- * @memberof VueInject
172
- * */
173
- rpgCurrentPlayer: this.clientEngine.objects
174
- .pipe(
175
- map((objects: any) => objects[this.gameEngine.playerId])
176
- ),
177
- rpgGameEngine: this.gameEngine,
178
-
179
- /**
180
- * Tell the server to close the GUI.
181
- *
182
- * It is a function with 2 parameters:
183
- * * `name`: The name of the component
184
- * * `data`: The data you want to pass to the server
185
- *
186
- * ```js
187
- * export default {
188
- * inject: ['rpgGuiClose'],
189
- * methods: {
190
- * close() {
191
- * this.rpgGuiClose('gui-name', {
192
- * amount: 1000
193
- * })
194
- * }
195
- * }
196
- * }
197
- * ```
198
- *
199
- * @prop {Function(name, data)} [rpgGuiClose]
200
- * @memberof VueInject
201
- * */
202
- rpgGuiClose(name: string, data?) {
203
- const guiId = name || this.$options.name
204
- self.socket.emit('gui.exit', {
205
- guiId,
206
- data
207
- })
208
- },
209
-
210
- /**
211
- * Perform an interaction with the open GUI
212
- *
213
- * It is a function with 2 parameters:
214
- * * `guiId`: The name of the component/Gui
215
- * * `name`: The name of the interaction (defined on the server side)
216
- * * `data`: Data to be sent
217
- *
218
- * ```js
219
- * export default {
220
- * inject: ['rpgGuiInteraction'],
221
- * methods: {
222
- * changeGold() {
223
- * this.rpgGuiInteraction('gui-name', 'change-gold', {
224
- * amount: 100
225
- * })
226
- * }
227
- * }
228
- * }
229
- * ```
230
- *
231
- * @prop {Function(guiId, name, data = {})} [rpgGuiInteraction]
232
- * @memberof VueInject
233
- * */
234
- rpgGuiInteraction: (guiId: string, name: string, data: any = {}) => {
235
- this.socket.emit('gui.interaction', {
236
- guiId,
237
- name,
238
- data
239
- })
240
- },
241
-
242
- /**
243
- * Listen to the keys that are pressed on the keyboard
244
- *
245
- * ```js
246
- * export default {
247
- * inject: ['rpgKeypress'],
248
- * mounted() {
249
- * this.obs = this.rpgKeypress.subscribe(({ inputName, control }) => {
250
- * console.log(inputName) // "escape"
251
- * console.log(control.actionName) // "back"
252
- * })
253
- * },
254
- * unmounted() {
255
- * this.obs.unsubscribe()
256
- * }
257
- * }
258
- * ```
259
- *
260
- * @prop {Observable<{ inputName: string, control: { actionName: string, options: any } }>} [rpgKeypress]
261
- * @memberof VueInject
262
- * */
263
- rpgKeypress: this.clientEngine.keyChange
264
- .pipe(
265
- map(name => {
266
- const control = this.clientEngine.controls.getControl(name)
267
- return {
268
- inputName: name,
269
- control
270
- }
271
- })
272
- ),
273
-
274
- /**
275
- * Recovers the socket.
276
- *
277
- * ```js
278
- * export default {
279
- * inject: ['rpgSocket'],
280
- * mounted() {
281
- * const socket = this.rpgSocket()
282
- * socket.emit('foo', 'bar')
283
- * }
284
- * }
285
- * ```
286
- *
287
- * @prop {Function returns RpgScene} [rpgSocket]
288
- * @memberof VueInject
289
- * */
290
- rpgSocket: () => this.socket,
291
-
292
- /**
293
- * The RpgGui object to control GUIs
294
- *
295
- * ```js
296
- * export default {
297
- * inject: ['rpgGui'],
298
- * mounted() {
299
- * const guis = this.rpgGui.getAll()
300
- * }
301
- * }
302
- * ```
303
- *
304
- * @prop {RpgGui} [rpgGui]
305
- * @memberof VueInject
306
- * */
307
- rpgGui: this,
308
-
309
- /**
310
- * Equivalent to RpgSound
311
- *
312
- * ```js
313
- * export default {
314
- * inject: ['rpgSound'],
315
- * mounted() {
316
- * this.rpgSound.get('my-sound-id').play()
317
- * }
318
- * }
319
- * ```
320
- *
321
- * @prop {RpgSound} [rpgSound]
322
- * @memberof VueInject
323
- * */
324
- rpgSound: RpgSound,
325
-
326
- /**
327
- * Find the game's image and sound library
328
- *
329
- * ```js
330
- * export default {
331
- * inject: ['rpgResource'],
332
- * mounted() {
333
- * const resourceImage = this.rpgResource.spritesheets.get('image_id')
334
- * const resourceSound = this.rpgResource.sounds.get('sound_id')
335
- * }
336
- * }
337
- * ```
338
- *
339
- * @prop { { spritesheets: Map, sounds: Map } } [rpgResource]
340
- * @memberof VueInject
341
- * */
342
- rpgResource: RpgResource,
343
-
344
- /**
345
- * Get RpgClientEngine instance
346
- *
347
- * ```js
348
- * export default {
349
- * inject: ['rpgEngine'],
350
- * mounted() {
351
- * const vueInstance = this.rpgEngine.vueInstance
352
- * }
353
- * }
354
- * ```
355
- *
356
- * @prop {RpgClientEngine} [rpgEngine]
357
- * @memberof VueInject
358
- * */
359
- rpgEngine: this.clientEngine
360
- }
361
- },
362
- computed: {
363
- fixedGui() {
364
- return Object.values(this.gui).filter((gui: any) => !gui.attachToSprite)
365
- },
366
- attachedGui() {
367
- return Object.values(this.gui).filter((gui: any) => gui.attachToSprite)
368
- }
369
- },
370
- methods: {
371
- propagate: (type: string, event) => {
372
- this.renderer.canvas.dispatchEvent(new MouseEvent(type, event))
373
- },
374
- tooltipPosition: (position: { x: number, y: number }) => {
375
- const scene = this.renderer.getScene<SceneMap>()
376
- const viewport = scene?.viewport
377
- if (viewport) {
378
- const left = position.x - viewport.left
379
- const top = position.y - viewport.top
380
- return {
381
- transform: `translate(${left}px,${top}px)`
382
- }
383
- }
384
- },
385
- tooltipFilter(sprites: RpgCommonPlayer[], ui: GuiOptions): RpgCommonPlayer[] {
386
- return sprites.filter(tooltip => tooltip.guiDisplay)
387
- }
388
- }
389
- }
390
-
391
- this.app = createApp(obj)
392
-
393
- for (let ui of gui) {
394
- this.app.component(ui.name, ui)
395
- this.gui[ui.name] = {
396
- data: ui.data,
397
- attachToSprite: ui.rpgAttachToSprite,
398
- display: false,
399
- name: ui.name
400
- }
401
- }
402
- this.vm = this.app.mount(selectorGui) as VueInstance
403
- this.vm.gui = this.gui
404
- this.renderer.app = this.app
405
- this.renderer.vm = this.vm
406
- }
407
-
408
- /** @internal */
409
- update(logicObjects: RpgCommonPlayer) {
410
- this.vm.tooltips = Object.values(logicObjects).map((object: any) => object.object)
411
- }
412
-
413
- /** @internal */
414
- _setSocket(socket) {
415
- this.socket = socket
416
- this.socket.on('gui.open', ({ guiId, data }) => {
417
- this.display(guiId, data)
418
- })
419
- this.socket.on('gui.tooltip', ({ players, display }) => {
420
- for (let playerId of players) {
421
- const sprite = this.renderer.getScene<SceneMap>()?.getSprite(playerId)
422
- if (sprite) sprite.guiDisplay = display
423
- }
424
- })
425
- this.socket.on('gui.exit', (guiId) => {
426
- this.hide(guiId)
427
- })
428
- }
429
-
430
- /** @internal */
431
- _setGui(id, obj) {
432
- const guiObj = this.get(id)
433
- if (!guiObj) {
434
- throw `The GUI named ${id} is non-existent. Please add the component in the gui property of the decorator @RpgClient`
435
- }
436
- for (let key in obj) {
437
- guiObj[key] = obj[key]
438
- }
439
- this.vm.gui = Object.assign({}, this.vm.gui)
440
- }
441
-
442
- /**
443
- * Get a GUI. You retrieve GUI data and information whether it is displayed or not
444
- *
445
- * ```ts
446
- * import { RpgGui } from '@rpgjs/client'
447
- *
448
- * const gui = RpgGui.get('my-gui')
449
- * console.log(gui.display) // false
450
- * ```
451
- *
452
- * @title Get a GUI
453
- * @method RpgGui.get(id)
454
- * @param {string} id
455
- * @returns { { data: any, display: boolean } }
456
- * @memberof RpgGui
457
- */
458
- get(id) {
459
- if (typeof id != 'string') {
460
- id = id.name
461
- }
462
- return this.gui[id]
463
- }
464
-
465
- /**
466
- * Get all GUI. You retrieve GUI data and information whether it is displayed or not
467
- *
468
- * ```ts
469
- * import { RpgGui } from '@rpgjs/client'
470
- *
471
- * const gui = RpgGui.getAll()
472
- * console.log(gui) // { 'rpg-dialog': { data: {}, display: true } }
473
- * ```
474
- *
475
- * @title Get all GUI
476
- * @method RpgGui.getAll()
477
- * @returns { { [guiName]: { data: any, display: boolean } }}
478
- * @memberof RpgGui
479
- */
480
- getAll() {
481
- return this.gui
482
- }
483
-
484
- /**
485
- * Checks if the GUI exists RpgClient's gui array
486
- *
487
- * ```ts
488
- * import { RpgGui } from '@rpgjs/client'
489
- *
490
- * RpgGui.exists('my-gui') // true
491
- * ```
492
- *
493
- * @title GUI Exists ?
494
- * @method RpgGui.exists(id)
495
- * @param {string} id
496
- * @returns {boolean}
497
- * @memberof RpgGui
498
- */
499
- exists(id: string): boolean {
500
- return !!this.get(id)
501
- }
502
-
503
- /**
504
- * Calls a GUI according to identifier. You can send retrievable data in the component
505
- *
506
- * ```ts
507
- * import { RpgGui } from '@rpgjs/client'
508
- *
509
- * RpgGui.display('my-gui')
510
- * ```
511
- *
512
- * @title Display GUI
513
- * @method RpgGui.display(id,data)
514
- * @param {string} id
515
- * @param {object} [data]
516
- * @returns {void}
517
- * @memberof RpgGui
518
- */
519
- display(id: string, data = {}) {
520
- this._setGui(id, {
521
- display: true,
522
- data
523
- })
524
- }
525
-
526
- /**
527
- * Hide a GUI according to its identifier
528
- *
529
- * ```ts
530
- * import { RpgGui } from '@rpgjs/client'
531
- *
532
- * RpgGui.hide('my-gui')
533
- * ```
534
- *
535
- * @title Hide GUI
536
- * @method RpgGui.hide(id)
537
- * @param {string} id
538
- * @returns {void}
539
- * @memberof RpgGui
540
- */
541
- hide(id: string) {
542
- this._setGui(id, {
543
- display: false
544
- })
545
- }
546
-
547
- /** @internal */
548
- clear() {
549
- this.gui = {}
550
- }
551
- }
552
-
553
- export const RpgGui = new Gui()
@@ -1,43 +0,0 @@
1
- const __sfc__ = {}
2
- import { renderList as _renderList, Fragment as _Fragment, openBlock as _openBlock, createElementBlock as _createElementBlock, resolveDynamicComponent as _resolveDynamicComponent, normalizeProps as _normalizeProps, guardReactiveProps as _guardReactiveProps, createBlock as _createBlock, mergeProps as _mergeProps, createCommentVNode as _createCommentVNode, normalizeStyle as _normalizeStyle, createElementVNode as _createElementVNode } from "vue"
3
-
4
- const _hoisted_1 = {
5
- id: "tooltips",
6
- style: {"position":"absolute","top":"0","left":"0"}
7
- }
8
- export default function render(_ctx, _cache) {
9
- return (_openBlock(), _createElementBlock("div", {
10
- onPointerdown: _cache[0] || (_cache[0] = $event => (_ctx.propagate('pointerdown', $event))),
11
- onPointermove: _cache[1] || (_cache[1] = $event => (_ctx.propagate('pointermove', $event))),
12
- onPointerleave: _cache[2] || (_cache[2] = $event => (_ctx.propagate('pointerleave', $event))),
13
- onPointerover: _cache[3] || (_cache[3] = $event => (_ctx.propagate('pointerover', $event))),
14
- onPointercancel: _cache[4] || (_cache[4] = $event => (_ctx.propagate('pointercancel', $event))),
15
- onPointerup: _cache[5] || (_cache[5] = $event => (_ctx.propagate('pointerup', $event)))
16
- }, [
17
- (_openBlock(true), _createElementBlock(_Fragment, null, _renderList(_ctx.fixedGui, (ui) => {
18
- return (_openBlock(), _createElementBlock(_Fragment, null, [
19
- (ui.display)
20
- ? (_openBlock(), _createBlock(_resolveDynamicComponent(ui.name), _normalizeProps(_mergeProps({ key: 0 }, ui.data)), null, 16 /* FULL_PROPS */))
21
- : _createCommentVNode("v-if", true)
22
- ], 64 /* STABLE_FRAGMENT */))
23
- }), 256 /* UNKEYED_FRAGMENT */)),
24
- _createElementVNode("div", _hoisted_1, [
25
- (_openBlock(true), _createElementBlock(_Fragment, null, _renderList(_ctx.attachedGui, (ui) => {
26
- return (_openBlock(), _createElementBlock(_Fragment, null, [
27
- (ui.display)
28
- ? (_openBlock(true), _createElementBlock(_Fragment, { key: 0 }, _renderList(_ctx.tooltipFilter(_ctx.tooltips, ui), (tooltip) => {
29
- return (_openBlock(), _createElementBlock("div", {
30
- style: _normalizeStyle(_ctx.tooltipPosition(tooltip.position))
31
- }, [
32
- (_openBlock(), _createBlock(_resolveDynamicComponent(ui.name), _mergeProps({ ...ui.data, spriteData: tooltip }, {
33
- ref_for: true,
34
- ref: ui.name
35
- }), null, 16 /* FULL_PROPS */))
36
- ], 4 /* STYLE */))
37
- }), 256 /* UNKEYED_FRAGMENT */))
38
- : _createCommentVNode("v-if", true)
39
- ], 64 /* STABLE_FRAGMENT */))
40
- }), 256 /* UNKEYED_FRAGMENT */))
41
- ])
42
- ], 32 /* HYDRATE_EVENTS */))
43
- }