@bpmn-io/properties-panel 1.6.2 → 1.7.0

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.
@@ -457,6 +457,7 @@
457
457
  background-color: transparent;
458
458
  }
459
459
 
460
+ .bio-properties-panel-feelers-editor .cm-editor.cm-focused,
460
461
  .bio-properties-panel-feelers-input .cm-editor.cm-focused {
461
462
  outline: none;
462
463
  }
@@ -1013,10 +1014,6 @@ textarea.bio-properties-panel-input {
1013
1014
  min-height: 28px;
1014
1015
  }
1015
1016
 
1016
- .bio-properties-panel-feel-container .cm-scroller {
1017
- overflow: hidden !important;
1018
- }
1019
-
1020
1017
  .bio-properties-panel-feel-indicator {
1021
1018
  position: absolute;
1022
1019
  border: 1px solid var(--input-border-color);
@@ -1030,6 +1027,18 @@ textarea.bio-properties-panel-input {
1030
1027
  padding: 2px 6px;
1031
1028
  }
1032
1029
 
1030
+ .bio-properties-panel-feel-editor-container .cm-scroller {
1031
+ overflow: hidden !important;
1032
+ }
1033
+
1034
+ .bio-properties-panel-feelers-editor .cm-editor {
1035
+ background-color: transparent;
1036
+ }
1037
+
1038
+ .bio-properties-panel-feelers-editor .cm-editor.cm-focused {
1039
+ background-color: transparent;
1040
+ }
1041
+
1033
1042
  .bio-properties-panel-feel-editor-container .bio-properties-panel-input {
1034
1043
  resize: vertical;
1035
1044
  overflow: hidden;
package/dist/index.esm.js CHANGED
@@ -1,12 +1,12 @@
1
- import { useContext, useRef, useEffect, useMemo, useState, useCallback, useLayoutEffect } from '../preact/hooks';
1
+ import { useContext, useRef, useEffect, useMemo, useCallback, useState, useLayoutEffect } from '../preact/hooks';
2
2
  import { isFunction, isArray, get, assign, set, sortBy, find, isNumber, debounce } from 'min-dash';
3
3
  import classnames from 'classnames';
4
4
  import { forwardRef } from '../preact/compat';
5
5
  import { jsx, jsxs } from '../preact/jsx-runtime';
6
6
  import { query } from 'min-dom';
7
7
  import { createContext, createElement } from '../preact';
8
- import FeelEditor from '@bpmn-io/feel-editor';
9
8
  import { FeelersEditor } from 'feelers';
9
+ import FeelEditor from '@bpmn-io/feel-editor';
10
10
 
11
11
  var ArrowIcon = function ArrowIcon(props) {
12
12
  return jsx("svg", {
@@ -310,15 +310,10 @@ function useLayoutState(path, defaultValue) {
310
310
  setLayoutForKey
311
311
  } = useContext(LayoutContext);
312
312
  const layoutForKey = getLayoutForKey(path, defaultValue);
313
- const [value, set] = useState(layoutForKey);
314
- const setState = newValue => {
315
- // (1) set component state
316
- set(newValue);
317
-
318
- // (2) set context
313
+ const setState = useCallback(newValue => {
319
314
  setLayoutForKey(path, newValue);
320
- };
321
- return [value, setState];
315
+ }, [setLayoutForKey]);
316
+ return [layoutForKey, setState];
322
317
  }
323
318
 
324
319
  /**
@@ -634,15 +629,21 @@ function PropertiesPanel(props) {
634
629
  headerProvider,
635
630
  placeholderProvider,
636
631
  groups,
637
- layoutConfig = {},
632
+ layoutConfig,
638
633
  layoutChanged,
639
- descriptionConfig = {},
634
+ descriptionConfig,
640
635
  descriptionLoaded,
641
636
  eventBus
642
637
  } = props;
643
638
 
644
639
  // set-up layout context
645
640
  const [layout, setLayout] = useState(createLayout(layoutConfig));
641
+
642
+ // react to external changes in the layout config
643
+ useUpdateEffect(() => {
644
+ const newLayout = createLayout(layoutConfig);
645
+ setLayout(newLayout);
646
+ }, [layoutConfig]);
646
647
  useEffect(() => {
647
648
  if (typeof layoutChanged === 'function') {
648
649
  layoutChanged(layout);
@@ -664,10 +665,12 @@ function PropertiesPanel(props) {
664
665
  };
665
666
 
666
667
  // set-up description context
667
- const description = createDescriptionContext(descriptionConfig);
668
- if (typeof descriptionLoaded === 'function') {
669
- descriptionLoaded(description);
670
- }
668
+ const description = useMemo(() => createDescriptionContext(descriptionConfig), [descriptionConfig]);
669
+ useEffect(() => {
670
+ if (typeof descriptionLoaded === 'function') {
671
+ descriptionLoaded(description);
672
+ }
673
+ }, [description, descriptionLoaded]);
671
674
  const getDescriptionForId = (id, element) => {
672
675
  return description[id] && description[id](element);
673
676
  };
@@ -742,19 +745,38 @@ function PropertiesPanel(props) {
742
745
 
743
746
  // helpers //////////////////
744
747
 
745
- function createLayout(overrides) {
748
+ function createLayout(overrides = {}, defaults = DEFAULT_LAYOUT) {
746
749
  return {
747
- ...DEFAULT_LAYOUT,
750
+ ...defaults,
748
751
  ...overrides
749
752
  };
750
753
  }
751
- function createDescriptionContext(overrides) {
754
+ function createDescriptionContext(overrides = {}) {
752
755
  return {
753
756
  ...DEFAULT_DESCRIPTION,
754
757
  ...overrides
755
758
  };
756
759
  }
757
760
 
761
+ // hooks //////////////////
762
+
763
+ /**
764
+ * This hook behaves like useEffect, but does not trigger on the first render.
765
+ *
766
+ * @param {Function} effect
767
+ * @param {Array} deps
768
+ */
769
+ function useUpdateEffect(effect, deps) {
770
+ const isMounted = useRef(false);
771
+ useEffect(() => {
772
+ if (isMounted.current) {
773
+ return effect();
774
+ } else {
775
+ isMounted.current = true;
776
+ }
777
+ }, deps);
778
+ }
779
+
758
780
  function DropdownButton(props) {
759
781
  const {
760
782
  class: className,
@@ -1289,6 +1311,88 @@ const useBufferedFocus$1 = function (editor, ref) {
1289
1311
  }, [editor, buffer]);
1290
1312
  };
1291
1313
  const CodeEditor$1 = forwardRef((props, ref) => {
1314
+ const {
1315
+ onInput,
1316
+ disabled,
1317
+ tooltipContainer,
1318
+ enableGutters,
1319
+ value,
1320
+ onLint = () => {},
1321
+ contentAttributes = {},
1322
+ hostLanguage = null,
1323
+ singleLine = false
1324
+ } = props;
1325
+ const inputRef = useRef();
1326
+ const [editor, setEditor] = useState();
1327
+ const [localValue, setLocalValue] = useState(value || '');
1328
+ useBufferedFocus$1(editor, ref);
1329
+ const handleInput = useStaticCallback(newValue => {
1330
+ onInput(newValue);
1331
+ setLocalValue(newValue);
1332
+ });
1333
+ useEffect(() => {
1334
+ let editor;
1335
+ editor = new FeelersEditor({
1336
+ container: inputRef.current,
1337
+ onChange: handleInput,
1338
+ value: localValue,
1339
+ onLint,
1340
+ contentAttributes,
1341
+ tooltipContainer,
1342
+ enableGutters,
1343
+ hostLanguage,
1344
+ singleLine
1345
+ });
1346
+ setEditor(editor);
1347
+ return () => {
1348
+ onLint([]);
1349
+ inputRef.current.innerHTML = '';
1350
+ setEditor(null);
1351
+ };
1352
+ }, []);
1353
+ useEffect(() => {
1354
+ if (!editor) {
1355
+ return;
1356
+ }
1357
+ if (value === localValue) {
1358
+ return;
1359
+ }
1360
+ editor.setValue(value);
1361
+ setLocalValue(value);
1362
+ }, [value]);
1363
+ const handleClick = () => {
1364
+ ref.current.focus();
1365
+ };
1366
+ return jsx("div", {
1367
+ name: props.name,
1368
+ class: classnames('bio-properties-panel-feelers-editor bio-properties-panel-input', localValue ? 'edited' : null, disabled ? 'disabled' : null),
1369
+ ref: inputRef,
1370
+ onClick: handleClick
1371
+ });
1372
+ });
1373
+
1374
+ const useBufferedFocus = function (editor, ref) {
1375
+ const [buffer, setBuffer] = useState(undefined);
1376
+ ref.current = useMemo(() => ({
1377
+ focus: offset => {
1378
+ if (editor) {
1379
+ editor.focus(offset);
1380
+ } else {
1381
+ if (typeof offset === 'undefined') {
1382
+ offset = Infinity;
1383
+ }
1384
+ setBuffer(offset);
1385
+ }
1386
+ }
1387
+ }), [editor]);
1388
+ useEffect(() => {
1389
+ if (typeof buffer !== 'undefined' && editor) {
1390
+ editor.focus(buffer);
1391
+ setBuffer(false);
1392
+ }
1393
+ }, [editor, buffer]);
1394
+ };
1395
+ const CodeEditor = forwardRef((props, ref) => {
1292
1396
  const {
1293
1397
  value,
1294
1398
  onInput,
@@ -1301,7 +1405,7 @@ const CodeEditor$1 = forwardRef((props, ref) => {
1301
1405
  const inputRef = useRef();
1302
1406
  const [editor, setEditor] = useState();
1303
1407
  const [localValue, setLocalValue] = useState(value || '');
1304
- useBufferedFocus$1(editor, ref);
1408
+ useBufferedFocus(editor, ref);
1305
1409
  const handleInput = useStaticCallback(newValue => {
1306
1410
  onInput(newValue);
1307
1411
  setLocalValue(newValue);
@@ -1557,7 +1661,7 @@ function FeelTextfield(props) {
1557
1661
  active: feelActive,
1558
1662
  disabled: feel !== 'optional' || disabled,
1559
1663
  onClick: handleFeelToggle
1560
- }), feelActive ? jsx(CodeEditor$1, {
1664
+ }), feelActive ? jsx(CodeEditor, {
1561
1665
  id: prefixId$6(id),
1562
1666
  name: id,
1563
1667
  onInput: handleLocalInput,
@@ -1574,6 +1678,9 @@ function FeelTextfield(props) {
1574
1678
  }) : jsx(OptionalComponent, {
1575
1679
  ...props,
1576
1680
  onInput: handleLocalInput,
1681
+ contentAttributes: {
1682
+ 'id': prefixId$6(id)
1683
+ },
1577
1684
  value: localValue,
1578
1685
  ref: editorRef
1579
1686
  })]
@@ -1694,6 +1801,8 @@ function FeelEntry(props) {
1694
1801
  getValue,
1695
1802
  setValue,
1696
1803
  tooltipContainer,
1804
+ hostLanguage,
1805
+ singleLine,
1697
1806
  validate,
1698
1807
  show = noop$1,
1699
1808
  example,
@@ -1749,6 +1858,8 @@ function FeelEntry(props) {
1749
1858
  onFocus: onFocus,
1750
1859
  onBlur: onBlur,
1751
1860
  example: example,
1861
+ hostLanguage: hostLanguage,
1862
+ singleLine: singleLine,
1752
1863
  show: show,
1753
1864
  value: value,
1754
1865
  variables: variables,
@@ -1784,13 +1895,42 @@ function FeelEntry(props) {
1784
1895
  * @param {Function} props.onFocus
1785
1896
  * @param {Function} props.onBlur
1786
1897
  */
1787
- function FeelTextArea(props) {
1898
+ function FeelTextAreaEntry(props) {
1788
1899
  return jsx(FeelEntry, {
1789
1900
  class: "bio-properties-panel-feel-textarea",
1790
1901
  OptionalComponent: OptionalFeelTextArea,
1791
1902
  ...props
1792
1903
  });
1793
1904
  }
1905
+
1906
+ /**
1907
+ * @param {Object} props
1908
+ * @param {Object} props.element
1909
+ * @param {String} props.id
1910
+ * @param {String} props.description
1911
+ * @param {String} props.hostLanguage
1912
+ * @param {Boolean} props.singleLine
1913
+ * @param {Boolean} props.debounce
1914
+ * @param {Boolean} props.disabled
1915
+ * @param {Boolean} props.feel
1916
+ * @param {String} props.label
1917
+ * @param {Function} props.getValue
1918
+ * @param {Function} props.setValue
1919
+ * @param {Function} props.tooltipContainer
1920
+ * @param {Function} props.validate
1921
+ * @param {Function} props.show
1922
+ * @param {Function} props.example
1923
+ * @param {Function} props.variables
1924
+ * @param {Function} props.onFocus
1925
+ * @param {Function} props.onBlur
1926
+ */
1927
+ function FeelTemplatingEntry(props) {
1928
+ return jsx(FeelEntry, {
1929
+ class: "bio-properties-panel-feel-templating",
1930
+ OptionalComponent: CodeEditor$1,
1931
+ ...props
1932
+ });
1933
+ }
1794
1934
  function isEdited$7(node) {
1795
1935
  return node && (!!node.value || node.classList.contains('edited'));
1796
1936
  }
@@ -1801,86 +1941,6 @@ function prefixId$6(id) {
1801
1941
  return `bio-properties-panel-${id}`;
1802
1942
  }
1803
1943
 
1804
- const useBufferedFocus = function (editor, ref) {
1805
- const [buffer, setBuffer] = useState(undefined);
1806
- ref.current = useMemo(() => ({
1807
- focus: offset => {
1808
- if (editor) {
1809
- editor.focus(offset);
1810
- } else {
1811
- if (typeof offset === 'undefined') {
1812
- offset = Infinity;
1813
- }
1814
- setBuffer(offset);
1815
- }
1816
- }
1817
- }), [editor]);
1818
- useEffect(() => {
1819
- if (typeof buffer !== 'undefined' && editor) {
1820
- editor.focus(buffer);
1821
- setBuffer(false);
1822
- }
1823
- }, [editor, buffer]);
1824
- };
1825
- const CodeEditor = forwardRef((props, ref) => {
1826
- const {
1827
- value,
1828
- onInput,
1829
- onLint = () => {},
1830
- contentAttributes = {},
1831
- disabled,
1832
- tooltipContainer,
1833
- useGutters = false,
1834
- darkMode = false
1835
- } = props;
1836
- const inputRef = useRef();
1837
- const [editor, setEditor] = useState();
1838
- const [localValue, setLocalValue] = useState(value || '');
1839
- useBufferedFocus(editor, ref);
1840
- const handleInput = useStaticCallback(newValue => {
1841
- onInput(newValue);
1842
- setLocalValue(newValue);
1843
- });
1844
- useEffect(() => {
1845
- let editor;
1846
- editor = new FeelersEditor({
1847
- container: inputRef.current,
1848
- onChange: handleInput,
1849
- onLint: onLint,
1850
- contentAttributes: contentAttributes,
1851
- tooltipContainer: tooltipContainer,
1852
- value: localValue,
1853
- darkMode: darkMode,
1854
- enableGutters: useGutters
1855
- });
1856
- setEditor(editor);
1857
- return () => {
1858
- onLint([]);
1859
- inputRef.current.innerHTML = '';
1860
- setEditor(null);
1861
- };
1862
- }, []);
1863
- useEffect(() => {
1864
- if (!editor) {
1865
- return;
1866
- }
1867
- if (value === localValue) {
1868
- return;
1869
- }
1870
- editor.setValue(value);
1871
- setLocalValue(value);
1872
- }, [value]);
1873
- const handleClick = () => {
1874
- ref.current.focus();
1875
- };
1876
- return jsx("div", {
1877
- name: props.name,
1878
- class: classnames('bio-properties-panel-feelers-editor bio-properties-panel-input', localValue ? 'edited' : null, disabled ? 'disabled' : null),
1879
- ref: inputRef,
1880
- onClick: handleClick
1881
- });
1882
- });
1883
-
1884
1944
  const noop = () => {};
1885
1945
 
1886
1946
  /**
@@ -1897,7 +1957,7 @@ const noop = () => {};
1897
1957
  * @param {Function} props.validate
1898
1958
  * @param {Function} props.show
1899
1959
  */
1900
- function FeelTemplatingEntry(props) {
1960
+ function TemplatingEntry(props) {
1901
1961
  const {
1902
1962
  element,
1903
1963
  id,
@@ -1948,7 +2008,7 @@ function FeelTemplatingEntry(props) {
1948
2008
  return jsxs("div", {
1949
2009
  class: classnames('bio-properties-panel-entry', error ? 'has-error' : ''),
1950
2010
  "data-entry-id": id,
1951
- children: [jsx(FeelTemplating, {
2011
+ children: [jsx(Templating, {
1952
2012
  debounce: debounce,
1953
2013
  disabled: disabled,
1954
2014
  id: id,
@@ -1968,7 +2028,7 @@ function FeelTemplatingEntry(props) {
1968
2028
  })]
1969
2029
  });
1970
2030
  }
1971
- function FeelTemplating(props) {
2031
+ function Templating(props) {
1972
2032
  const {
1973
2033
  debounce,
1974
2034
  id,
@@ -2029,7 +2089,7 @@ function FeelTemplating(props) {
2029
2089
  }), jsx("div", {
2030
2090
  class: "bio-properties-panel-feelers-input",
2031
2091
  ref: containerRef,
2032
- children: jsx(CodeEditor, {
2092
+ children: jsx(CodeEditor$1, {
2033
2093
  name: id,
2034
2094
  onInput: handleInput,
2035
2095
  contentAttributes: {
@@ -2038,7 +2098,6 @@ function FeelTemplating(props) {
2038
2098
  disabled: disabled,
2039
2099
  onLint: handleLint,
2040
2100
  value: localValue,
2041
- useGutters: false,
2042
2101
  ref: editorRef,
2043
2102
  tooltipContainer: tooltipContainer
2044
2103
  })
@@ -2999,5 +3058,5 @@ var index = {
2999
3058
  debounceInput: ['factory', debounceInput]
3000
3059
  };
3001
3060
 
3002
- export { ArrowIcon, CheckboxEntry, CollapsibleEntry, CreateIcon, index as DebounceInputModule, DeleteIcon, DescriptionContext, Description as DescriptionEntry, DropdownButton, ErrorsContext, EventContext, ExternalLinkIcon, FeelEntry, FeelOptionalIcon, FeelRequiredIcon, FeelTemplatingEntry, FeelTextArea as FeelTextAreaEntry, Group, Header, HeaderButton, LayoutContext, List as ListEntry, ListGroup, ListItem, NumberFieldEntry, Placeholder, PropertiesPanel, LayoutContext as PropertiesPanelContext, SelectEntry, Simple as SimpleEntry, TextAreaEntry, TextfieldEntry as TextFieldEntry, ToggleSwitchEntry, isEdited$8 as isCheckboxEntryEdited, isEdited$7 as isFeelEntryEdited, isEdited$6 as isFeelTemplatingEntryEdited, isEdited$5 as isNumberFieldEntryEdited, isEdited$4 as isSelectEntryEdited, isEdited$3 as isSimpleEntryEdited, isEdited$2 as isTextAreaEntryEdited, isEdited$1 as isTextFieldEntryEdited, isEdited as isToggleSwitchEntryEdited, useDescriptionContext, useError, useEvent, useKeyFactory, useLayoutState, usePrevious, useShowEntryEvent, useStaticCallback, useStickyIntersectionObserver };
3061
+ export { ArrowIcon, CheckboxEntry, CollapsibleEntry, CreateIcon, index as DebounceInputModule, DeleteIcon, DescriptionContext, Description as DescriptionEntry, DropdownButton, ErrorsContext, EventContext, ExternalLinkIcon, FeelEntry, FeelOptionalIcon, FeelRequiredIcon, FeelTemplatingEntry, FeelTextAreaEntry, Group, Header, HeaderButton, LayoutContext, List as ListEntry, ListGroup, ListItem, NumberFieldEntry, Placeholder, PropertiesPanel, LayoutContext as PropertiesPanelContext, SelectEntry, Simple as SimpleEntry, TemplatingEntry, TextAreaEntry, TextfieldEntry as TextFieldEntry, ToggleSwitchEntry, isEdited$8 as isCheckboxEntryEdited, isEdited$7 as isFeelEntryEdited, isEdited$5 as isNumberFieldEntryEdited, isEdited$4 as isSelectEntryEdited, isEdited$3 as isSimpleEntryEdited, isEdited$6 as isTemplatingEntryEdited, isEdited$2 as isTextAreaEntryEdited, isEdited$1 as isTextFieldEntryEdited, isEdited as isToggleSwitchEntryEdited, useDescriptionContext, useError, useEvent, useKeyFactory, useLayoutState, usePrevious, useShowEntryEvent, useStaticCallback, useStickyIntersectionObserver };
3003
3062
  //# sourceMappingURL=index.esm.js.map