@operato/board 10.0.0-beta.5 → 10.0.0-beta.51

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 (89) hide show
  1. package/CHANGELOG.md +422 -0
  2. package/dist/src/component/container.js +18 -3
  3. package/dist/src/component/container.js.map +1 -1
  4. package/dist/src/component/conveyance.d.ts +2 -0
  5. package/dist/src/component/conveyance.js +38 -0
  6. package/dist/src/component/conveyance.js.map +1 -0
  7. package/dist/src/component/etc.js +2 -10
  8. package/dist/src/component/etc.js.map +1 -1
  9. package/dist/src/component/facility.d.ts +2 -0
  10. package/dist/src/component/facility.js +35 -0
  11. package/dist/src/component/facility.js.map +1 -0
  12. package/dist/src/component/index.d.ts +5 -0
  13. package/dist/src/component/index.js +5 -0
  14. package/dist/src/component/index.js.map +1 -1
  15. package/dist/src/component/line.js +4 -28
  16. package/dist/src/component/line.js.map +1 -1
  17. package/dist/src/component/manufacturing.d.ts +2 -0
  18. package/dist/src/component/manufacturing.js +41 -0
  19. package/dist/src/component/manufacturing.js.map +1 -0
  20. package/dist/src/component/register-default-groups.js +19 -2
  21. package/dist/src/component/register-default-groups.js.map +1 -1
  22. package/dist/src/component/shape.js +5 -29
  23. package/dist/src/component/shape.js.map +1 -1
  24. package/dist/src/component/storage.d.ts +2 -0
  25. package/dist/src/component/storage.js +27 -0
  26. package/dist/src/component/storage.js.map +1 -0
  27. package/dist/src/component/text-and-media.js +2 -25
  28. package/dist/src/component/text-and-media.js.map +1 -1
  29. package/dist/src/component/transport.d.ts +2 -0
  30. package/dist/src/component/transport.js +36 -0
  31. package/dist/src/component/transport.js.map +1 -0
  32. package/dist/src/component/warehouse.d.ts +1 -0
  33. package/dist/src/component/warehouse.js +8 -1
  34. package/dist/src/component/warehouse.js.map +1 -1
  35. package/dist/src/data-storage/board-model-cache.d.ts +30 -0
  36. package/dist/src/data-storage/board-model-cache.js +93 -0
  37. package/dist/src/data-storage/board-model-cache.js.map +1 -0
  38. package/dist/src/graphql/playback-buffer.d.ts +79 -0
  39. package/dist/src/graphql/playback-buffer.js +139 -0
  40. package/dist/src/graphql/playback-buffer.js.map +1 -0
  41. package/dist/src/graphql/playback-buffer.test.d.ts +1 -0
  42. package/dist/src/graphql/playback-buffer.test.js +261 -0
  43. package/dist/src/graphql/playback-buffer.test.js.map +1 -0
  44. package/dist/src/graphql/playback-subscription.d.ts +89 -0
  45. package/dist/src/graphql/playback-subscription.js +258 -0
  46. package/dist/src/graphql/playback-subscription.js.map +1 -0
  47. package/dist/src/index.d.ts +3 -0
  48. package/dist/src/index.js +2 -0
  49. package/dist/src/index.js.map +1 -1
  50. package/dist/src/modeller/bulk-create-dialog.d.ts +51 -0
  51. package/dist/src/modeller/bulk-create-dialog.js +531 -0
  52. package/dist/src/modeller/bulk-create-dialog.js.map +1 -0
  53. package/dist/src/modeller/bulk-create.d.ts +101 -0
  54. package/dist/src/modeller/bulk-create.js +199 -0
  55. package/dist/src/modeller/bulk-create.js.map +1 -0
  56. package/dist/src/modeller/component-toolbar/component-menu.js +8 -1
  57. package/dist/src/modeller/component-toolbar/component-menu.js.map +1 -1
  58. package/dist/src/modeller/edit-toolbar-style.js +38 -1
  59. package/dist/src/modeller/edit-toolbar-style.js.map +1 -1
  60. package/dist/src/modeller/edit-toolbar.d.ts +21 -16
  61. package/dist/src/modeller/edit-toolbar.js +362 -201
  62. package/dist/src/modeller/edit-toolbar.js.map +1 -1
  63. package/dist/src/modeller/scene-viewer/ox-scene-viewer.d.ts +2 -1
  64. package/dist/src/modeller/scene-viewer/ox-scene-viewer.js +7 -11
  65. package/dist/src/modeller/scene-viewer/ox-scene-viewer.js.map +1 -1
  66. package/dist/src/ox-board-modeller.d.ts +8 -1
  67. package/dist/src/ox-board-modeller.js +125 -6
  68. package/dist/src/ox-board-modeller.js.map +1 -1
  69. package/dist/src/ox-board-preview.d.ts +36 -0
  70. package/dist/src/ox-board-preview.js +114 -0
  71. package/dist/src/ox-board-preview.js.map +1 -0
  72. package/dist/src/ox-board-template-list.d.ts +1 -0
  73. package/dist/src/ox-board-template-list.js +19 -1
  74. package/dist/src/ox-board-template-list.js.map +1 -1
  75. package/dist/src/ox-board-viewer.d.ts +50 -1
  76. package/dist/src/ox-board-viewer.js +271 -28
  77. package/dist/src/ox-board-viewer.js.map +1 -1
  78. package/dist/src/ox-playback-controls.d.ts +56 -0
  79. package/dist/src/ox-playback-controls.js +515 -0
  80. package/dist/src/ox-playback-controls.js.map +1 -0
  81. package/dist/src/selector/ox-board-selector.js +11 -1
  82. package/dist/src/selector/ox-board-selector.js.map +1 -1
  83. package/dist/tsconfig.tsbuildinfo +1 -1
  84. package/package.json +17 -12
  85. package/translations/en.json +19 -1
  86. package/translations/ja.json +19 -1
  87. package/translations/ko.json +19 -1
  88. package/translations/ms.json +19 -1
  89. package/translations/zh.json +19 -1
@@ -1,14 +1,16 @@
1
1
  import { __decorate } from "tslib";
2
2
  import '@material/web/icon/icon.js';
3
3
  import '@material/web/fab/fab.js';
4
- import { css, html, LitElement } from 'lit';
4
+ import { css, html, LitElement, nothing } from 'lit';
5
5
  import { customElement, property, query, state } from 'lit/decorators.js';
6
6
  import * as XLSX from 'xlsx';
7
- import { create, SCENE_MODE } from '@hatiolab/things-scene';
7
+ import { create, LoadTracker, LoadingOverlay, SCENE_MODE } from '@hatiolab/things-scene';
8
8
  import { isIOS, togglefullscreen } from '@operato/utils';
9
9
  import { ScrollbarStyles } from '@operato/styles';
10
10
  import { BoardDataStorage } from './data-storage/data-storage.js';
11
11
  import { DataSubscriptionProviderImpl } from './graphql/data-subscription.js';
12
+ import { PlaybackProvider } from './graphql/playback-subscription.js';
13
+ import './ox-playback-controls.js';
12
14
  import { runScenario, startScenario } from './graphql/scenario.js';
13
15
  import { fetchPlayGroupByName } from './graphql/play-group.js';
14
16
  function objectToQueryString(obj) {
@@ -36,28 +38,27 @@ let BoardViewer = class BoardViewer extends LitElement {
36
38
  this.history = false;
37
39
  this.hideFullscreen = false;
38
40
  this.hideNavigation = false;
41
+ this.playbackEnabled = false;
42
+ this._playbackState = 'idle';
43
+ this._playbackActive = false;
44
+ this._playbackSpeed = 1;
45
+ this._playbackCurrentTime = '';
46
+ this._playbackProvider = null;
47
+ this._savedRealProvider = null;
39
48
  this._scene = null;
40
49
  this._forward = [];
41
50
  this._backward = [];
42
51
  this.currentBoardId = (_a = this.board) === null || _a === void 0 ? void 0 : _a.id;
52
+ this._fabExpanded = false;
43
53
  this.resizeHandler = () => {
44
54
  this._scene && this._scene.fit();
45
55
  };
46
56
  }
57
+ get _is3dMode() {
58
+ var _a, _b, _c;
59
+ return !!((_c = (_b = (_a = this._scene) === null || _a === void 0 ? void 0 : _a.root) === null || _b === void 0 ? void 0 : _b.rootModel) === null || _c === void 0 ? void 0 : _c.is3dMode);
60
+ }
47
61
  render() {
48
- var fullscreen = !isIOS() && !this.hideFullscreen
49
- ? html `
50
- <md-fab
51
- id="fullscreen"
52
- @click=${(e) => this.onTapFullscreen()}
53
- @mouseover=${(e) => this.transientShowButtons(true)}
54
- @mouseout=${(e) => this.transientShowButtons()}
55
- title="fullscreen"
56
- >
57
- <md-icon slot="icon">${document.fullscreenElement ? 'fullscreen_exit' : 'fullscreen'}</md-icon>
58
- </md-fab>
59
- `
60
- : html ``;
61
62
  var prev = !this.hideNavigation
62
63
  ? html `
63
64
  <md-icon
@@ -92,7 +93,60 @@ let BoardViewer = class BoardViewer extends LitElement {
92
93
  ></div>
93
94
 
94
95
  <slot></slot>
95
- ${next} ${fullscreen}
96
+ ${next}
97
+
98
+ ${!this.hideFullscreen ? html `
99
+ <div
100
+ fab-group
101
+ ?expanded=${this._fabExpanded}
102
+ @mouseover=${(e) => this.transientShowButtons(true)}
103
+ @mouseout=${(e) => this.transientShowButtons()}
104
+ >
105
+ <md-fab
106
+ class="main-fab"
107
+ ?expanded=${this._fabExpanded}
108
+ @click=${() => { this._fabExpanded = !this._fabExpanded; }}
109
+ title="menu"
110
+ ><md-icon slot="icon">add</md-icon></md-fab>
111
+
112
+ ${isIOS() ? nothing : html `<md-fab
113
+ class="sub-fab"
114
+ @click=${() => { this._fabExpanded = false; this.onTapFullscreen(); }}
115
+ title="fullscreen"
116
+ ><md-icon slot="icon">${document.fullscreenElement ? 'fullscreen_exit' : 'fullscreen'}</md-icon></md-fab>`}
117
+
118
+ <md-fab
119
+ class="sub-fab"
120
+ @click=${() => { this._fabExpanded = false; this.onTapToggle3D(); }}
121
+ title=${this._is3dMode ? '2D mode' : '3D mode'}
122
+ ><md-icon slot="icon">${this._is3dMode ? 'view_in_ar' : '3d_rotation'}</md-icon></md-fab>
123
+
124
+ ${this.playbackEnabled ? html `
125
+ <md-fab
126
+ class="sub-fab"
127
+ @click=${() => { this._fabExpanded = false; this._onTogglePlaybackPanel(); }}
128
+ title="playback"
129
+ ><md-icon slot="icon">${this._playbackActive ? 'stop' : 'history'}</md-icon></md-fab>
130
+ ` : html ``}
131
+ </div>
132
+ ` : html ``}
133
+
134
+ ${this._playbackActive
135
+ ? html `
136
+ <ox-playback-controls
137
+ .playbackState=${this._playbackState}
138
+ .speed=${this._playbackSpeed}
139
+ .currentTime=${this._playbackCurrentTime}
140
+ .timeRange=${this.playbackTimeRange || { from: new Date(Date.now() - 3600000), to: new Date() }}
141
+ @playback-start=${this._onPlaybackStart}
142
+ @playback-pause=${this._onPlaybackPause}
143
+ @playback-resume=${this._onPlaybackResume}
144
+ @playback-stop=${this._onPlaybackStop}
145
+ @playback-seek=${this._onPlaybackSeek}
146
+ @playback-speed=${this._onPlaybackSpeed}
147
+ ></ox-playback-controls>
148
+ `
149
+ : html ``}
96
150
  `;
97
151
  }
98
152
  connectedCallback() {
@@ -111,7 +165,16 @@ let BoardViewer = class BoardViewer extends LitElement {
111
165
  this.closeScene();
112
166
  }
113
167
  updated(changes) {
168
+ // loadTracker가 외부에서 전달되면 즉시 overlay 연결 (fetch 중에도 표시)
169
+ if (changes.has('loadTracker') && this.loadTracker) {
170
+ this._ensureOverlay(this.loadTracker);
171
+ }
114
172
  if (changes.has('board')) {
173
+ // tracker: 외부에서 안 왔으면 여기서 생성 (reset 하지 않음 — 연속성 유지)
174
+ if (!this.loadTracker) {
175
+ this.loadTracker = new LoadTracker();
176
+ this._ensureOverlay(this.loadTracker);
177
+ }
115
178
  this.hidePopup();
116
179
  this.closeScene();
117
180
  if (this.board && this.board.id) {
@@ -147,7 +210,8 @@ let BoardViewer = class BoardViewer extends LitElement {
147
210
  refProvider: this.provider,
148
211
  dataStorage: this.board.id !== 'preview' ? new BoardDataStorage(this.board.id) : undefined,
149
212
  dataSubscriptionProvider: new DataSubscriptionProviderImpl(),
150
- handlers: ['waypoint-handler']
213
+ handlers: ['waypoint-handler'],
214
+ loading: { tracker: this.loadTracker }
151
215
  });
152
216
  if (this.baseUrl) {
153
217
  this._scene.baseUrl = this.baseUrl;
@@ -155,7 +219,20 @@ let BoardViewer = class BoardViewer extends LitElement {
155
219
  // this.provider!.add(this.board.id, this._scene)
156
220
  this.setupScene({ id: this.board.id, scene: this._scene });
157
221
  }
222
+ _ensureOverlay(tracker) {
223
+ if (!this._loadingOverlay) {
224
+ this._loadingOverlay = new LoadingOverlay();
225
+ }
226
+ this._loadingOverlay.attach(this.renderRoot, tracker);
227
+ }
158
228
  closeScene() {
229
+ // 플레이백 중이면 정리
230
+ if (this._playbackProvider) {
231
+ this._playbackProvider.dispose();
232
+ this._playbackProvider = null;
233
+ this._savedRealProvider = null;
234
+ this._playbackState = 'idle';
235
+ }
159
236
  if (this._scene) {
160
237
  this.unbindSceneEvents(this._scene);
161
238
  this._scene.target = null;
@@ -173,12 +250,12 @@ let BoardViewer = class BoardViewer extends LitElement {
173
250
  this.transientShowButtons();
174
251
  }
175
252
  setupScene({ id, scene }, history) {
176
- var _a, _b;
253
+ var _a;
177
254
  this._scene = scene;
178
255
  // 2D 모드: model-layer의 fillStyle을 호스트 배경색으로 설정하여 경계를 자연스럽게 함
179
256
  // 3D 모드: 3D 공간에서 여백 개념이 없으므로 배경색 설정 불필요
180
257
  const backgroundColor = (_a = this._scene) === null || _a === void 0 ? void 0 : _a.root.state.fillStyle;
181
- if (!((_b = this._scene) === null || _b === void 0 ? void 0 : _b.root.state.threed) && typeof backgroundColor === 'string') {
258
+ if (!this._is3dMode && typeof backgroundColor === 'string') {
182
259
  this.style.backgroundColor = backgroundColor;
183
260
  }
184
261
  else {
@@ -285,7 +362,8 @@ let BoardViewer = class BoardViewer extends LitElement {
285
362
  transientShowButtons(stop) {
286
363
  var buttons = [];
287
364
  !this.hideNavigation && buttons.push(this._next, this._prev);
288
- !this.hideFullscreen && buttons.push(this._fullscreen);
365
+ if (this._fabGroup)
366
+ buttons.push(this._fabGroup);
289
367
  if (buttons.length == 0) {
290
368
  return;
291
369
  }
@@ -308,7 +386,7 @@ let BoardViewer = class BoardViewer extends LitElement {
308
386
  }
309
387
  this._forward.length <= 0 ? this._next.setAttribute('hidden', '') : this._next.removeAttribute('hidden');
310
388
  this._backward.length <= 0 ? this._prev.setAttribute('hidden', '') : this._prev.removeAttribute('hidden');
311
- this._fullscreen && this._fullscreen.removeAttribute('hidden');
389
+ this._fabGroup && this._fabGroup.removeAttribute('hidden');
312
390
  this._fade_animations.forEach(animation => {
313
391
  animation.cancel();
314
392
  if (stop)
@@ -346,6 +424,14 @@ let BoardViewer = class BoardViewer extends LitElement {
346
424
  onTapFullscreen() {
347
425
  togglefullscreen(this, () => this.requestUpdate(), () => this.requestUpdate());
348
426
  }
427
+ onTapToggle3D() {
428
+ var _a, _b;
429
+ const modelLayer = (_b = (_a = this._scene) === null || _a === void 0 ? void 0 : _a.root) === null || _b === void 0 ? void 0 : _b.rootModel;
430
+ if (!(modelLayer === null || modelLayer === void 0 ? void 0 : modelLayer.toggleThreeD))
431
+ return;
432
+ modelLayer.toggleThreeD();
433
+ this.requestUpdate();
434
+ }
349
435
  onRunBoard() {
350
436
  this.dispatchEvent(new CustomEvent('run-board', { bubbles: true, composed: true, detail: this.board.id }));
351
437
  }
@@ -452,6 +538,122 @@ let BoardViewer = class BoardViewer extends LitElement {
452
538
  // clickComponent 이벤트만 발생시킨다.
453
539
  window.dispatchEvent(new CustomEvent('clickComponent', { detail: component }));
454
540
  }
541
+ /* playback */
542
+ /**
543
+ * 외부에서 플레이백을 활성화한다.
544
+ * playback-enabled 속성을 설정하면 컨트롤바가 나타나고,
545
+ * 이 메서드로 시간 범위 등 상세 설정을 할 수 있다.
546
+ */
547
+ enablePlayback(config) {
548
+ this.playbackEnabled = true;
549
+ if (config === null || config === void 0 ? void 0 : config.timeRange) {
550
+ this.playbackTimeRange = config.timeRange;
551
+ }
552
+ }
553
+ disablePlayback() {
554
+ this._stopPlayback();
555
+ this._playbackActive = false;
556
+ this.playbackEnabled = false;
557
+ }
558
+ _onTogglePlaybackPanel() {
559
+ if (this._playbackActive) {
560
+ // 패널 닫기 — 재생 중이면 중지
561
+ this._stopPlayback();
562
+ this._playbackActive = false;
563
+ }
564
+ else {
565
+ this._playbackActive = true;
566
+ }
567
+ }
568
+ async _onPlaybackStart(e) {
569
+ const { fromTime, speed } = e.detail;
570
+ await this._startPlayback(fromTime, speed);
571
+ }
572
+ async _onPlaybackPause() {
573
+ var _a;
574
+ await ((_a = this._playbackProvider) === null || _a === void 0 ? void 0 : _a.pause());
575
+ }
576
+ async _onPlaybackResume() {
577
+ var _a;
578
+ await ((_a = this._playbackProvider) === null || _a === void 0 ? void 0 : _a.resume());
579
+ }
580
+ _onPlaybackStop() {
581
+ this._stopPlayback();
582
+ this._playbackActive = false;
583
+ }
584
+ async _onPlaybackSeek(e) {
585
+ var _a;
586
+ await ((_a = this._playbackProvider) === null || _a === void 0 ? void 0 : _a.seek(e.detail.toTime));
587
+ }
588
+ async _onPlaybackSpeed(e) {
589
+ var _a;
590
+ await ((_a = this._playbackProvider) === null || _a === void 0 ? void 0 : _a.setSpeed(e.detail.speed));
591
+ }
592
+ async _startPlayback(fromTime, speed) {
593
+ if (!this._scene)
594
+ return;
595
+ const rootContainer = this._scene.rootContainer;
596
+ // 실시간 provider 보관 및 구독 해제
597
+ if (!this._savedRealProvider) {
598
+ this._savedRealProvider = rootContainer.app.dataSubscriptionProvider;
599
+ await this._unsubscribeAll(rootContainer);
600
+ }
601
+ // PlaybackProvider 생성
602
+ this._playbackProvider = new PlaybackProvider((status) => {
603
+ this._playbackState = status.state;
604
+ this._playbackSpeed = status.speed;
605
+ this._playbackCurrentTime = status.currentTime;
606
+ });
607
+ // provider 교체 및 재구독
608
+ rootContainer.app.dataSubscriptionProvider = this._playbackProvider;
609
+ await this._resubscribeAll(rootContainer);
610
+ // 플레이백 시작
611
+ await this._playbackProvider.start(fromTime, speed);
612
+ }
613
+ async _stopPlayback() {
614
+ if (!this._scene || !this._playbackProvider)
615
+ return;
616
+ const rootContainer = this._scene.rootContainer;
617
+ // 플레이백 구독 해제
618
+ this._playbackProvider.dispose();
619
+ await this._unsubscribeAll(rootContainer);
620
+ // 실시간 provider 복귀
621
+ if (this._savedRealProvider) {
622
+ rootContainer.app.dataSubscriptionProvider = this._savedRealProvider;
623
+ await this._resubscribeAll(rootContainer);
624
+ this._savedRealProvider = null;
625
+ }
626
+ this._playbackProvider = null;
627
+ this._playbackState = 'idle';
628
+ this._playbackCurrentTime = '';
629
+ this._playbackSpeed = 1;
630
+ }
631
+ /**
632
+ * 모든 tag 컴포넌트의 기존 구독을 해제한다.
633
+ */
634
+ async _unsubscribeAll(rootContainer) {
635
+ const promises = [];
636
+ rootContainer.model_layer.traverse((component) => {
637
+ var _a;
638
+ if ((_a = component.model) === null || _a === void 0 ? void 0 : _a.tag) {
639
+ promises.push(rootContainer.unsubscribe(component.model.tag, component));
640
+ }
641
+ });
642
+ await Promise.all(promises);
643
+ }
644
+ /**
645
+ * 모든 tag 컴포넌트를 현재 provider로 재구독한다.
646
+ */
647
+ async _resubscribeAll(rootContainer) {
648
+ const promises = [];
649
+ rootContainer.model_layer.traverse((component) => {
650
+ var _a;
651
+ if ((_a = component.model) === null || _a === void 0 ? void 0 : _a.tag) {
652
+ promises.push(rootContainer.subscribe(component.model.tag, component));
653
+ }
654
+ });
655
+ await Promise.all(promises);
656
+ }
455
657
  hidePopup() {
456
658
  if (this.popup) {
457
659
  this.removeChild(this.popup);
@@ -584,11 +786,40 @@ BoardViewer.styles = [
584
786
  z-index: 1000;
585
787
  }
586
788
 
587
- #fullscreen {
789
+ [fab-group] {
588
790
  position: absolute;
589
791
  bottom: 15px;
590
792
  right: 16px;
591
793
  z-index: 1000;
794
+ display: flex;
795
+ flex-direction: column-reverse;
796
+ gap: 8px;
797
+ }
798
+
799
+ [fab-group] md-fab {
800
+ --md-fab-container-width: 48px;
801
+ --md-fab-container-height: 48px;
802
+ }
803
+
804
+ [fab-group] md-fab.main-fab md-icon {
805
+ transition: transform 0.3s;
806
+ }
807
+
808
+ [fab-group] md-fab.main-fab[expanded] md-icon {
809
+ transform: rotate(45deg);
810
+ }
811
+
812
+ [fab-group] md-fab.sub-fab {
813
+ --md-fab-container-width: 40px;
814
+ --md-fab-container-height: 40px;
815
+ transform: scale(0);
816
+ opacity: 0;
817
+ transition: transform 0.2s, opacity 0.2s;
818
+ }
819
+
820
+ [fab-group][expanded] md-fab.sub-fab {
821
+ transform: scale(1);
822
+ opacity: 1;
592
823
  }
593
824
 
594
825
  [hidden] {
@@ -621,6 +852,9 @@ __decorate([
621
852
  __decorate([
622
853
  property({ type: Boolean })
623
854
  ], BoardViewer.prototype, "history", void 0);
855
+ __decorate([
856
+ property({ type: Object })
857
+ ], BoardViewer.prototype, "loadTracker", void 0);
624
858
  __decorate([
625
859
  property({ type: Boolean, reflect: true, attribute: 'hide-fullscreen' })
626
860
  ], BoardViewer.prototype, "hideFullscreen", void 0);
@@ -628,20 +862,23 @@ __decorate([
628
862
  property({ type: Boolean, reflect: true, attribute: 'hide-navigation' })
629
863
  ], BoardViewer.prototype, "hideNavigation", void 0);
630
864
  __decorate([
631
- state()
632
- ], BoardViewer.prototype, "_scene", void 0);
865
+ property({ type: Boolean, reflect: true, attribute: 'playback-enabled' })
866
+ ], BoardViewer.prototype, "playbackEnabled", void 0);
867
+ __decorate([
868
+ property({ type: Object, attribute: 'playback-time-range' })
869
+ ], BoardViewer.prototype, "playbackTimeRange", void 0);
633
870
  __decorate([
634
871
  state()
635
- ], BoardViewer.prototype, "_forward", void 0);
872
+ ], BoardViewer.prototype, "_playbackState", void 0);
636
873
  __decorate([
637
874
  state()
638
- ], BoardViewer.prototype, "_backward", void 0);
875
+ ], BoardViewer.prototype, "_playbackActive", void 0);
639
876
  __decorate([
640
877
  state()
641
- ], BoardViewer.prototype, "_oldtarget", void 0);
878
+ ], BoardViewer.prototype, "_playbackSpeed", void 0);
642
879
  __decorate([
643
880
  state()
644
- ], BoardViewer.prototype, "_fade_animations", void 0);
881
+ ], BoardViewer.prototype, "_playbackCurrentTime", void 0);
645
882
  __decorate([
646
883
  query('#target')
647
884
  ], BoardViewer.prototype, "_target", void 0);
@@ -651,9 +888,15 @@ __decorate([
651
888
  __decorate([
652
889
  query('#next')
653
890
  ], BoardViewer.prototype, "_next", void 0);
891
+ __decorate([
892
+ state()
893
+ ], BoardViewer.prototype, "_fabExpanded", void 0);
654
894
  __decorate([
655
895
  query('#fullscreen')
656
896
  ], BoardViewer.prototype, "_fullscreen", void 0);
897
+ __decorate([
898
+ query('[fab-group]')
899
+ ], BoardViewer.prototype, "_fabGroup", void 0);
657
900
  BoardViewer = __decorate([
658
901
  customElement('ox-board-viewer')
659
902
  ], BoardViewer);