@dxos/react-ui-form 0.8.4-main.b97322e → 0.8.4-main.f5c0578
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/dist/lib/browser/index.mjs +168 -149
- package/dist/lib/browser/index.mjs.map +4 -4
- package/dist/lib/browser/meta.json +1 -1
- package/dist/lib/node-esm/index.mjs +168 -149
- package/dist/lib/node-esm/index.mjs.map +4 -4
- package/dist/lib/node-esm/meta.json +1 -1
- package/dist/types/src/components/ControlSection/ControlSection.stories.d.ts.map +1 -1
- package/dist/types/src/components/FieldEditor/FieldEditor.d.ts +2 -1
- package/dist/types/src/components/FieldEditor/FieldEditor.d.ts.map +1 -1
- package/dist/types/src/components/FieldEditor/FieldEditor.stories.d.ts.map +1 -1
- package/dist/types/src/components/Form/ArrayField.d.ts.map +1 -1
- package/dist/types/src/components/Form/Defaults.d.ts.map +1 -1
- package/dist/types/src/components/Form/Form.d.ts +2 -2
- package/dist/types/src/components/Form/Form.d.ts.map +1 -1
- package/dist/types/src/components/Form/Form.stories.d.ts.map +1 -1
- package/dist/types/src/components/Form/FormActions.d.ts.map +1 -1
- package/dist/types/src/components/Form/FormContent.d.ts +1 -1
- package/dist/types/src/components/Form/FormContent.d.ts.map +1 -1
- package/dist/types/src/components/Form/FormContext.d.ts +1 -1
- package/dist/types/src/components/Form/FormContext.d.ts.map +1 -1
- package/dist/types/src/components/Form/RefField.d.ts +1 -1
- package/dist/types/src/components/Form/RefField.d.ts.map +1 -1
- package/dist/types/src/components/Form/custom/SelectOptionsInput.d.ts.map +1 -1
- package/dist/types/src/components/Form/custom/SelectOptionsInput.stories.d.ts.map +1 -1
- package/dist/types/src/components/Form/factory.d.ts.map +1 -1
- package/dist/types/src/components/ViewEditor/ViewEditor.d.ts.map +1 -1
- package/dist/types/src/components/ViewEditor/ViewEditor.stories.d.ts.map +1 -1
- package/dist/types/src/components/deprecated/Form.d.ts.map +1 -1
- package/dist/types/src/components/deprecated/Form.stories.d.ts.map +1 -1
- package/dist/types/src/hooks/useForm.d.ts +1 -1
- package/dist/types/src/hooks/useForm.d.ts.map +1 -1
- package/dist/types/src/translations.d.ts +3 -2
- package/dist/types/src/translations.d.ts.map +1 -1
- package/dist/types/tsconfig.tsbuildinfo +1 -1
- package/package.json +30 -29
- package/src/components/ControlSection/ControlSection.stories.tsx +2 -1
- package/src/components/FieldEditor/FieldEditor.stories.tsx +4 -3
- package/src/components/FieldEditor/FieldEditor.test.tsx +3 -2
- package/src/components/FieldEditor/FieldEditor.tsx +16 -6
- package/src/components/Form/ArrayField.tsx +7 -6
- package/src/components/Form/Defaults.tsx +2 -1
- package/src/components/Form/Form.stories.tsx +4 -3
- package/src/components/Form/Form.tsx +4 -3
- package/src/components/Form/FormActions.tsx +2 -1
- package/src/components/Form/FormContent.tsx +6 -5
- package/src/components/Form/FormContext.tsx +5 -5
- package/src/components/Form/RefField.tsx +6 -5
- package/src/components/Form/custom/GeoPointInput.tsx +2 -2
- package/src/components/Form/custom/SelectOptionsInput.stories.tsx +3 -2
- package/src/components/Form/custom/SelectOptionsInput.tsx +28 -29
- package/src/components/Form/factory.tsx +1 -1
- package/src/components/ViewEditor/ViewEditor.stories.tsx +5 -4
- package/src/components/ViewEditor/ViewEditor.test.tsx +5 -4
- package/src/components/ViewEditor/ViewEditor.tsx +69 -54
- package/src/components/deprecated/Form.stories.tsx +3 -2
- package/src/components/deprecated/Form.tsx +3 -3
- package/src/hooks/useForm.ts +5 -3
- package/src/hooks/useRefQueryLookupHandler.ts +1 -1
- package/src/translations.ts +3 -2
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dxos/react-ui-form",
|
|
3
|
-
"version": "0.8.4-main.
|
|
3
|
+
"version": "0.8.4-main.f5c0578",
|
|
4
4
|
"description": "Data components.",
|
|
5
5
|
"homepage": "https://dxos.org",
|
|
6
6
|
"bugs": "https://github.com/dxos/dxos/issues",
|
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
"type": "module",
|
|
10
10
|
"exports": {
|
|
11
11
|
".": {
|
|
12
|
+
"source": "./src/index.ts",
|
|
12
13
|
"types": "./dist/types/src/index.d.ts",
|
|
13
14
|
"browser": "./dist/lib/browser/index.mjs",
|
|
14
15
|
"node": "./dist/lib/node-esm/index.mjs"
|
|
@@ -29,48 +30,48 @@
|
|
|
29
30
|
"@radix-ui/react-context": "1.1.1",
|
|
30
31
|
"date-fns": "^3.3.1",
|
|
31
32
|
"jsonpath": "^1.1.1",
|
|
32
|
-
"@dxos/async": "0.8.4-main.
|
|
33
|
-
"@dxos/
|
|
34
|
-
"@dxos/
|
|
35
|
-
"@dxos/echo": "0.8.4-main.
|
|
36
|
-
"@dxos/echo-db": "0.8.4-main.
|
|
37
|
-
"@dxos/effect": "0.8.4-main.
|
|
38
|
-
"@dxos/invariant": "0.8.4-main.
|
|
39
|
-
"@dxos/keys": "0.8.4-main.
|
|
40
|
-
"@dxos/
|
|
41
|
-
"@dxos/
|
|
42
|
-
"@dxos/
|
|
43
|
-
"@dxos/
|
|
44
|
-
"@dxos/react-ui-
|
|
45
|
-
"@dxos/react-ui-
|
|
46
|
-
"@dxos/react-ui-
|
|
47
|
-
"@dxos/react-ui-
|
|
48
|
-
"@dxos/react-ui-
|
|
49
|
-
"@dxos/schema": "0.8.4-main.
|
|
50
|
-
"@dxos/util": "0.8.4-main.
|
|
33
|
+
"@dxos/async": "0.8.4-main.f5c0578",
|
|
34
|
+
"@dxos/echo": "0.8.4-main.f5c0578",
|
|
35
|
+
"@dxos/debug": "0.8.4-main.f5c0578",
|
|
36
|
+
"@dxos/echo-schema": "0.8.4-main.f5c0578",
|
|
37
|
+
"@dxos/echo-db": "0.8.4-main.f5c0578",
|
|
38
|
+
"@dxos/effect": "0.8.4-main.f5c0578",
|
|
39
|
+
"@dxos/invariant": "0.8.4-main.f5c0578",
|
|
40
|
+
"@dxos/keys": "0.8.4-main.f5c0578",
|
|
41
|
+
"@dxos/log": "0.8.4-main.f5c0578",
|
|
42
|
+
"@dxos/lit-ui": "0.8.4-main.f5c0578",
|
|
43
|
+
"@dxos/live-object": "0.8.4-main.f5c0578",
|
|
44
|
+
"@dxos/react-client": "0.8.4-main.f5c0578",
|
|
45
|
+
"@dxos/react-ui-pickers": "0.8.4-main.f5c0578",
|
|
46
|
+
"@dxos/react-ui-list": "0.8.4-main.f5c0578",
|
|
47
|
+
"@dxos/react-ui-stack": "0.8.4-main.f5c0578",
|
|
48
|
+
"@dxos/react-ui-tag-picker": "0.8.4-main.f5c0578",
|
|
49
|
+
"@dxos/react-ui-types": "0.8.4-main.f5c0578",
|
|
50
|
+
"@dxos/schema": "0.8.4-main.f5c0578",
|
|
51
|
+
"@dxos/util": "0.8.4-main.f5c0578"
|
|
51
52
|
},
|
|
52
53
|
"devDependencies": {
|
|
53
54
|
"@types/jsonpath": "^0.2.4",
|
|
54
55
|
"@types/react": "~18.2.0",
|
|
55
56
|
"@types/react-dom": "~18.2.0",
|
|
56
|
-
"effect": "3.17.
|
|
57
|
+
"effect": "3.17.7",
|
|
57
58
|
"fast-check": "^3.19.0",
|
|
58
59
|
"react": "~18.2.0",
|
|
59
60
|
"react-dom": "~18.2.0",
|
|
60
61
|
"vite": "5.4.7",
|
|
61
|
-
"@dxos/echo-signals": "0.8.4-main.
|
|
62
|
-
"@dxos/
|
|
63
|
-
"@dxos/react-ui": "0.8.4-main.
|
|
64
|
-
"@dxos/
|
|
65
|
-
"@dxos/
|
|
66
|
-
"@dxos/
|
|
62
|
+
"@dxos/echo-signals": "0.8.4-main.f5c0578",
|
|
63
|
+
"@dxos/react-ui": "0.8.4-main.f5c0578",
|
|
64
|
+
"@dxos/react-ui-syntax-highlighter": "0.8.4-main.f5c0578",
|
|
65
|
+
"@dxos/storybook-utils": "0.8.4-main.f5c0578",
|
|
66
|
+
"@dxos/react-ui-theme": "0.8.4-main.f5c0578",
|
|
67
|
+
"@dxos/random": "0.8.4-main.f5c0578"
|
|
67
68
|
},
|
|
68
69
|
"peerDependencies": {
|
|
69
70
|
"effect": "^3.13.3",
|
|
70
71
|
"react": "~18.2.0",
|
|
71
72
|
"react-dom": "~18.2.0",
|
|
72
|
-
"@dxos/react-ui": "0.8.4-main.
|
|
73
|
-
"@dxos/react-ui-theme": "0.8.4-main.
|
|
73
|
+
"@dxos/react-ui": "0.8.4-main.f5c0578",
|
|
74
|
+
"@dxos/react-ui-theme": "0.8.4-main.f5c0578"
|
|
74
75
|
},
|
|
75
76
|
"publishConfig": {
|
|
76
77
|
"access": "public"
|
|
@@ -10,9 +10,10 @@ import React from 'react';
|
|
|
10
10
|
import { StackItem } from '@dxos/react-ui-stack';
|
|
11
11
|
import { withLayout, withTheme } from '@dxos/storybook-utils';
|
|
12
12
|
|
|
13
|
-
import { ControlPage, ControlSection, type ControlSectionProps } from './ControlSection';
|
|
14
13
|
import { translations } from '../../translations';
|
|
15
14
|
|
|
15
|
+
import { ControlPage, ControlSection, type ControlSectionProps } from './ControlSection';
|
|
16
|
+
|
|
16
17
|
const meta: Meta<ControlSectionProps> = {
|
|
17
18
|
title: 'ui/react-ui-form/ControlSection',
|
|
18
19
|
component: ControlSection,
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
import '@dxos-theme';
|
|
6
6
|
|
|
7
7
|
import { type Meta, type StoryObj } from '@storybook/react-vite';
|
|
8
|
-
import React, {
|
|
8
|
+
import React, { useEffect, useMemo } from 'react';
|
|
9
9
|
|
|
10
10
|
import { createEchoSchema } from '@dxos/live-object/testing';
|
|
11
11
|
import { log } from '@dxos/log';
|
|
@@ -13,9 +13,10 @@ import { ProjectionModel } from '@dxos/schema';
|
|
|
13
13
|
import { TestSchema, testView } from '@dxos/schema/testing';
|
|
14
14
|
import { withLayout, withTheme } from '@dxos/storybook-utils';
|
|
15
15
|
|
|
16
|
-
import { FieldEditor, type FieldEditorProps } from './FieldEditor';
|
|
17
16
|
import { translations } from '../../translations';
|
|
18
|
-
import { TestLayout, TestPanel
|
|
17
|
+
import { FIELD_EDITOR_DEBUG_SYMBOL, TestLayout, TestPanel } from '../testing';
|
|
18
|
+
|
|
19
|
+
import { FieldEditor, type FieldEditorProps } from './FieldEditor';
|
|
19
20
|
|
|
20
21
|
// Type definition for debug objects exposed to tests.
|
|
21
22
|
export type FieldEditorDebugObjects = {
|
|
@@ -3,14 +3,15 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import { composeStories } from '@storybook/react';
|
|
6
|
-
import {
|
|
6
|
+
import { act, cleanup, fireEvent, screen } from '@testing-library/react';
|
|
7
7
|
import { afterEach, describe, expect, test } from 'vitest';
|
|
8
8
|
|
|
9
9
|
import { ProjectionModel } from '@dxos/schema';
|
|
10
10
|
|
|
11
|
+
import { FIELD_EDITOR_DEBUG_SYMBOL } from '../testing';
|
|
12
|
+
|
|
11
13
|
import * as stories from './FieldEditor.stories';
|
|
12
14
|
import { type FieldEditorDebugObjects } from './FieldEditor.stories';
|
|
13
|
-
import { FIELD_EDITOR_DEBUG_SYMBOL } from '../testing';
|
|
14
15
|
|
|
15
16
|
const { Default } = composeStories(stories);
|
|
16
17
|
|
|
@@ -5,23 +5,24 @@
|
|
|
5
5
|
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
|
6
6
|
|
|
7
7
|
import { type SchemaRegistry } from '@dxos/echo-db';
|
|
8
|
-
import { FormatEnum, FormatEnums, formatToType
|
|
8
|
+
import { type EchoSchema, FormatEnum, FormatEnums, formatToType } from '@dxos/echo-schema';
|
|
9
9
|
import { log } from '@dxos/log';
|
|
10
10
|
import { useTranslation } from '@dxos/react-ui';
|
|
11
11
|
import {
|
|
12
|
-
getFormatSchema,
|
|
13
|
-
getSchemaProperties,
|
|
14
|
-
sortProperties,
|
|
15
12
|
type FieldType,
|
|
16
|
-
type PropertyType,
|
|
17
13
|
type ProjectionModel,
|
|
14
|
+
type PropertyType,
|
|
18
15
|
type SchemaProperty,
|
|
16
|
+
getFormatSchema,
|
|
17
|
+
getSchemaProperties,
|
|
18
|
+
sortProperties,
|
|
19
19
|
} from '@dxos/schema';
|
|
20
20
|
|
|
21
21
|
import { translationKey } from '../../translations';
|
|
22
22
|
import { Form, type FormProps, type InputComponent, SelectInput, SelectOptionInput } from '../Form';
|
|
23
23
|
|
|
24
24
|
export type FieldEditorProps = {
|
|
25
|
+
readonly?: boolean;
|
|
25
26
|
projection: ProjectionModel;
|
|
26
27
|
field: FieldType;
|
|
27
28
|
registry?: SchemaRegistry;
|
|
@@ -32,7 +33,15 @@ export type FieldEditorProps = {
|
|
|
32
33
|
/**
|
|
33
34
|
* Displays a Form representing the metadata for a given `Field` and `View`.
|
|
34
35
|
*/
|
|
35
|
-
export const FieldEditor = ({
|
|
36
|
+
export const FieldEditor = ({
|
|
37
|
+
readonly,
|
|
38
|
+
projection,
|
|
39
|
+
field,
|
|
40
|
+
registry,
|
|
41
|
+
onSave,
|
|
42
|
+
onCancel,
|
|
43
|
+
outerSpacing,
|
|
44
|
+
}: FieldEditorProps) => {
|
|
36
45
|
const { t } = useTranslation(translationKey);
|
|
37
46
|
const [props, setProps] = useState<PropertyType>(projection.getFieldProjection(field.id).props);
|
|
38
47
|
useEffect(() => setProps(projection.getFieldProjection(field.id).props), [field, projection]);
|
|
@@ -178,6 +187,7 @@ export const FieldEditor = ({ projection, field, registry, onSave, onCancel, out
|
|
|
178
187
|
<Form<PropertyType>
|
|
179
188
|
key={field.id}
|
|
180
189
|
autoFocus
|
|
190
|
+
readonly={readonly}
|
|
181
191
|
values={props}
|
|
182
192
|
schema={fieldSchema}
|
|
183
193
|
filter={propIsNotType}
|
|
@@ -6,18 +6,19 @@ import { SchemaAST, pipe } from 'effect';
|
|
|
6
6
|
import { capitalize } from 'effect/String';
|
|
7
7
|
import React, { Fragment, useCallback } from 'react';
|
|
8
8
|
|
|
9
|
-
import { findNode, getDiscriminatedType, isDiscriminatedUnion
|
|
9
|
+
import { SimpleType, findNode, getDiscriminatedType, isDiscriminatedUnion } from '@dxos/effect';
|
|
10
10
|
import { invariant } from '@dxos/invariant';
|
|
11
11
|
import { IconButton, useTranslation } from '@dxos/react-ui';
|
|
12
|
-
import {
|
|
12
|
+
import { type SchemaProperty, getSchemaProperties } from '@dxos/schema';
|
|
13
13
|
|
|
14
|
-
import { type ComponentLookup } from './Form';
|
|
15
|
-
import { FormField } from './FormContent';
|
|
16
|
-
import { useFormValues, type FormInputStateProps } from './FormContext';
|
|
17
|
-
import { InputHeader, type InputComponent } from './Input';
|
|
18
14
|
import { translationKey } from '../../translations';
|
|
19
15
|
import { findArrayElementType } from '../../util';
|
|
20
16
|
|
|
17
|
+
import { type ComponentLookup } from './Form';
|
|
18
|
+
import { FormField } from './FormContent';
|
|
19
|
+
import { type FormInputStateProps, useFormValues } from './FormContext';
|
|
20
|
+
import { type InputComponent, InputHeader } from './Input';
|
|
21
|
+
|
|
21
22
|
type ArrayFieldProps = {
|
|
22
23
|
property: SchemaProperty<any>;
|
|
23
24
|
readonly?: boolean;
|
|
@@ -6,9 +6,10 @@ import React, { useCallback, useEffect, useRef } from 'react';
|
|
|
6
6
|
|
|
7
7
|
import { Input, Select, useTranslation } from '@dxos/react-ui';
|
|
8
8
|
|
|
9
|
-
import { type InputProps, InputHeader } from './Input';
|
|
10
9
|
import { translationKey } from '../../translations';
|
|
11
10
|
|
|
11
|
+
import { InputHeader, type InputProps } from './Input';
|
|
12
|
+
|
|
12
13
|
export const TextInput = ({
|
|
13
14
|
type,
|
|
14
15
|
label,
|
|
@@ -9,17 +9,18 @@ import { Schema } from 'effect';
|
|
|
9
9
|
import React, { useCallback, useState } from 'react';
|
|
10
10
|
|
|
11
11
|
import { ContactType } from '@dxos/client/testing';
|
|
12
|
-
import { type BaseObject, Expando, Format,
|
|
12
|
+
import { type BaseObject, Expando, Format, Ref, type TypeAnnotation, getObjectDXN } from '@dxos/echo-schema';
|
|
13
13
|
import { live } from '@dxos/live-object';
|
|
14
14
|
import { withSurfaceVariantsLayout } from '@dxos/react-ui/testing';
|
|
15
15
|
import { Testing } from '@dxos/schema/testing';
|
|
16
16
|
import { withLayout, withTheme } from '@dxos/storybook-utils';
|
|
17
17
|
|
|
18
|
-
import { SelectInput } from './Defaults';
|
|
19
|
-
import { Form, type FormProps } from './Form';
|
|
20
18
|
import { translations } from '../../translations';
|
|
21
19
|
import { TestLayout, TestPanel } from '../testing';
|
|
22
20
|
|
|
21
|
+
import { SelectInput } from './Defaults';
|
|
22
|
+
import { Form, type FormProps } from './Form';
|
|
23
|
+
|
|
23
24
|
const AddressSchema = Schema.Struct({
|
|
24
25
|
street: Schema.optional(Schema.String.annotations({ title: 'Street' })),
|
|
25
26
|
city: Schema.optional(Schema.String.annotations({ title: 'City' })),
|
|
@@ -10,11 +10,12 @@ import { type ThemedClassName } from '@dxos/react-ui';
|
|
|
10
10
|
import { cardDialogOverflow, cardSpacing } from '@dxos/react-ui-stack';
|
|
11
11
|
import { type SchemaProperty } from '@dxos/schema';
|
|
12
12
|
|
|
13
|
+
import { type FormOptions } from '../../hooks';
|
|
14
|
+
|
|
13
15
|
import { FormActions, type FormOuterSpacing } from './FormActions';
|
|
14
16
|
import { FormFields, type FormFieldsProps } from './FormContent';
|
|
15
17
|
import { FormProvider } from './FormContext';
|
|
16
|
-
import { type
|
|
17
|
-
import { type FormOptions } from '../../hooks';
|
|
18
|
+
import { type InputComponent, type InputProps } from './Input';
|
|
18
19
|
|
|
19
20
|
export type PropsFilter<T extends BaseObject> = (props: SchemaProperty<T>[]) => SchemaProperty<T>[];
|
|
20
21
|
|
|
@@ -99,7 +100,7 @@ export const Form = <T extends BaseObject>({
|
|
|
99
100
|
readonly={readonly}
|
|
100
101
|
schema={schema}
|
|
101
102
|
/>
|
|
102
|
-
{(onCancel || onSave) && !autoSave && (
|
|
103
|
+
{(onCancel || onSave) && !autoSave && !readonly && (
|
|
103
104
|
<FormActions readonly={readonly} onCancel={onCancel} outerSpacing={outerSpacing} />
|
|
104
105
|
)}
|
|
105
106
|
</div>
|
|
@@ -8,9 +8,10 @@ import { IconButton, useTranslation } from '@dxos/react-ui';
|
|
|
8
8
|
import { cardSpacing } from '@dxos/react-ui-stack';
|
|
9
9
|
import { mx } from '@dxos/react-ui-theme';
|
|
10
10
|
|
|
11
|
-
import { useFormContext } from './FormContext';
|
|
12
11
|
import { translationKey } from '../../translations';
|
|
13
12
|
|
|
13
|
+
import { useFormContext } from './FormContext';
|
|
14
|
+
|
|
14
15
|
export type FormOuterSpacing = boolean | 'blockStart-0' | 'scroll-fields';
|
|
15
16
|
|
|
16
17
|
export type FormActionsProps = {
|
|
@@ -9,18 +9,19 @@ import React, { forwardRef, useMemo } from 'react';
|
|
|
9
9
|
import { createJsonPath, findNode, getDiscriminatedType, isDiscriminatedUnion } from '@dxos/effect';
|
|
10
10
|
import { type ThemedClassName } from '@dxos/react-ui';
|
|
11
11
|
import { mx } from '@dxos/react-ui-theme';
|
|
12
|
-
import {
|
|
12
|
+
import { type SchemaProperty, getSchemaProperties } from '@dxos/schema';
|
|
13
13
|
import { isNotFalsy } from '@dxos/util';
|
|
14
14
|
|
|
15
|
+
import { type QueryRefOptions } from '../../hooks';
|
|
16
|
+
import { getRefProps } from '../../util';
|
|
17
|
+
|
|
15
18
|
import { ArrayField } from './ArrayField';
|
|
16
19
|
import { SelectInput } from './Defaults';
|
|
20
|
+
import { getInputComponent } from './factory';
|
|
17
21
|
import { type ComponentLookup } from './Form';
|
|
18
|
-
import {
|
|
22
|
+
import { useFormValues, useInputProps } from './FormContext';
|
|
19
23
|
import { type InputComponent } from './Input';
|
|
20
24
|
import { RefField } from './RefField';
|
|
21
|
-
import { getInputComponent } from './factory';
|
|
22
|
-
import { type QueryRefOptions } from '../../hooks';
|
|
23
|
-
import { getRefProps } from '../../util';
|
|
24
25
|
|
|
25
26
|
export type FormFieldProps = {
|
|
26
27
|
property: SchemaProperty<any>;
|
|
@@ -3,19 +3,19 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import React, {
|
|
6
|
-
|
|
6
|
+
type FocusEvent,
|
|
7
|
+
type PropsWithChildren,
|
|
7
8
|
type RefObject,
|
|
9
|
+
createContext,
|
|
10
|
+
useCallback,
|
|
8
11
|
useContext,
|
|
9
12
|
useEffect,
|
|
10
13
|
useMemo,
|
|
11
|
-
type FocusEvent,
|
|
12
|
-
type PropsWithChildren,
|
|
13
|
-
useCallback,
|
|
14
14
|
} from 'react';
|
|
15
15
|
|
|
16
16
|
import { raise } from '@dxos/debug';
|
|
17
17
|
import { type BaseObject, getValue } from '@dxos/echo-schema';
|
|
18
|
-
import {
|
|
18
|
+
import { type SimpleType, createJsonPath } from '@dxos/effect';
|
|
19
19
|
|
|
20
20
|
import { type FormHandler, type FormOptions, useForm } from '../../hooks';
|
|
21
21
|
|
|
@@ -3,28 +3,29 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import { type SchemaAST } from 'effect';
|
|
6
|
-
import React, { useCallback, useMemo
|
|
6
|
+
import React, { type FocusEvent, useCallback, useMemo } from 'react';
|
|
7
7
|
|
|
8
8
|
import {
|
|
9
9
|
Expando,
|
|
10
|
-
getTypeAnnotation,
|
|
11
10
|
Ref,
|
|
12
11
|
ReferenceAnnotationId,
|
|
13
12
|
type ReferenceAnnotationValue,
|
|
13
|
+
getTypeAnnotation,
|
|
14
14
|
} from '@dxos/echo-schema';
|
|
15
15
|
import { findAnnotation } from '@dxos/effect';
|
|
16
16
|
import { DXN } from '@dxos/keys';
|
|
17
17
|
import { DxRefTag } from '@dxos/lit-ui/react';
|
|
18
18
|
import { Input, useTranslation } from '@dxos/react-ui';
|
|
19
|
-
import { TagPicker, type
|
|
19
|
+
import { TagPicker, type TagPickerItemData, type TagPickerMode } from '@dxos/react-ui-tag-picker';
|
|
20
20
|
import { descriptionText, mx } from '@dxos/react-ui-theme';
|
|
21
21
|
import { isNonNullable } from '@dxos/util';
|
|
22
22
|
|
|
23
|
-
import { TextInput } from './Defaults';
|
|
24
|
-
import { InputHeader, type InputProps } from './Input';
|
|
25
23
|
import { type QueryRefOptions, useQueryRefOptions } from '../../hooks';
|
|
26
24
|
import { translationKey } from '../../translations';
|
|
27
25
|
|
|
26
|
+
import { TextInput } from './Defaults';
|
|
27
|
+
import { InputHeader, type InputProps } from './Input';
|
|
28
|
+
|
|
28
29
|
type RefFieldProps = InputProps & {
|
|
29
30
|
ast?: SchemaAST.AST;
|
|
30
31
|
array?: boolean;
|
|
@@ -2,9 +2,9 @@
|
|
|
2
2
|
// Copyright 2024 DXOS.org
|
|
3
3
|
//
|
|
4
4
|
|
|
5
|
-
import React, {
|
|
5
|
+
import React, { type ChangeEvent, useCallback, useEffect, useMemo, useState } from 'react';
|
|
6
6
|
|
|
7
|
-
import { type GeoPoint
|
|
7
|
+
import { GeoLocation, type GeoPoint } from '@dxos/echo-schema';
|
|
8
8
|
import { Input, useTranslation } from '@dxos/react-ui';
|
|
9
9
|
import { safeParseFloat } from '@dxos/util';
|
|
10
10
|
|
|
@@ -8,14 +8,15 @@ import { type Meta, type StoryObj } from '@storybook/react-vite';
|
|
|
8
8
|
import { Schema } from 'effect';
|
|
9
9
|
import React, { useState } from 'react';
|
|
10
10
|
|
|
11
|
-
import {
|
|
11
|
+
import { type SelectOption, SelectOptionSchema } from '@dxos/echo-schema';
|
|
12
12
|
import { withLayout, withTheme } from '@dxos/storybook-utils';
|
|
13
13
|
|
|
14
|
-
import { SelectOptionInput } from './SelectOptionsInput';
|
|
15
14
|
import { translations } from '../../../translations';
|
|
16
15
|
import { TestLayout, TestPanel } from '../../testing';
|
|
17
16
|
import { Form } from '../Form';
|
|
18
17
|
|
|
18
|
+
import { SelectOptionInput } from './SelectOptionsInput';
|
|
19
|
+
|
|
19
20
|
const schema = Schema.Struct({
|
|
20
21
|
options: Schema.Array(SelectOptionSchema).pipe(Schema.mutable),
|
|
21
22
|
}).pipe(Schema.mutable);
|
|
@@ -2,19 +2,18 @@
|
|
|
2
2
|
// Copyright 2025 DXOS.org
|
|
3
3
|
//
|
|
4
4
|
|
|
5
|
-
import React, { type ChangeEvent, type KeyboardEvent, useCallback, useEffect,
|
|
5
|
+
import React, { type ChangeEvent, type KeyboardEvent, useCallback, useEffect, useRef, useState } from 'react';
|
|
6
6
|
|
|
7
7
|
import { type SelectOption } from '@dxos/echo-schema';
|
|
8
8
|
import { PublicKey } from '@dxos/keys';
|
|
9
|
-
import { type ChromaticPalette,
|
|
9
|
+
import { type ChromaticPalette, IconButton, Input, Tag, useTranslation } from '@dxos/react-ui';
|
|
10
10
|
import { List } from '@dxos/react-ui-list';
|
|
11
11
|
import { HuePicker } from '@dxos/react-ui-pickers';
|
|
12
|
-
import { hues,
|
|
12
|
+
import { hues, subtleHover } from '@dxos/react-ui-theme';
|
|
13
13
|
|
|
14
14
|
import { translationKey } from '../../../translations';
|
|
15
15
|
import { InputHeader, type InputProps } from '../Input';
|
|
16
16
|
|
|
17
|
-
// TODO(ZaymonFC): Handle disabled.
|
|
18
17
|
export const SelectOptionInput = ({ type, label, disabled, getStatus, getValue, onValueChange }: InputProps) => {
|
|
19
18
|
const [selected, setSelectedId] = useState<string | null>(null);
|
|
20
19
|
const [isNewOption, setIsNewOption] = useState(false);
|
|
@@ -115,7 +114,12 @@ export const SelectOptionInput = ({ type, label, disabled, getStatus, getValue,
|
|
|
115
114
|
<InputHeader error={error} label={label} />
|
|
116
115
|
<div role='none'>
|
|
117
116
|
{options && (
|
|
118
|
-
<List.Root
|
|
117
|
+
<List.Root
|
|
118
|
+
items={options}
|
|
119
|
+
isItem={(item) => true}
|
|
120
|
+
onMove={disabled ? undefined : handleMove}
|
|
121
|
+
readonly={disabled}
|
|
122
|
+
>
|
|
119
123
|
{({ items }) => (
|
|
120
124
|
<div role='list' className='w-full overflow-auto'>
|
|
121
125
|
{items?.map((item) => (
|
|
@@ -123,26 +127,30 @@ export const SelectOptionInput = ({ type, label, disabled, getStatus, getValue,
|
|
|
123
127
|
<List.Item
|
|
124
128
|
role='button'
|
|
125
129
|
item={item}
|
|
126
|
-
classNames={[
|
|
130
|
+
classNames={[subtleHover, 'flex flex-col cursor-pointer rounded-sm']}
|
|
127
131
|
aria-expanded={selected === item.id}
|
|
128
132
|
>
|
|
129
133
|
<div className='flex items-center'>
|
|
130
|
-
<List.ItemDragHandle />
|
|
134
|
+
<List.ItemDragHandle disabled={disabled} />
|
|
131
135
|
<List.ItemTitle onClick={() => handleClick(item.id)} classNames='flex-1'>
|
|
132
136
|
{/* TODO(ZaymonFC): Move spacer into Tag component. */}
|
|
133
137
|
<Tag palette={item.color as ChromaticPalette}>{item.title || '\u200b'}</Tag>
|
|
134
138
|
</List.ItemTitle>
|
|
135
|
-
<
|
|
139
|
+
<IconButton
|
|
140
|
+
iconOnly
|
|
141
|
+
variant='ghost'
|
|
142
|
+
label={t(selected === item.id ? 'collapse label' : 'expand label', { ns: 'os' })}
|
|
136
143
|
icon={selected === item.id ? 'ph--caret-down--regular' : 'ph--caret-right--regular'}
|
|
137
144
|
onClick={() => handleClick(item.id)}
|
|
138
145
|
/>
|
|
139
146
|
</div>
|
|
140
147
|
{selected === item.id && (
|
|
141
|
-
<div className='
|
|
148
|
+
<div className='pli-cardSpacingInline plb-cardSpacingBlock flex flex-col gap-1 density-fine'>
|
|
142
149
|
{/* 16px to match drag handle width. */}
|
|
143
150
|
<Input.Label classNames='text-xs'>{t('select option label')}</Input.Label>
|
|
144
|
-
<div className='
|
|
151
|
+
<div className='grid grid-cols-[1fr_min-content_min-content] gap-1'>
|
|
145
152
|
<Input.TextInput
|
|
153
|
+
disabled={disabled}
|
|
146
154
|
placeholder={t('select option label placeholder')}
|
|
147
155
|
ref={selected === item.id ? inputRef : undefined}
|
|
148
156
|
value={item.title}
|
|
@@ -151,14 +159,9 @@ export const SelectOptionInput = ({ type, label, disabled, getStatus, getValue,
|
|
|
151
159
|
classNames='flex-1'
|
|
152
160
|
data-no-submit
|
|
153
161
|
/>
|
|
154
|
-
<
|
|
155
|
-
<HuePicker
|
|
156
|
-
value={item.color}
|
|
157
|
-
onChange={handleColorChange(item.id)}
|
|
158
|
-
rootVariant='toolbar-button'
|
|
159
|
-
/>
|
|
160
|
-
</Toolbar.Root>
|
|
162
|
+
<HuePicker disabled={disabled} value={item.color} onChange={handleColorChange(item.id)} />
|
|
161
163
|
<IconButton
|
|
164
|
+
disabled={disabled}
|
|
162
165
|
icon='ph--trash--fill'
|
|
163
166
|
iconOnly
|
|
164
167
|
label={t('select option delete')}
|
|
@@ -170,18 +173,14 @@ export const SelectOptionInput = ({ type, label, disabled, getStatus, getValue,
|
|
|
170
173
|
</List.Item>
|
|
171
174
|
</div>
|
|
172
175
|
))}
|
|
173
|
-
<
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
<span className='text-sm'>{t('select option add')}</span>
|
|
182
|
-
</div>
|
|
183
|
-
</div>
|
|
184
|
-
</div>
|
|
176
|
+
<IconButton
|
|
177
|
+
variant='ghost'
|
|
178
|
+
icon='ph--plus--regular'
|
|
179
|
+
label={t('select option add')}
|
|
180
|
+
onClick={handleAdd}
|
|
181
|
+
disabled={disabled}
|
|
182
|
+
classNames='is-full'
|
|
183
|
+
/>
|
|
185
184
|
</div>
|
|
186
185
|
)}
|
|
187
186
|
</List.Root>
|
|
@@ -5,9 +5,9 @@
|
|
|
5
5
|
import { FormatEnum } from '@dxos/echo-schema';
|
|
6
6
|
import { type SimpleType } from '@dxos/effect';
|
|
7
7
|
|
|
8
|
+
import { GeoPointInput } from './custom';
|
|
8
9
|
import { BooleanInput, MarkdownInput, NumberInput, TextInput } from './Defaults';
|
|
9
10
|
import { type InputComponent } from './Input';
|
|
10
|
-
import { GeoPointInput } from './custom';
|
|
11
11
|
|
|
12
12
|
/**
|
|
13
13
|
* Get property input component.
|
|
@@ -6,20 +6,21 @@ import '@dxos-theme';
|
|
|
6
6
|
|
|
7
7
|
import { type Meta, type StoryObj } from '@storybook/react-vite';
|
|
8
8
|
import { Schema } from 'effect';
|
|
9
|
-
import React, { useCallback, useMemo, useState
|
|
9
|
+
import React, { useCallback, useEffect, useMemo, useState } from 'react';
|
|
10
10
|
|
|
11
11
|
import { Obj, Type } from '@dxos/echo';
|
|
12
|
-
import {
|
|
12
|
+
import { type EchoSchema, Format, TypedObject, toJsonSchema } from '@dxos/echo-schema';
|
|
13
13
|
import { Filter, useQuery, useSpace } from '@dxos/react-client/echo';
|
|
14
14
|
import { withClientProvider } from '@dxos/react-client/testing';
|
|
15
15
|
import { useAsyncEffect } from '@dxos/react-ui';
|
|
16
16
|
import { DataType, ProjectionModel, createView } from '@dxos/schema';
|
|
17
|
-
import {
|
|
17
|
+
import { withLayout, withTheme } from '@dxos/storybook-utils';
|
|
18
18
|
|
|
19
|
-
import { ViewEditor, type ViewEditorProps } from './ViewEditor';
|
|
20
19
|
import { translations } from '../../translations';
|
|
21
20
|
import { TestLayout, TestPanel, VIEW_EDITOR_DEBUG_SYMBOL } from '../testing';
|
|
22
21
|
|
|
22
|
+
import { ViewEditor, type ViewEditorProps } from './ViewEditor';
|
|
23
|
+
|
|
23
24
|
// Type definition for debug objects exposed to tests.
|
|
24
25
|
export type ViewEditorDebugObjects = {
|
|
25
26
|
schema: EchoSchema;
|
|
@@ -3,15 +3,16 @@
|
|
|
3
3
|
//
|
|
4
4
|
|
|
5
5
|
import { composeStories } from '@storybook/react';
|
|
6
|
-
import {
|
|
6
|
+
import { cleanup, fireEvent, screen, waitFor } from '@testing-library/react';
|
|
7
7
|
import { afterEach, describe, expect, test } from 'vitest';
|
|
8
8
|
|
|
9
9
|
import { EchoSchema, isInstanceOf } from '@dxos/echo-schema';
|
|
10
10
|
import { DataType, ProjectionModel } from '@dxos/schema';
|
|
11
11
|
|
|
12
|
+
import { VIEW_EDITOR_DEBUG_SYMBOL } from '../testing';
|
|
13
|
+
|
|
12
14
|
import * as stories from './ViewEditor.stories';
|
|
13
15
|
import { type ViewEditorDebugObjects } from './ViewEditor.stories';
|
|
14
|
-
import { VIEW_EDITOR_DEBUG_SYMBOL } from '../testing';
|
|
15
16
|
|
|
16
17
|
const { Default } = composeStories(stories);
|
|
17
18
|
|
|
@@ -41,7 +42,7 @@ describe('ViewEditor', () => {
|
|
|
41
42
|
test('renders view editor', async () => {
|
|
42
43
|
await Default.run();
|
|
43
44
|
await waitForViewEditor();
|
|
44
|
-
expect(screen.getByText('
|
|
45
|
+
expect(screen.getByText('Record type')).toBeInTheDocument();
|
|
45
46
|
});
|
|
46
47
|
|
|
47
48
|
test('change property name', async () => {
|
|
@@ -140,7 +141,7 @@ describe('ViewEditor', () => {
|
|
|
140
141
|
// Find the delete button for the 'name' property.
|
|
141
142
|
const nameProperty = screen.getByText('name');
|
|
142
143
|
const propertyRow = nameProperty.closest('[role="listitem"]');
|
|
143
|
-
const deleteButton = propertyRow?.querySelector('
|
|
144
|
+
const deleteButton = propertyRow?.querySelector('[data-testid="field.delete"]');
|
|
144
145
|
|
|
145
146
|
if (!deleteButton) {
|
|
146
147
|
throw new Error('Delete button not found');
|