@operato/scene-tab 8.0.0-beta.0 → 8.0.0-beta.2

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/demo/index.html DELETED
@@ -1,288 +0,0 @@
1
- <!DOCTYPE html>
2
- <!--
3
- @license
4
- Copyright © HatioLab Inc. All rights reserved.
5
- -->
6
- <html>
7
- <head>
8
- <meta charset="utf-8" />
9
- <meta name="viewport" content="width=device-width, minimum-scale=1.0, initial-scale=1.0, user-scalable=yes" />
10
- <title>things-scene-tab Demo</title>
11
- <script src="../../webcomponentsjs/webcomponents-lite.min.js"></script>
12
-
13
- <link rel="import" href="../../things-scene-viewer/things-scene-viewer.html" />
14
- <link rel="import" href="../../things-scene-indoor-map/things-scene-indoor-map.html" />
15
- <link rel="import" href="../../things-scene-modeler/things-scene-properties.html" />
16
-
17
- <script src="../things-scene-tab.js"></script>
18
-
19
- <style is="custom-style">
20
- @font-face {
21
- font-family: 'Bitstream Vera Serif Bold';
22
- src: url('fonts/VeraSeBd.ttf');
23
- }
24
-
25
- things-scene-viewer {
26
- display: block;
27
- width: 100%;
28
- height: 560px;
29
- }
30
- </style>
31
- </head>
32
- <body unresolved>
33
- <template is="dom-bind" id="app">
34
- <p>An example of <code>&lt;things-scene-tab&gt;</code>:</p>
35
-
36
- <things-scene-viewer id="scene" scene="{{scene}}" selected="{{selected}}" model="[[model]]" mode="1">
37
- <things-scene-layer type="selection-layer"></things-scene-layer>
38
- <things-scene-layer type="modeling-layer"></things-scene-layer>
39
- <things-scene-handler type="text-editor"></things-scene-handler>
40
- <things-scene-handler type="move-handler"></things-scene-handler>
41
- </things-scene-viewer>
42
-
43
- <things-scene-properties scene="[[scene]]" selected="[[selected]]" model="{{target}}" bounds="{{bounds}}">
44
- <fieldset class="same-width">
45
- <legend>Stack style</legend>
46
-
47
- <label>Active TabCard</label>
48
- <input
49
- type="number"
50
- value-as-number="{{target.layoutConfig.activeIndex::change}}"
51
- min="0"
52
- max="100"
53
- step="1"
54
- numberonly="true"
55
- />
56
-
57
- <label>reference</label>
58
- <input type="text" value="{{target.reference::change}}" />
59
- </fieldset>
60
- </things-scene-properties>
61
- </template>
62
-
63
- <script>
64
- window.addEventListener('WebComponentsReady', function (e) {
65
- var app = document.querySelector('#app')
66
-
67
- app.model = {
68
- width: 500,
69
- height: 500,
70
- components: [
71
- {
72
- type: 'tab',
73
- reference: 'indoor-map',
74
- left: 100,
75
- top: 100,
76
- width: 100,
77
- height: 400,
78
- lineWidth: 10,
79
- // lineWidth: 0,
80
- fillStyle: 'navy',
81
- strokeStyle: 'red',
82
- activeFillStyle: 'red',
83
- fontColor: 'black',
84
- activeFontColor: 'white',
85
- activeIndex: 2
86
- },
87
- {
88
- type: 'tab-container',
89
- id: 'tab-container',
90
- left: 250,
91
- top: 100,
92
- width: 600,
93
- height: 400,
94
- fontSize: 80,
95
- fontColor: '#000000',
96
- lineWidth: 10,
97
- strokeStyle: 'red',
98
- active: 0,
99
- components: [
100
- {
101
- type: 'tab-card',
102
- fillStyle: 'orange',
103
- width: 100,
104
- height: 100,
105
- text: 'first',
106
- components: [
107
- {
108
- type: 'rect',
109
- left: 100,
110
- top: 220,
111
- width: 100,
112
- height: 100,
113
- fillStyle: 'red',
114
- lineWidth: 4
115
- },
116
- {
117
- type: 'ellipse',
118
- cx: 400,
119
- cy: 200,
120
- rx: 100,
121
- ry: 100,
122
- fillStyle: 'blue',
123
- lineWidth: 4
124
- },
125
- {
126
- type: 'polygon',
127
- path: [
128
- {
129
- x: 100,
130
- y: 100
131
- },
132
- {
133
- x: 200,
134
- y: 150
135
- },
136
- {
137
- x: 150,
138
- y: 200
139
- }
140
- ],
141
- fillStyle: 'blue',
142
- lineWidth: 4
143
- }
144
- ]
145
- },
146
- {
147
- type: 'tab-card',
148
- fillStyle: 'navy',
149
- width: 100,
150
- height: 100,
151
- components: [
152
- {
153
- type: 'rect',
154
- left: 100,
155
- top: 220,
156
- width: 100,
157
- height: 100,
158
- fillStyle: 'red',
159
- lineWidth: 4
160
- },
161
- {
162
- type: 'ellipse',
163
- cx: 400,
164
- cy: 200,
165
- rx: 100,
166
- ry: 100,
167
- fillStyle: 'blue',
168
- lineWidth: 4
169
- },
170
- {
171
- type: 'polygon',
172
- path: [
173
- {
174
- x: 100,
175
- y: 100
176
- },
177
- {
178
- x: 200,
179
- y: 150
180
- },
181
- {
182
- x: 150,
183
- y: 200
184
- }
185
- ],
186
- fillStyle: 'blue',
187
- lineWidth: 4
188
- }
189
- ]
190
- },
191
- {
192
- type: 'tab-card',
193
- fillStyle: 'black',
194
- width: 100,
195
- height: 100,
196
- components: [
197
- {
198
- type: 'rect',
199
- left: 100,
200
- top: 220,
201
- width: 100,
202
- height: 100,
203
- fillStyle: 'red',
204
- lineWidth: 4
205
- },
206
- {
207
- type: 'ellipse',
208
- cx: 400,
209
- cy: 200,
210
- rx: 100,
211
- ry: 100,
212
- fillStyle: 'blue',
213
- lineWidth: 4
214
- },
215
- {
216
- type: 'polygon',
217
- path: [
218
- {
219
- x: 100,
220
- y: 100
221
- },
222
- {
223
- x: 200,
224
- y: 150
225
- },
226
- {
227
- x: 150,
228
- y: 200
229
- }
230
- ],
231
- fillStyle: 'blue',
232
- lineWidth: 4
233
- }
234
- ]
235
- },
236
- {
237
- type: 'tab-card',
238
- fillStyle: 'green',
239
- width: 100,
240
- height: 100,
241
- components: [
242
- {
243
- type: 'rect',
244
- left: 100,
245
- top: 220,
246
- width: 100,
247
- height: 100,
248
- fillStyle: 'red',
249
- lineWidth: 4
250
- },
251
- {
252
- type: 'ellipse',
253
- cx: 400,
254
- cy: 200,
255
- rx: 100,
256
- ry: 100,
257
- fillStyle: 'blue',
258
- lineWidth: 4
259
- },
260
- {
261
- type: 'polygon',
262
- path: [
263
- {
264
- x: 100,
265
- y: 100
266
- },
267
- {
268
- x: 200,
269
- y: 150
270
- },
271
- {
272
- x: 150,
273
- y: 200
274
- }
275
- ],
276
- fillStyle: 'blue',
277
- lineWidth: 4
278
- }
279
- ]
280
- }
281
- ]
282
- }
283
- ]
284
- }
285
- })
286
- </script>
287
- </body>
288
- </html>
@@ -1,5 +0,0 @@
1
- <!--
2
- @license
3
- Copyright © HatioLab Inc. All rights reserved.
4
- -->
5
- <script src="../things-scene-tab.js"></script>
package/src/index.ts DELETED
@@ -1,8 +0,0 @@
1
- /*
2
- * Copyright © HatioLab Inc. All rights reserved.
3
- */
4
-
5
- export { default as TabCard } from './tab-card'
6
- export { default as TabContainer } from './tab-container'
7
- export { default as Tab } from './tab'
8
- export { default as TabButton } from './tab-button'
package/src/tab-button.ts DELETED
@@ -1,74 +0,0 @@
1
- /*
2
- * Copyright © HatioLab Inc. All rights reserved.
3
- */
4
- import { Component, RectPath, State } from '@hatiolab/things-scene'
5
-
6
- import Tab from './tab'
7
-
8
- export default class TabButton extends RectPath(Component) {
9
- get index() {
10
- return (this.parent as Tab).indexOf(this)
11
- }
12
-
13
- get activated() {
14
- return (this.parent as Tab).activeIndex === this.index
15
- }
16
-
17
- private _fillStyle?: string
18
- private _fontColor?: string
19
- private _strokeStyle?: string
20
- private _lineWidth?: string
21
-
22
- prerender(context: CanvasRenderingContext2D) {
23
- super.prerender(context)
24
-
25
- let { activeFillStyle, activeLineColor, activeLineWidth, activeFontColor } = this.state
26
-
27
- if (this.activated) {
28
- this.model.fillStyle = activeFillStyle
29
- this.model.fontColor = activeFontColor
30
- this.model.strokeStyle = activeLineColor
31
- this.model.lineWidth = activeLineWidth
32
- } else {
33
- this.model.fillStyle = this._fillStyle
34
- this.model.fontColor = this._fontColor
35
- this.model.strokeStyle = this._strokeStyle
36
- this.model.lineWidth = this._lineWidth
37
- }
38
- }
39
-
40
- render(context: CanvasRenderingContext2D) {
41
- var { left = 0, top = 0, width, height } = this.bounds
42
-
43
- context.beginPath()
44
-
45
- context.rect(left, top, width, height)
46
-
47
- this.drawFill(context)
48
- this.drawStroke(context)
49
- }
50
-
51
- onclick(e: MouseEvent) {
52
- ;(this.parent as Tab).activeIndex = this.index
53
- this.parent.invalidate()
54
- }
55
-
56
- setStylesFromParent(style: State) {
57
- if ('fillStyle' in style) this._fillStyle = style.fillStyle
58
- if ('fontColor' in style) this._fontColor = style.fontColor
59
- if ('strokeStyle' in style) this._strokeStyle = style.strokeStyle
60
- if ('lineWidth' in style) this._lineWidth = style.lineWidth
61
-
62
- this.set(style)
63
- }
64
-
65
- onchange(after: State) {
66
- if ('text' in after) {
67
- ;(this.parent as Tab).reference?.getAt(this.index).setState('text', after.text)
68
- }
69
-
70
- this.invalidate()
71
- }
72
- }
73
-
74
- Component.register('tab-button', TabButton)
package/src/tab-card.ts DELETED
@@ -1,76 +0,0 @@
1
- /*
2
- * Copyright © HatioLab Inc. All rights reserved.
3
- */
4
- import { Component, ComponentNature, Container } from '@hatiolab/things-scene'
5
-
6
- import TabContainer from './tab-container'
7
-
8
- const NATURE: ComponentNature = {
9
- mutable: false,
10
- resizable: true,
11
- rotatable: true,
12
- properties: [
13
- {
14
- type: 'action',
15
- label: 'remove',
16
- name: 'remove',
17
- property: {
18
- icon: 'remove_circle',
19
- action: function (tabCard: TabCard) {
20
- let tabContainer = tabCard.parent as TabContainer
21
- tabContainer.removeComponent(tabCard)
22
- tabContainer.set('activeIndex', 0)
23
- }
24
- }
25
- }
26
- ]
27
- }
28
-
29
- export default class TabCard extends Container {
30
- private _clickPoint?: Component
31
-
32
- get hasTextProperty() {
33
- return false
34
- }
35
-
36
- get showMoveHandle() {
37
- return false
38
- }
39
-
40
- /*
41
- * PATH 리스트를 직접 수정할 수 있는 지를 결정한다.
42
- *
43
- * 일반적으로 PATH는 바운드 생성을 위해서 논리적으로 생성되므로, 직접 수정하지 않는다.(return false)
44
- * 그러나, 각 꼭지점들이 개별로 움직이는 다각형류는 path 라는 모델데이타를 가지므로, 직접수정이 가능할 수 있다.(return true)
45
- *
46
- * Immutable 컴포넌트의 형상을 바꾸는 방법은 바운드를 이용한 리사이즈나, 특별한 컨트롤을 통해서 가능하다.
47
- */
48
- get mutable() {
49
- return false
50
- }
51
-
52
- /*
53
- * BOUND를 통해서 리사이즈를 할 수 있는 지를 결정한다.
54
- *
55
- * 일반적으로 면적을 갖는 컴포넌트는 대체로 가능하다.(return true)
56
- * 그러나, LINE 등 면적을 가지지않는 컴포넌트는 가능하지 않도록 정의한다.(return false)
57
- */
58
- get resizable() {
59
- return false
60
- }
61
-
62
- /*
63
- * 회전을 할 수 있는 지를 결정한다.
64
- *
65
- * 일반적으로 모든 컴포넌트는 가능하다.(return true)
66
- */
67
- get rotatable() {
68
- return false
69
- }
70
-
71
- get nature() {
72
- return NATURE
73
- }
74
- }
75
-
76
- Component.register('tab-card', TabCard)
@@ -1,210 +0,0 @@
1
- /*
2
- * Copyright © HatioLab Inc. All rights reserved.
3
- */
4
- import { CardLayout, Component, ComponentNature, Container, Model, POINT, State } from '@hatiolab/things-scene'
5
-
6
- import TabCard from './tab-card'
7
-
8
- const LABEL_WIDTH = 25
9
- const LABEL_HEIGHT = 25
10
-
11
- function rgba(r: number, g: number, b: number, a: number) {
12
- return `rgba(${r}, ${g}, ${b}, ${a})`
13
- }
14
-
15
- const NATURE: ComponentNature = {
16
- mutable: false,
17
- resizable: true,
18
- rotatable: true,
19
- properties: [
20
- {
21
- type: 'action',
22
- label: 'add-card',
23
- name: 'addCard',
24
- property: {
25
- icon: 'add_circle',
26
- action: (tabContainer: TabContainer) => {
27
- tabContainer.addCard()
28
- }
29
- }
30
- },
31
- {
32
- type: 'number',
33
- label: 'active index',
34
- name: 'activeIndex'
35
- }
36
- ],
37
- 'value-property': 'activeIndex',
38
- help: 'scene/component/tab-container'
39
- }
40
-
41
- export default class TabContainer extends Container {
42
- private _focused: boolean = false
43
- private __down_point?: POINT
44
-
45
- get nature() {
46
- return NATURE
47
- }
48
-
49
- get layout() {
50
- return CardLayout
51
- }
52
-
53
- get layoutConfig() {
54
- return this.getState('layoutConfig')
55
- }
56
-
57
- set layoutConfig(config) {
58
- this.setState('layoutConfig', config)
59
- }
60
-
61
- get activeCard(): TabCard {
62
- return this.components[this.getState('layoutConfig').activeIndex || 0] as TabCard
63
- }
64
-
65
- get activeIndex() {
66
- return this.getState('activeIndex') || 0
67
- }
68
-
69
- set activeIndex(activeIndex: number) {
70
- this.setState('activeIndex', Number(activeIndex))
71
- }
72
-
73
- ready() {
74
- super.ready()
75
-
76
- if (this.components.length == 0) {
77
- this.addCard()
78
- }
79
-
80
- this.data = this.state.activeIndex
81
- }
82
-
83
- postrender(context: CanvasRenderingContext2D) {
84
- if (!this.app.isViewMode && this._focused) {
85
- var { left, top, width, fillStyle } = this.state
86
-
87
- // tabCard 선택 탭 그리기
88
- for (let i = 0; i < this.components.length; i++) {
89
- context.beginPath()
90
-
91
- context.rect(left - LABEL_WIDTH, top + i * LABEL_HEIGHT, LABEL_WIDTH, LABEL_HEIGHT)
92
-
93
- let color = 255 - ((20 * (i + 1)) % 255)
94
- context.fillStyle = rgba(color, color, color, 1)
95
- context.fill()
96
-
97
- context.closePath()
98
- }
99
-
100
- context.beginPath()
101
-
102
- context.moveTo(left, top)
103
- context.lineTo(left - LABEL_WIDTH, top)
104
- context.lineTo(left - LABEL_WIDTH, top + this.components.length * LABEL_HEIGHT)
105
- context.lineTo(left, top + this.components.length * LABEL_HEIGHT)
106
-
107
- context.strokeStyle = '#ccc'
108
- context.stroke()
109
-
110
- context.closePath()
111
- }
112
-
113
- super.postrender(context)
114
- }
115
-
116
- contains(x: number, y: number) {
117
- var contains = super.contains(x, y)
118
-
119
- if (this.app.isViewMode) return contains
120
-
121
- var { left, top, width } = this.bounds
122
- var h = LABEL_HEIGHT
123
-
124
- contains =
125
- contains ||
126
- // card selector 영역에 포함되는지
127
- (x < Math.max(left - LABEL_WIDTH, left) &&
128
- x > Math.min(left - LABEL_WIDTH, left) &&
129
- y < Math.max(top + h * this.size(), top) &&
130
- y > Math.min(top + h * this.size(), top))
131
-
132
- if (contains) this._focused = true
133
- else this._focused = false
134
-
135
- this.invalidate()
136
- return contains
137
- }
138
-
139
- onchange(after: State) {
140
- if ('activeIndex' in after) {
141
- this.layoutConfig = {
142
- ...this.layoutConfig,
143
- activeIndex: after.activeIndex
144
- }
145
-
146
- this.data = after.activeIndex
147
- }
148
- }
149
-
150
- onmouseup(e: MouseEvent) {
151
- var down_point = this.__down_point
152
- delete this.__down_point
153
-
154
- if (!down_point || down_point.x != e.offsetX || down_point.y != e.offsetY) {
155
- return
156
- }
157
-
158
- var point = this.transcoordC2S(e.offsetX, e.offsetY)
159
-
160
- var { left, top } = this.state
161
-
162
- var x = point.x - left
163
- var y = point.y - top
164
-
165
- if (x > 0) return
166
-
167
- y /= LABEL_HEIGHT
168
- y = Math.floor(y)
169
-
170
- if (!this.layoutConfig) this.layoutConfig = {}
171
-
172
- if (y >= this.components.length) return
173
-
174
- // /* 생성 버튼이 클릭되면, 새로운 tabCard를 추가한다. */
175
- // if(y == this.components.length) {
176
- // this.add(Model.compile({
177
- // type: 'tab-card',
178
- // width: 100,
179
- // height: 100
180
- // }))
181
- // }
182
- this.setState('activeIndex', y)
183
- }
184
-
185
- onmousedown(e: MouseEvent) {
186
- this.__down_point = {
187
- x: e.offsetX,
188
- y: e.offsetY
189
- }
190
- }
191
-
192
- addCard() {
193
- const color = 255 - ((20 * (this.components.length + 1)) % 255)
194
- const hex = color.toString(16)
195
-
196
- const tabCard = Model.compile({
197
- type: 'tab-card',
198
- fillStyle: `#${hex}${hex}${hex}`,
199
- top: 0,
200
- left: 0,
201
- width: 100,
202
- height: 100
203
- })
204
-
205
- this.addComponent(tabCard)
206
- this.setState('activeIndex', this.components.length - 1)
207
- }
208
- }
209
-
210
- Component.register('tab-container', TabContainer)