@pictogrammers/components 0.5.15 → 0.5.18

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 (149) hide show
  1. package/package.json +1 -1
  2. package/pg/autocompleteItem/__examples__/basic/basic.html +3 -0
  3. package/pg/autocompleteItem/autocompleteItem.css +55 -0
  4. package/pg/autocompleteItem/autocompleteItem.html +1 -0
  5. package/pg/autocompleteItem/autocompleteItem.ts +65 -0
  6. package/pg/button/button.css +5 -0
  7. package/pg/buttonMenu/buttonMenu.ts +1 -1
  8. package/pg/inputCombobox/__examples__/basic/basic.ts +33 -0
  9. package/pg/inputCombobox/inputCombobox.ts +158 -0
  10. package/pg/inputCombobox/inputCombobox.ts.tmp.44252.751480cb81cc +158 -0
  11. package/pg/inputCombobox/inputCombobox.ts.tmp.44252.dcea847c40a8 +156 -0
  12. package/pg/inputPill/inputPill.html +6 -0
  13. package/pg/inputPill/inputPill.html.tmp.26852.84ac63f4c46f +6 -0
  14. package/pg/inputPill/inputPill.ts +41 -0
  15. package/pg/inputPills/__examples__/basic/basic.html +9 -0
  16. package/pg/inputPills/__examples__/basic/basic.html.tmp.26852.4771e4cad5b7 +9 -0
  17. package/pg/inputPills/__examples__/basic/basic.ts.tmp.26852.d8fe41df18bd +0 -0
  18. package/pg/inputPixelEditor/README.md +104 -69
  19. package/pg/inputPixelEditor/README.md.tmp.42596.658de5f0a6f5 +0 -0
  20. package/pg/inputPixelEditor/__examples__/basic/basic.ts +6 -5
  21. package/pg/inputPixelEditor/inputPixelEditor.ts +96 -24
  22. package/pg/inputPixelEditor/inputPixelEditor.ts.tmp.38516.96529dd82670 +1703 -0
  23. package/pg/inputPixelEditor/inputPixelEditor.ts.tmp.42596.48ecc3ad9c72 +1724 -0
  24. package/pg/inputPixelEditor/utils/bitmapToMask.ts +113 -79
  25. package/pg/inputPixelEditor/utils/getLassoPixels.ts +51 -0
  26. package/pg/inputSelect/inputSelect.ts +5 -1
  27. package/pg/inputText/README.md +6 -6
  28. package/pg/inputText/__examples__/basic/basic.ts +1 -1
  29. package/pg/inputText/inputText.css +2 -2
  30. package/pg/inputText copy/README.md +38 -0
  31. package/pg/inputText copy/inputText.css +41 -0
  32. package/pg/inputText copy/inputText.html +1 -0
  33. package/pg/inputText copy/inputText.spec.ts +59 -0
  34. package/pg/inputText copy/inputText.ts +67 -0
  35. package/pg/inputTextarea/README.md +39 -0
  36. package/pg/inputTextarea/__examples__/basic/basic.html +9 -0
  37. package/pg/inputTextarea/__examples__/basic/basic.ts +30 -0
  38. package/pg/inputTextarea/inputTextarea.ts +121 -0
  39. package/pg/inputTextarea copy/README.md +39 -0
  40. package/pg/inputTextarea copy/inputTextarea.css +41 -0
  41. package/pg/inputTextarea copy/inputTextarea.html +1 -0
  42. package/pg/inputTextarea copy/inputTextarea.spec.ts +59 -0
  43. package/pg/inputTextarea copy/inputTextarea.ts +79 -0
  44. package/pg/inputTextareaAutocomplete/README.md +70 -0
  45. package/pg/inputTextareaAutocomplete/__examples__/basic/basic.ts +67 -0
  46. package/pg/inputTextareaAutocomplete/inputTextareaAutocomplete.ts +267 -0
  47. package/pg/node/README.md +35 -0
  48. package/pg/node/__examples__/basic/basic.ts +34 -0
  49. package/pg/node/index.ts +3 -0
  50. package/pg/node/node.css +53 -0
  51. package/pg/node/node.html +5 -0
  52. package/pg/node/node.ts +270 -0
  53. package/pg/nodeEditorLink/nodeEditorLink.css +69 -0
  54. package/pg/nodeEditorLink/nodeEditorLink.css.tmp.1408.09e961fd0dcc +69 -0
  55. package/pg/nodeEditorLink/nodeEditorLink.html +9 -0
  56. package/pg/nodeEditorNumber/nodeEditorNumber.css +59 -0
  57. package/pg/nodeEditorNumber/nodeEditorNumber.ts +57 -0
  58. package/pg/nodeEditorRange/nodeEditorRange.css +23 -0
  59. package/pg/nodeEditorRange/nodeEditorRange.ts +69 -0
  60. package/pg/nodeEditorText/__examples__/basic/basic.html +9 -0
  61. package/pg/nodeEditorText/__examples__/basic/basic.ts +30 -0
  62. package/pg/nodeEditorText/nodeEditorText.css +17 -0
  63. package/pg/nodeEditorText/nodeEditorText.html +4 -0
  64. package/pg/nodeEditorText/nodeEditorText.ts +57 -0
  65. package/pg/nodeEditorText copy/README.md +35 -0
  66. package/pg/nodeEditorText copy/nodeEditorText.css +49 -0
  67. package/pg/nodeEditorText copy/nodeEditorText.html +4 -0
  68. package/pg/nodeEditorText copy/nodeEditorText.ts +50 -0
  69. package/pg/nodeEditorTextArray/nodeEditorTextArray.css +68 -0
  70. package/pg/nodeEditorTextArray/nodeEditorTextArray.html +9 -0
  71. package/pg/nodeEditorTextArray/nodeEditorTextArray.ts +162 -0
  72. package/pg/nodeEntry/nodeEntry.css +61 -0
  73. package/pg/nodeEntry/nodeEntry.ts +164 -0
  74. package/pg/nodeEntry/nodeEntry.ts.tmp.28724.dda67762bca5 +164 -0
  75. package/pg/nodeInputText/nodeInputText.css +75 -0
  76. package/pg/nodeInputText/nodeInputText.html +4 -0
  77. package/pg/nodeInputText/nodeInputText.ts +105 -0
  78. package/pg/nodeOutput/nodeOutput.css +32 -0
  79. package/pg/nodeResize/README.md +3 -0
  80. package/pg/nodeResize/THINKING.md +81 -0
  81. package/pg/nodeResize/THINKING.md.tmp.24812.99a70ba81062 +81 -0
  82. package/pg/nodeResize/basic/basic.ts +17 -0
  83. package/pg/nodeResize/dragUtil.ts +105 -0
  84. package/pg/nodeResize/dragUtil.ts.tmp.34372.787464c73309 +75 -0
  85. package/pg/nodeResize/nodeResize.css +187 -0
  86. package/pg/nodeResize/nodeResize.html +9 -0
  87. package/pg/nodeResize/nodeResize.ts +156 -0
  88. package/pg/nodes/README.md +177 -0
  89. package/pg/nodes/__examples__/basic/basic.html +33 -0
  90. package/pg/nodes/__examples__/basic/basic.ts +716 -0
  91. package/pg/nodes/__examples__/basic/exampleNodes.ts +129 -0
  92. package/pg/nodes/__examples__/basic/exampleScripts.ts +129 -0
  93. package/pg/nodes/__examples__/basic/keystore.ts +38 -0
  94. package/pg/nodes/executeInSandbox.ts +32 -0
  95. package/pg/nodes/index.ts +3 -0
  96. package/pg/nodes/nodes.css +69 -0
  97. package/pg/nodes/nodes.html +6 -0
  98. package/pg/nodes/nodes.ts +1240 -0
  99. package/pg/nodes copy/nodes.css +41 -0
  100. package/pg/nodes copy/nodes.html +1 -0
  101. package/pg/overlayContextMenu/__examples__/filter/filter.ts +87 -0
  102. package/pg/overlayContextMenu/overlayContextMenu.css +14 -0
  103. package/pg/overlayContextMenu/overlayContextMenu.html +4 -3
  104. package/pg/overlayContextMenu/overlayContextMenu.ts +6 -2
  105. package/pg/overlayContextMenu/overlayContextMenu.ts.tmp.37088.530ff1c0a321 +0 -0
  106. package/pg/overlayMenu/overlayMenu.css +3 -1
  107. package/pg/overlayMenu/overlayMenu.ts +11 -2
  108. package/pg/overlayMenu/overlayMenu.ts.tmp.44252.9bb22fd59ede +80 -0
  109. package/pg/overlaySelectMenu/overlaySelectMenu.css +2 -0
  110. package/pg/overlaySubMenu/overlaySubMenu.css +8 -6
  111. package/pg/poco/README.md +22 -0
  112. package/pg/poco/__examples__/basic/basic.html +11 -0
  113. package/pg/poco/__examples__/basic/basic.ts +95 -0
  114. package/pg/poco/__examples__/basic/examples.ts +258 -0
  115. package/pg/poco/__examples__/basic/myFont.ts +1300 -0
  116. package/pg/poco/index.ts +3 -0
  117. package/pg/poco/mockPoco.ts +640 -0
  118. package/pg/poco/poco.css +7 -0
  119. package/pg/poco/poco.html +1 -0
  120. package/pg/poco/poco.ts +75 -0
  121. package/pg/popover/README.md +47 -0
  122. package/pg/popover/__examples__/basic/basic.html +3 -0
  123. package/pg/popover/popover.html +3 -0
  124. package/pg/popover/popover.ts +44 -0
  125. package/pg/popoverAutocomplete/__examples__/basic/basic.html +4 -0
  126. package/pg/popoverAutocomplete/__examples__/basic/basic.ts +46 -0
  127. package/pg/popoverAutocomplete/popoverAutocomplete.css +25 -0
  128. package/pg/popoverAutocomplete/popoverAutocomplete.html +1 -0
  129. package/pg/popoverAutocomplete/popoverAutocomplete.ts +134 -0
  130. package/pg/popoverAutocompleteItem/popoverAutocompleteItem.css +69 -0
  131. package/pg/popoverAutocompleteItem/popoverAutocompleteItem.ts +90 -0
  132. package/pg/table/__examples__/basic/basic.ts +1 -0
  133. package/pg/tableCellFileLocal/tableCellFileLocal.html +3 -0
  134. package/pg/tableCellFileLocal/tableCellFileLocal.html.tmp.20484.68ee2e30710e +3 -0
  135. package/pg/tableCellFileLocal/tableCellFileLocal.ts +44 -0
  136. package/pg/tableCellSelect/tableCellSelect.html +3 -0
  137. package/pg/tableCellSelect/tableCellSelect.html.tmp.41808.99c1a6f14340 +3 -0
  138. package/pg/tableCellSelect/tableCellSelect.ts +51 -0
  139. package/pg/tree/__examples__/basic/basic.ts +12 -5
  140. package/pg/tree/tree.html +1 -1
  141. package/pg/tree/tree.ts +385 -227
  142. package/pg/tree/tree.ts.tmp.38376.07d376a04f41 +343 -0
  143. package/pg/tree/tree.ts.tmp.38376.2a04599ade9f +361 -0
  144. package/pg/tree/tree.ts.tmp.38376.6cb2c663d476 +0 -0
  145. package/pg/tree/tree.ts.tmp.38376.ac5af1aff2b0 +393 -0
  146. package/pg/tree/tree.ts.tmp.38376.ac9acfc4f95f +324 -0
  147. package/pg/treeItem/treeItem.ts +536 -558
  148. package/pg/treeItem/treeItem.ts.tmp.38376.145d3121d648 +530 -0
  149. package/pg/treeItem/treeItem.ts.tmp.38376.b5224d48e5c0 +0 -0
@@ -0,0 +1,41 @@
1
+ :host {
2
+ display: block;
3
+ font-family: var(--pg-font-family, system-ui);
4
+ }
5
+
6
+ [part=input] {
7
+ border: 1px solid var(--pg-input-text-border-color, #453C4F);
8
+ border-radius: 0.125rem;
9
+ padding-inline-start: var(--pg-input-text-padding-inline-start, var(--pg-input-text-padding-inline, 0.5rem));
10
+ padding-inline-end: var(--pg-input-text-padding-inline-end, var(--pg-input-text-padding-inline, 0.5rem));
11
+ padding-block-start: var(--pg-input-text-padding-block-start, var(--pg-input-text-padding-block, 0.25rem));
12
+ padding-block-end: var(--pg-input-text-padding-block-start, var(--pg-input-text-padding-block, 0.25rem));
13
+ font-family: var(--pg-input-text-font-family, var(--pg-font-family));
14
+ font-size: 1rem;
15
+ outline: none;
16
+ field-sizing: content;
17
+ min-width: calc(
18
+ 100%
19
+ - var(--pg-input-text-padding-inline-start, var(--pg-input-text-padding-inline, 0.5rem))
20
+ - var(--pg-input-text-padding-inline-end, var(--pg-input-text-padding-inline, 0.5rem))
21
+ - 2px
22
+ );
23
+ max-width: calc(
24
+ var(--pg-input-text-max-width, 100%)
25
+ - var(--pg-input-text-padding-inline-start, var(--pg-input-text-padding-inline, 0.5rem))
26
+ - var(--pg-input-text-padding-inline-end, var(--pg-input-text-padding-inline, 0.5rem))
27
+ - 2px
28
+ );
29
+ background-color: transparent;
30
+ }
31
+
32
+ [part=input]:read-only {
33
+ border-color: transparent;
34
+ }
35
+
36
+ [part=input]:active {
37
+ box-shadow: 0 0 0 3px var(--pg-input-text-active-glow, rgb(79, 143, 249, 0.6));
38
+ }
39
+ [part=input]:focus {
40
+ box-shadow: 0 0 0 3px var(--pg-input-text-focus-glow, rgb(79, 143, 249, 0.5));
41
+ }
@@ -0,0 +1 @@
1
+ <div part="items"></div>
@@ -0,0 +1,87 @@
1
+ import { Component, Part, Prop } from '@pictogrammers/element';
2
+
3
+ import PgMenuItemIcon from '../../../menuItemIcon/menuItemIcon';
4
+ import PgMenuDivider from '../../../menuDivider/menuDivider';
5
+ import PgOverlayContextMenu from '../../overlayContextMenu';
6
+
7
+ import template from './filter.html';
8
+ import style from './filter.css';
9
+ import PgMenuItem from 'components/pg/menuItem/menuItem';
10
+
11
+ @Component({
12
+ selector: 'x-pg-overlay-context-menu-filter',
13
+ template,
14
+ style
15
+ })
16
+ export default class XPgOverlayContextMenuFilter extends HTMLElement {
17
+ @Part() $area: HTMLDivElement;
18
+ @Part() $result: HTMLSpanElement;
19
+
20
+ connectedCallback() {
21
+ this.$area.addEventListener('contextmenu', this.#handleContextMenu.bind(this));
22
+ }
23
+
24
+ #value = null;
25
+
26
+ async #handleContextMenu(e: MouseEvent) {
27
+ e.preventDefault();
28
+ const items = [{
29
+ label: 'Add File',
30
+ value: 'addFile',
31
+ type: PgMenuItem,
32
+ },
33
+ {
34
+ label: 'Add Folder',
35
+ value: 'addFolder',
36
+ type: PgMenuItem,
37
+ },
38
+ {
39
+ type: PgMenuDivider
40
+ },
41
+ {
42
+ label: 'Copy',
43
+ value: 'copy',
44
+ type: PgMenuItem,
45
+ },
46
+ {
47
+ label: 'Paste',
48
+ value: 'paste',
49
+ type: PgMenuItem,
50
+ },
51
+ {
52
+ label: 'Rename',
53
+ value: 'rename',
54
+ type: PgMenuItem,
55
+ },
56
+ {
57
+ label: 'Delete',
58
+ value: 'delete',
59
+ type: PgMenuItem,
60
+ },
61
+ {
62
+ type: PgMenuDivider
63
+ },
64
+ {
65
+ label: 'Refresh',
66
+ value: 'refresh',
67
+ type: PgMenuItem,
68
+ },
69
+ {
70
+ label: 'Download',
71
+ value: 'download',
72
+ type: PgMenuItem,
73
+ }];
74
+ const result = await PgOverlayContextMenu.open({
75
+ source: this.$area,
76
+ x: e.clientX,
77
+ y: e.clientY,
78
+ value: this.#value,
79
+ filter: true,
80
+ items
81
+ });
82
+ if (result !== undefined) {
83
+ this.#value = result;
84
+ }
85
+ this.$result.textContent = JSON.stringify(result);
86
+ }
87
+ }
@@ -13,4 +13,18 @@
13
13
  left: anchor(left);
14
14
  min-width: 10rem;
15
15
  margin: var(--pg-overlay-menu-_y, 0) 0 0 var(--pg-overlay-menu-_x, 0);
16
+ position-visibility: always;
17
+ position-anchor: auto;
18
+ }
19
+
20
+ [part="filter"] {
21
+ display: none;
22
+ --pg-input-border-radius: 0.5rem;
23
+ }
24
+
25
+ [part="overlay"].filter [part="filter"] {
26
+ display: block;
27
+ margin-bottom: 0.25rem;
28
+ border-radius: 0.5rem;
29
+ box-shadow: var(--pg-menu-box-shadow, none);
16
30
  }
@@ -1,3 +1,4 @@
1
- <div part="overlay">
2
- <pg-menu part="menu"></pg-menu>
3
- </div>
1
+ <div part="overlay">
2
+ <pg-input-text part="filter" placeholder="Filter"></pg-input-text>
3
+ <pg-menu part="menu"></pg-menu>
4
+ </div>
@@ -1,5 +1,6 @@
1
1
  import { Component, Part, Prop } from '@pictogrammers/element';
2
2
 
3
+ import PgInputText from '../inputText/inputText';
3
4
  import PgMenu from '../menu/menu';
4
5
  import PgOverlay from '../overlay/overlay';
5
6
 
@@ -57,11 +58,14 @@ export default class PgOverlayContextMenu extends PgOverlay {
57
58
  // ToDo: update to CSS Variables
58
59
  this.$overlay.style.setProperty('--pg-overlay-menu-_x', `${x}px`);
59
60
  this.$overlay.style.setProperty('--pg-overlay-menu-_y', `${y}px`);
60
- // Focus
61
- this.$menu.focus(0);
62
61
  // Should return focus
63
62
  this.#handleDown = this.#down.bind(this);
64
63
  document.addEventListener('pointerdown', this.#handleDown);
64
+ // Rendering children is after parent's connectedCallback
65
+ queueMicrotask(() => {
66
+ // Focus
67
+ this.$menu.focus(0);
68
+ });
65
69
  }
66
70
 
67
71
  #ignore = false;
@@ -8,9 +8,11 @@
8
8
  border: 0;
9
9
  background: transparent;
10
10
  --pg-menu-box-shadow: 0 0.125rem 0.5rem rgba(0, 0, 0, 0.25);
11
- top: calc(anchor(bottom) - 0.25rem);
11
+ top: calc(anchor(bottom) - 1px);
12
12
  left: anchor(left);
13
13
  min-width: calc(anchor-size(width) + calc(2 * var(--pg-menu-padding, 0.25rem)));
14
14
  translate: var(--pg-overlay-menu-_x, 0) var(--pg-overlay-menu-_y, 0);
15
15
  overflow: visible;
16
+ position-visibility: always;
17
+ position-anchor: auto;
16
18
  }
@@ -19,6 +19,7 @@ export default class PgOverlayMenu extends PgOverlay {
19
19
  @Prop() default: any = null;
20
20
  @Prop() items: any[] = [];
21
21
  @Prop() value: any = null;
22
+ @Prop() preventFocus: boolean = false;
22
23
 
23
24
  render(changes) {
24
25
 
@@ -27,11 +28,12 @@ export default class PgOverlayMenu extends PgOverlay {
27
28
  connectedCallback() {
28
29
  this.$menu.items = this.items;
29
30
  this.$menu.addEventListener('select', this.#handleSelect.bind(this));
31
+ this.$menu.addEventListener('close', this.#handleMenuClose.bind(this));
30
32
  this.$overlay.popover = 'auto';
31
33
  if (this.source !== null) {
32
34
  // @ts-ignore
33
35
  this.$overlay.showPopover({
34
- source: this.source
36
+ source: this.source,
35
37
  });
36
38
  }
37
39
  this.$overlay.addEventListener('toggle', this.#toggle.bind(this));
@@ -46,7 +48,9 @@ export default class PgOverlayMenu extends PgOverlay {
46
48
  ? 0
47
49
  : this.items.findIndex(x => x.value === value);
48
50
  // Focus
49
- this.$menu.focus(index);
51
+ if (!this.preventFocus) {
52
+ this.$menu.focus(index);
53
+ }
50
54
  }
51
55
 
52
56
  #toggle(e: ToggleEvent) {
@@ -68,4 +72,9 @@ export default class PgOverlayMenu extends PgOverlay {
68
72
  });
69
73
  this.source?.focus();
70
74
  }
75
+
76
+ #handleMenuClose() {
77
+ this.close();
78
+ this.source?.focus();
79
+ }
71
80
  }
@@ -0,0 +1,80 @@
1
+ import { Component, Part, Prop } from '@pictogrammers/element';
2
+
3
+ import PgMenu from '../menu/menu';
4
+ import PgOverlay from '../overlay/overlay';
5
+
6
+ import template from './overlayMenu.html';
7
+ import style from './overlayMenu.css';
8
+
9
+ @Component({
10
+ selector: 'pg-overlay-menu',
11
+ template,
12
+ style
13
+ })
14
+ export default class PgOverlayMenu extends PgOverlay {
15
+ @Part() $overlay: HTMLDivElement;
16
+ @Part() $menu: PgMenu;
17
+
18
+ @Prop() source: HTMLElement | null = null;
19
+ @Prop() default: any = null;
20
+ @Prop() items: any[] = [];
21
+ @Prop() value: any = null;
22
+ @Prop() preventFocus: boolean = false;
23
+
24
+ render(changes) {
25
+
26
+ }
27
+
28
+ connectedCallback() {
29
+ this.$menu.items = this.items;
30
+ this.$menu.addEventListener('select', this.#handleSelect.bind(this));
31
+ this.$menu.addEventListener('close', this.#handleMenuClose.bind(this));
32
+ this.$overlay.popover = 'auto';
33
+ if (this.source !== null) {
34
+ // @ts-ignore
35
+ this.$overlay.showPopover({
36
+ source: this.source
37
+ });
38
+ }
39
+ this.$overlay.addEventListener('toggle', this.#toggle.bind(this));
40
+ // Position
41
+ const rect = this.source?.getBoundingClientRect();
42
+ let x = 0, y = 0;
43
+ const value = this.value === null || typeof this.value !== 'object'
44
+ ? this.value
45
+ : this.value.value;
46
+ // value is an item in the items list
47
+ const index = this.value === null
48
+ ? 0
49
+ : this.items.findIndex(x => x.value === value);
50
+ // Focus
51
+ if (!this.preventFocus) {
52
+ this.$menu.focus(index);
53
+ }
54
+ }
55
+
56
+ #toggle(e: ToggleEvent) {
57
+ if (e.newState === 'closed') {
58
+ this.close();
59
+ this.source?.focus();
60
+ }
61
+ }
62
+
63
+ disconnectedCallback() {
64
+ }
65
+
66
+ #handleSelect(e: any) {
67
+ // e.detail.item.index = e.detail.index;
68
+ const { indexes, item } = e.detail;
69
+ this.close({
70
+ indexes,
71
+ item
72
+ });
73
+ this.source?.focus();
74
+ }
75
+
76
+ #handleMenuClose() {
77
+ this.close();
78
+ this.source?.focus();
79
+ }
80
+ }
@@ -14,4 +14,6 @@
14
14
  min-width: calc(anchor-size(width) + calc(2 * var(--pg-menu-padding, 0.25rem)));
15
15
  margin: var(--pg-overlay-menu-_y, 0) 0 0 var(--pg-overlay-menu-_x, 0);
16
16
  overflow: visible;
17
+ position-visibility: always;
18
+ position-anchor: auto;
17
19
  }
@@ -9,18 +9,20 @@
9
9
  background: transparent;
10
10
  overflow: visible;
11
11
  --pg-menu-box-shadow: 0 0.125rem 0.5rem rgba(0, 0, 0, 0.25);
12
- top: calc(anchor(top) - 0.25rem);
13
- left: calc(anchor(right) - 0.25rem);
12
+ top: calc(anchor(top) - 0.25rem - 1px);
13
+ left: calc(anchor(right) - 0.125rem - 1px);
14
14
  translate: var(--pg-overlay-menu-_x, 0) var(--pg-overlay-menu-_y, 0);
15
15
  position-try-fallbacks: --custom-right, --custom-left;
16
+ position-visibility: always;
17
+ position-anchor: auto;
16
18
  }
17
19
 
18
20
  @position-try --custom-right {
19
- top: calc(anchor(top) - 0.25rem);
20
- left: calc(anchor(right) - 0.25rem);
21
+ top: calc(anchor(top) - 0.25rem - 1px);
22
+ left: calc(anchor(right) - 0.125rem - 1px);
21
23
  }
22
24
 
23
25
  @position-try --custom-left {
24
- top: calc(anchor(top) - 0.25rem);
25
- left: calc(anchor(left) - anchor-size(width) + 0.25rem);
26
+ top: calc(anchor(top) - 0.25rem - 1px);
27
+ left: calc(anchor(left) - anchor-size(width) + 0.25rem - 1px);
26
28
  }
@@ -0,0 +1,22 @@
1
+ # `<pg-poco>`
2
+
3
+ The `<pg-poco>` component allows creating an emulator that simulates the draw commands for the Moddable SDK.
4
+
5
+ ## Usage
6
+
7
+ See the demo for examples.
8
+
9
+ ## Timer
10
+
11
+ Equivalent to `setInterval`.
12
+
13
+ ```typescript
14
+ const id = Timer.set(() => {
15
+
16
+ // delay, interval
17
+ }, 1000, 1000);
18
+
19
+ // Timer.clear(id);
20
+ ```
21
+
22
+ For `setTimeout` leave off the `interval` value or set it to `0`.
@@ -0,0 +1,11 @@
1
+ <div class="example">
2
+ <div style="box-shadow: 0 0.0625rem 0.25rem rgba(0, 0, 0, 0.3);width:min-content;margin-bottom: 0.5rem;display: flex;">
3
+ <pg-poco part="poco"></pg-poco>
4
+ </div>
5
+ <label>Demo:
6
+ <select part="list"></select>
7
+ </label>
8
+ <textarea part="code" rows="20" spellcheck="false" style="margin-top:0.5rem;width:calc(100% - 1rem);padding:0.5rem;border-radius:0.5rem;"></textarea>
9
+ <button part="run">Run</button>
10
+ <pre part="error" style="padding: 0.5rem;border: 1px solid rgb(128 0 0);border-radius: 0.25rem;background: rgba(128, 0, 0, 0.1);"></pre>
11
+ </div>
@@ -0,0 +1,95 @@
1
+ import { Component, Part } from '@pictogrammers/element';
2
+
3
+ import PgPoco from '../../poco';
4
+ import { demos } from './examples';
5
+
6
+ import template from './basic.html';
7
+ import { mockCharmanderBMP, mockMyFont, mockMyFontBMP } from './myFont';
8
+
9
+ function dedent(str) {
10
+ const lines = str.split("\n");
11
+ const nonEmpty = lines.filter(l => l.trim().length > 0);
12
+ if (!nonEmpty.length) return str.trim();
13
+ const minIndent = Math.min(...nonEmpty.map(l => l.match(/^(\s*)/)[1].length));
14
+ return lines.map(l => l.slice(minIndent)).join("\n").trim();
15
+ }
16
+
17
+ @Component({
18
+ selector: 'x-pg-poco-basic',
19
+ template,
20
+ })
21
+ export default class XPgPocoBasic extends HTMLElement {
22
+ @Part() $poco: PgPoco;
23
+ @Part() $list: HTMLSelectElement;
24
+ @Part() $code: HTMLTextAreaElement;
25
+ @Part() $run: HTMLButtonElement;
26
+ @Part() $error: HTMLPreElement;
27
+
28
+ connectedCallback() {
29
+ demos.forEach((demo: any, index: number) => {
30
+ const newOption = new Option(demo.label, `${index}`);
31
+ this.$list.add(newOption);
32
+ });
33
+ this.$list.addEventListener('change', (e: any) => {
34
+ this.$code.value = dedent(demos[e.target.value].run);
35
+ });
36
+ this.$poco.height = 400;
37
+ this.$poco.height = 240;
38
+ this.$code.value = dedent(demos[0].run);
39
+ this.$run.addEventListener('click', this.handleRun.bind(this));
40
+ this.$error.style.display = 'none';
41
+ // Resources
42
+ this.$poco.setResourceBMPCanvas('colorBitmap.bmp', 40, 40, (ctx, w, h) => {
43
+ ctx.fillStyle = "#fff"; ctx.fillRect(0, 0, w, h);
44
+ ctx.fillStyle = "#000"; ctx.fillRect(4, 4, 32, 32);
45
+ ctx.fillStyle = "#fff"; ctx.fillRect(8, 8, 24, 24);
46
+ ctx.fillStyle = "#000"; ctx.fillRect(12, 12, 16, 16);
47
+ ctx.fillStyle = "#fff"; ctx.fillRect(16, 16, 8, 8);
48
+ });
49
+ this.$poco.setResourceBMPCanvas('monoBitmap.bmp', 32, 32, (ctx, w, h) => {
50
+ ctx.fillStyle = "#fff"; ctx.fillRect(0, 0, w, h);
51
+ ctx.strokeStyle = "#000"; ctx.lineWidth = 1;
52
+ ctx.strokeRect(0.5, 0.5, w - 1, h - 1);
53
+ ctx.beginPath(); ctx.moveTo(0, 0); ctx.lineTo(w / 2, h / 2); ctx.lineTo(w, 0); ctx.stroke();
54
+ ctx.beginPath(); ctx.moveTo(0, h); ctx.lineTo(w / 2, h / 2); ctx.lineTo(w, h); ctx.stroke();
55
+ });
56
+ this.$poco.setResourceBMPCanvas('grayBitmap.bmp', 32, 32, (ctx, w, h) => {
57
+ const grad = ctx.createRadialGradient(w / 2, h / 2, 2, w / 2, h / 2, w / 2);
58
+ grad.addColorStop(0, "#fff");
59
+ grad.addColorStop(1, "#000");
60
+ ctx.fillStyle = grad;
61
+ ctx.fillRect(0, 0, w, h);
62
+ });
63
+ this.$poco.setResourceBMPCanvas('circleMask.bmp', 40, 40, (ctx, w, h) => {
64
+ ctx.fillStyle = "#000"; ctx.fillRect(0, 0, w, h);
65
+ const grad = ctx.createRadialGradient(w / 2, h / 2, 0, w / 2, h / 2, w / 2);
66
+ grad.addColorStop(0, "#fff");
67
+ grad.addColorStop(1, "#000");
68
+ ctx.fillStyle = grad;
69
+ ctx.beginPath(); ctx.arc(w / 2, h / 2, w / 2, 0, Math.PI * 2); ctx.fill();
70
+ });
71
+ this.$poco.setResourceBMPCanvas('patternBitmap.bmp', 30, 30, (ctx, w, h) => {
72
+ const size = 10;
73
+ for (let r = 0; r < h; r += size)
74
+ for (let c = 0; c < w; c += size) {
75
+ ctx.fillStyle = ((r + c) / size % 2 === 0) ? "#000" : "#fff";
76
+ ctx.fillRect(c, r, size, size);
77
+ }
78
+ });
79
+ // Charmander
80
+ this.$poco.setResourceBMP('charmander.png', mockCharmanderBMP);
81
+ // Resources - Font
82
+ this.$poco.setResourceBMP('myFont.png', mockMyFontBMP);
83
+ this.$poco.setResourceBMFJSON('myFont.fnt', mockMyFont);
84
+ // Error handler
85
+ this.$poco.addEventListener('error', (e: any) => {
86
+ this.$error.textContent = e.detail.message;
87
+ this.$error.style.display = "block";
88
+ });
89
+ }
90
+
91
+ handleRun() {
92
+ this.$error.style.display = "none";
93
+ this.$poco.run(this.$code.value);
94
+ }
95
+ }