@pdfme/ui 1.0.0-beta.7 → 1.0.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.
- package/coverage/clover.xml +6 -0
- package/coverage/coverage-final.json +1 -0
- package/coverage/lcov-report/base.css +224 -0
- package/coverage/lcov-report/block-navigation.js +87 -0
- package/coverage/lcov-report/favicon.png +0 -0
- package/coverage/lcov-report/index.html +101 -0
- package/coverage/lcov-report/prettify.css +1 -0
- package/coverage/lcov-report/prettify.js +2 -0
- package/coverage/lcov-report/sort-arrow-sprite.png +0 -0
- package/coverage/lcov-report/sorter.js +196 -0
- package/coverage/lcov.info +0 -0
- package/dist/index.js +1 -1
- package/dist/index.js.LICENSE.txt +2 -2
- package/dist/index.js.map +1 -1
- package/dist/types/class.d.ts +5 -4
- package/dist/types/components/Designer/Main/Moveable.d.ts +1 -1
- package/dist/types/components/Designer/Sidebar/DetailView/ExampleInputEditor.d.ts +4 -1
- package/dist/types/components/Designer/Sidebar/DetailView/PositionAndSizeEditor.d.ts +4 -1
- package/dist/types/components/Designer/Sidebar/DetailView/TextPropEditor.d.ts +4 -1
- package/dist/types/components/Designer/Sidebar/DetailView/TypeAndKeyEditor.d.ts +4 -1
- package/dist/types/components/Designer/Sidebar/DetailView/index.d.ts +4 -1
- package/dist/types/components/Designer/Sidebar/ListView/Item.d.ts +25 -0
- package/dist/types/components/Designer/Sidebar/ListView/SelectableSortableContainer.d.ts +3 -0
- package/dist/types/components/Designer/Sidebar/ListView/SelectableSortableItem.d.ts +14 -0
- package/dist/types/components/Designer/Sidebar/{ListView.d.ts → ListView/index.d.ts} +2 -2
- package/dist/types/components/Designer/Sidebar/index.d.ts +2 -6
- package/dist/types/constants.d.ts +1 -0
- package/dist/types/contexts.d.ts +1 -1
- package/dist/types/helper.d.ts +1 -1
- package/dist/types/hooks.d.ts +1 -0
- package/dist/types/i18n.d.ts +4 -2
- package/package.json +10 -7
- package/src/Designer.tsx +4 -2
- package/src/Form.tsx +1 -0
- package/src/Viewer.tsx +1 -0
- package/src/assets/icons/align-horizontal-center.svg +1 -0
- package/src/assets/icons/align-horizontal-left.svg +1 -0
- package/src/assets/icons/align-horizontal-right.svg +1 -0
- package/src/assets/icons/align-vertical-bottom.svg +1 -0
- package/src/assets/icons/align-vertical-middle.svg +1 -0
- package/src/assets/icons/align-vertical-top.svg +1 -0
- package/src/assets/icons/close.svg +4 -0
- package/src/assets/icons/horizontal-distribute.svg +1 -0
- package/src/assets/icons/vertical-distribute.svg +1 -0
- package/src/assets/imageExample.png +0 -0
- package/src/class.ts +27 -8
- package/src/components/Designer/Main/Moveable.tsx +1 -1
- package/src/components/Designer/Main/index.tsx +22 -16
- package/src/components/Designer/Sidebar/DetailView/ExampleInputEditor.tsx +28 -6
- package/src/components/Designer/Sidebar/DetailView/PositionAndSizeEditor.tsx +115 -24
- package/src/components/Designer/Sidebar/DetailView/TextPropEditor.tsx +36 -6
- package/src/components/Designer/Sidebar/DetailView/TypeAndKeyEditor.tsx +14 -6
- package/src/components/Designer/Sidebar/DetailView/index.tsx +21 -16
- package/src/components/Designer/Sidebar/ListView/Item.tsx +113 -0
- package/src/components/Designer/Sidebar/ListView/SelectableSortableContainer.tsx +162 -0
- package/src/components/Designer/Sidebar/ListView/SelectableSortableItem.tsx +78 -0
- package/src/components/Designer/Sidebar/ListView/index.tsx +119 -0
- package/src/components/Designer/Sidebar/index.tsx +30 -14
- package/src/components/Designer/index.tsx +12 -24
- package/src/components/Error.tsx +2 -2
- package/src/components/Paper.tsx +11 -3
- package/src/components/Preview/Pager/Page.tsx +1 -1
- package/src/components/Preview/Pager/Unit.tsx +1 -1
- package/src/components/Preview/index.tsx +3 -4
- package/src/components/Root.tsx +2 -7
- package/src/components/Schemas/BarcodeSchema.tsx +43 -28
- package/src/components/Schemas/ImageSchema.tsx +71 -66
- package/src/components/Schemas/TextSchema.tsx +6 -3
- package/src/constants.ts +2 -0
- package/src/helper.ts +43 -37
- package/src/hooks.ts +11 -0
- package/src/i18n.ts +10 -7
- package/tsconfig.json +1 -1
- package/webpack.config.js +0 -18
- package/src/components/Designer/Sidebar/ListView.tsx +0 -180
@@ -0,0 +1,78 @@
|
|
1
|
+
import React, { useContext } from 'react';
|
2
|
+
import { useSortable } from '@dnd-kit/sortable';
|
3
|
+
import { SchemaForUI } from '@pdfme/common';
|
4
|
+
import { I18nContext } from '../../../../contexts';
|
5
|
+
import Item from './Item';
|
6
|
+
import { useMountStatus } from '../../../../hooks';
|
7
|
+
|
8
|
+
interface Props {
|
9
|
+
isSelected: boolean;
|
10
|
+
style?: React.CSSProperties;
|
11
|
+
onSelect: (id: string, isShiftSelect: boolean) => void;
|
12
|
+
onEdit: (id: string) => void;
|
13
|
+
schema: SchemaForUI;
|
14
|
+
schemas: SchemaForUI[];
|
15
|
+
onMouseEnter: () => void;
|
16
|
+
onMouseLeave: () => void;
|
17
|
+
}
|
18
|
+
const SelectableSortableItem = ({
|
19
|
+
isSelected,
|
20
|
+
style,
|
21
|
+
onSelect,
|
22
|
+
onEdit,
|
23
|
+
schema,
|
24
|
+
schemas,
|
25
|
+
onMouseEnter,
|
26
|
+
onMouseLeave,
|
27
|
+
}: Props) => {
|
28
|
+
const i18n = useContext(I18nContext);
|
29
|
+
const { setNodeRef, listeners, isDragging, isSorting, transform, transition } = useSortable({
|
30
|
+
id: schema.id,
|
31
|
+
});
|
32
|
+
const mounted = useMountStatus();
|
33
|
+
const mountedWhileDragging = isDragging && !mounted;
|
34
|
+
|
35
|
+
const newListeners = {
|
36
|
+
...listeners,
|
37
|
+
onClick: (event: any) => onSelect(schema.id, event.shiftKey),
|
38
|
+
};
|
39
|
+
|
40
|
+
let status: undefined | 'is-warning' | 'is-danger';
|
41
|
+
if (!schema.key) {
|
42
|
+
status = 'is-warning';
|
43
|
+
} else if (schemas.find((s) => schema.key && s.key === schema.key && s.id !== schema.id)) {
|
44
|
+
status = 'is-danger';
|
45
|
+
}
|
46
|
+
|
47
|
+
let title = i18n('edit');
|
48
|
+
if (status === 'is-warning') {
|
49
|
+
title = i18n('plsInputName');
|
50
|
+
} else if (status === 'is-danger') {
|
51
|
+
title = i18n('fieldMustUniq');
|
52
|
+
}
|
53
|
+
|
54
|
+
const selectedStyle = isSelected
|
55
|
+
? { color: '#fff', background: '#18a0fb', opacity: isSorting || isDragging ? 0.5 : 1 }
|
56
|
+
: ({} as React.CSSProperties);
|
57
|
+
|
58
|
+
return (
|
59
|
+
<Item
|
60
|
+
ref={setNodeRef}
|
61
|
+
onMouseEnter={onMouseEnter}
|
62
|
+
onMouseLeave={onMouseLeave}
|
63
|
+
onClick={() => onEdit(schema.id)}
|
64
|
+
value={schema.key}
|
65
|
+
status={status}
|
66
|
+
title={title}
|
67
|
+
style={{ ...selectedStyle, ...style }}
|
68
|
+
dragging={isDragging}
|
69
|
+
sorting={isSorting}
|
70
|
+
transition={transition}
|
71
|
+
transform={transform}
|
72
|
+
fadeIn={mountedWhileDragging}
|
73
|
+
listeners={newListeners}
|
74
|
+
/>
|
75
|
+
);
|
76
|
+
};
|
77
|
+
|
78
|
+
export default SelectableSortableItem;
|
@@ -0,0 +1,119 @@
|
|
1
|
+
import React, { useContext, useState } from 'react';
|
2
|
+
import { ZOOM, RULER_HEIGHT, SIDEBAR_WIDTH } from '../../../../constants';
|
3
|
+
import { I18nContext } from '../../../../contexts';
|
4
|
+
import Divider from '../../../Divider';
|
5
|
+
import SelectableSortableContainer from './SelectableSortableContainer';
|
6
|
+
import { SidebarProps } from '..';
|
7
|
+
|
8
|
+
const ListView = (
|
9
|
+
props: Pick<
|
10
|
+
SidebarProps,
|
11
|
+
| 'schemas'
|
12
|
+
| 'onSortEnd'
|
13
|
+
| 'onEdit'
|
14
|
+
| 'size'
|
15
|
+
| 'hoveringSchemaId'
|
16
|
+
| 'onChangeHoveringSchemaId'
|
17
|
+
| 'changeSchemas'
|
18
|
+
>
|
19
|
+
) => {
|
20
|
+
const {
|
21
|
+
schemas,
|
22
|
+
onSortEnd,
|
23
|
+
onEdit,
|
24
|
+
size,
|
25
|
+
hoveringSchemaId,
|
26
|
+
onChangeHoveringSchemaId,
|
27
|
+
changeSchemas,
|
28
|
+
} = props;
|
29
|
+
const i18n = useContext(I18nContext);
|
30
|
+
const [isBulkUpdateFieldNamesMode, setIsBulkUpdateFieldNamesMode] = useState(false);
|
31
|
+
const [fieldNamesValue, setFieldNamesValue] = useState('');
|
32
|
+
const height = size.height - RULER_HEIGHT * ZOOM - 135;
|
33
|
+
return (
|
34
|
+
<div>
|
35
|
+
<div style={{ height: 40, display: 'flex', alignItems: 'center' }}>
|
36
|
+
<span style={{ textAlign: 'center', width: '100%', fontWeight: 'bold' }}>
|
37
|
+
{i18n('fieldsList')}
|
38
|
+
</span>
|
39
|
+
</div>
|
40
|
+
<Divider />
|
41
|
+
{isBulkUpdateFieldNamesMode ? (
|
42
|
+
<div>
|
43
|
+
<textarea
|
44
|
+
wrap="off"
|
45
|
+
value={fieldNamesValue}
|
46
|
+
onChange={(e) => setFieldNamesValue(e.target.value)}
|
47
|
+
style={{
|
48
|
+
height: height - 5,
|
49
|
+
width: SIDEBAR_WIDTH,
|
50
|
+
fontSize: '1rem',
|
51
|
+
lineHeight: '2.5rem',
|
52
|
+
background: 'transparent',
|
53
|
+
margin: 0,
|
54
|
+
padding: '1rem',
|
55
|
+
boxSizing: 'border-box',
|
56
|
+
fontFamily: 'inherit',
|
57
|
+
}}
|
58
|
+
></textarea>
|
59
|
+
</div>
|
60
|
+
) : (
|
61
|
+
<SelectableSortableContainer
|
62
|
+
height={height}
|
63
|
+
schemas={schemas}
|
64
|
+
hoveringSchemaId={hoveringSchemaId}
|
65
|
+
onChangeHoveringSchemaId={onChangeHoveringSchemaId}
|
66
|
+
onSortEnd={onSortEnd}
|
67
|
+
onEdit={onEdit}
|
68
|
+
/>
|
69
|
+
)}
|
70
|
+
|
71
|
+
<div
|
72
|
+
style={{
|
73
|
+
display: 'flex',
|
74
|
+
justifyContent: 'flex-end',
|
75
|
+
cursor: 'pointer',
|
76
|
+
fontSize: '0.75rem',
|
77
|
+
}}
|
78
|
+
>
|
79
|
+
{isBulkUpdateFieldNamesMode ? (
|
80
|
+
<>
|
81
|
+
<u
|
82
|
+
onClick={() => {
|
83
|
+
const names = fieldNamesValue.split('\n');
|
84
|
+
if (names.length !== schemas.length) {
|
85
|
+
alert(i18n('errorBulkUpdateFieldName'));
|
86
|
+
} else {
|
87
|
+
changeSchemas(
|
88
|
+
names.map((value, index) => ({
|
89
|
+
key: 'key',
|
90
|
+
value,
|
91
|
+
schemaId: schemas[index].id,
|
92
|
+
}))
|
93
|
+
);
|
94
|
+
setIsBulkUpdateFieldNamesMode(false);
|
95
|
+
}
|
96
|
+
}}
|
97
|
+
>
|
98
|
+
{i18n('commitBulkUpdateFieldName')}
|
99
|
+
</u>
|
100
|
+
<span style={{ margin: '0 1rem' }}>/</span>
|
101
|
+
<u onClick={() => setIsBulkUpdateFieldNamesMode(false)}>{i18n('cancel')}</u>
|
102
|
+
</>
|
103
|
+
) : (
|
104
|
+
<u
|
105
|
+
onClick={() => {
|
106
|
+
setFieldNamesValue(schemas.map((s) => s.key).join('\n'));
|
107
|
+
setIsBulkUpdateFieldNamesMode(true);
|
108
|
+
}}
|
109
|
+
>
|
110
|
+
{i18n('bulkUpdateFieldName')}
|
111
|
+
</u>
|
112
|
+
)}
|
113
|
+
</div>
|
114
|
+
<Divider />
|
115
|
+
</div>
|
116
|
+
);
|
117
|
+
};
|
118
|
+
|
119
|
+
export default ListView;
|
@@ -1,6 +1,6 @@
|
|
1
1
|
import React, { useState, useContext } from 'react';
|
2
2
|
import { SchemaForUI, Size } from '@pdfme/common';
|
3
|
-
import { ZOOM, RULER_HEIGHT } from '../../../constants';
|
3
|
+
import { ZOOM, RULER_HEIGHT, SIDEBAR_WIDTH } from '../../../constants';
|
4
4
|
import { I18nContext } from '../../../contexts';
|
5
5
|
import backIcon from '../../../assets/icons/back.svg';
|
6
6
|
import forwardIcon from '../../../assets/icons/forward.svg';
|
@@ -13,10 +13,9 @@ export type SidebarProps = {
|
|
13
13
|
onChangeHoveringSchemaId: (id: string | null) => void;
|
14
14
|
size: Size;
|
15
15
|
pageSize: Size;
|
16
|
-
|
17
|
-
activeSchema: SchemaForUI;
|
16
|
+
activeElements: HTMLElement[];
|
18
17
|
schemas: SchemaForUI[];
|
19
|
-
onSortEnd: (
|
18
|
+
onSortEnd: (sortedSchemas: SchemaForUI[]) => void;
|
20
19
|
onEdit: (id: string) => void;
|
21
20
|
onEditEnd: () => void;
|
22
21
|
changeSchemas: (objs: { key: string; value: string | number; schemaId: string }[]) => void;
|
@@ -24,16 +23,27 @@ export type SidebarProps = {
|
|
24
23
|
};
|
25
24
|
|
26
25
|
const Sidebar = (props: SidebarProps) => {
|
27
|
-
const { height, size, addSchema } = props;
|
26
|
+
const { height, size, activeElements, schemas, addSchema } = props;
|
28
27
|
|
29
28
|
const i18n = useContext(I18nContext);
|
30
29
|
const [open, setOpen] = useState(true);
|
31
|
-
const sidebarWidth = 300;
|
32
30
|
const top = 0;
|
33
31
|
|
32
|
+
const getActiveSchemas = () => {
|
33
|
+
const ids = activeElements.map((ae) => ae.id);
|
34
|
+
return schemas.filter((s) => ids.includes(s.id));
|
35
|
+
};
|
36
|
+
|
37
|
+
const getLastActiveSchema = () => {
|
38
|
+
const activeSchemas = getActiveSchemas();
|
39
|
+
return activeSchemas[activeSchemas.length - 1];
|
40
|
+
};
|
41
|
+
|
34
42
|
return (
|
35
|
-
<div
|
36
|
-
|
43
|
+
<div
|
44
|
+
style={{ position: 'absolute', right: 0, zIndex: 1, height, width: open ? SIDEBAR_WIDTH : 0 }}
|
45
|
+
>
|
46
|
+
<div style={{ position: 'sticky', top, zIndex: 1, fontSize: '1rem' }}>
|
37
47
|
<button
|
38
48
|
style={{
|
39
49
|
position: 'absolute',
|
@@ -41,10 +51,11 @@ const Sidebar = (props: SidebarProps) => {
|
|
41
51
|
right: '0.5rem',
|
42
52
|
zIndex: 100,
|
43
53
|
border: 'none',
|
44
|
-
borderRadius:
|
54
|
+
borderRadius: 2,
|
45
55
|
padding: '0.5rem',
|
46
56
|
cursor: 'pointer',
|
47
57
|
background: '#eee',
|
58
|
+
width: 30,
|
48
59
|
}}
|
49
60
|
onClick={() => setOpen(!open)}
|
50
61
|
>
|
@@ -52,7 +63,7 @@ const Sidebar = (props: SidebarProps) => {
|
|
52
63
|
</button>
|
53
64
|
<div
|
54
65
|
style={{
|
55
|
-
width:
|
66
|
+
width: SIDEBAR_WIDTH,
|
56
67
|
height: size.height - RULER_HEIGHT * ZOOM,
|
57
68
|
display: open ? 'block' : 'none',
|
58
69
|
top,
|
@@ -65,9 +76,15 @@ const Sidebar = (props: SidebarProps) => {
|
|
65
76
|
overflowY: 'auto',
|
66
77
|
fontFamily: "'Open Sans', sans-serif",
|
67
78
|
fontWeight: 400,
|
79
|
+
textAlign: 'left',
|
80
|
+
boxSizing: 'content-box',
|
68
81
|
}}
|
69
82
|
>
|
70
|
-
{
|
83
|
+
{getActiveSchemas().length === 0 ? (
|
84
|
+
<ListView {...props} />
|
85
|
+
) : (
|
86
|
+
<DetailView {...props} activeSchema={getLastActiveSchema()} />
|
87
|
+
)}
|
71
88
|
<div
|
72
89
|
style={{
|
73
90
|
display: 'flex',
|
@@ -82,15 +99,14 @@ const Sidebar = (props: SidebarProps) => {
|
|
82
99
|
<button
|
83
100
|
style={{
|
84
101
|
padding: '0.5rem',
|
85
|
-
color: '#fff',
|
86
102
|
background: '#18a0fb',
|
87
103
|
border: 'none',
|
88
|
-
borderRadius:
|
104
|
+
borderRadius: 2,
|
89
105
|
cursor: 'pointer',
|
90
106
|
}}
|
91
107
|
onClick={addSchema}
|
92
108
|
>
|
93
|
-
<strong>{i18n('addNewField')}</strong>
|
109
|
+
<strong style={{ color: '#fff' }}>{i18n('addNewField')}</strong>
|
94
110
|
</button>
|
95
111
|
</div>
|
96
112
|
</div>
|
@@ -7,7 +7,6 @@ import { I18nContext } from '../../contexts';
|
|
7
7
|
import {
|
8
8
|
uuid,
|
9
9
|
set,
|
10
|
-
arrayMove,
|
11
10
|
cloneDeep,
|
12
11
|
initShortCuts,
|
13
12
|
destroyShortCuts,
|
@@ -99,11 +98,12 @@ const TemplateEditor = ({
|
|
99
98
|
// Assign to reference
|
100
99
|
set(tgt, key, value);
|
101
100
|
if (key === 'type') {
|
101
|
+
const type = String(value);
|
102
102
|
// set default value, text or barcode
|
103
|
-
set(tgt, 'data',
|
103
|
+
set(tgt, 'data', getSampleByType(type));
|
104
104
|
// For barcodes, adjust the height to get the correct ratio.
|
105
|
-
if (value !== 'text'
|
106
|
-
set(tgt, 'height', getKeepRatioHeightByWidth(
|
105
|
+
if (value !== 'text') {
|
106
|
+
set(tgt, 'height', getKeepRatioHeightByWidth(type, tgt.width));
|
107
107
|
}
|
108
108
|
}
|
109
109
|
|
@@ -122,12 +122,12 @@ const TemplateEditor = ({
|
|
122
122
|
};
|
123
123
|
const timeTavel = (mode: 'undo' | 'redo') => {
|
124
124
|
const isUndo = mode === 'undo';
|
125
|
-
|
125
|
+
const stack = isUndo ? past : future;
|
126
|
+
if (stack.current.length <= 0) return;
|
126
127
|
(isUndo ? future : past).current.push(cloneDeep(schemasList[pageCursor]));
|
127
128
|
const s = cloneDeep(schemasList);
|
128
|
-
s[pageCursor] =
|
129
|
+
s[pageCursor] = stack.current.pop()!;
|
129
130
|
setSchemasList(s);
|
130
|
-
onEditEnd();
|
131
131
|
};
|
132
132
|
initShortCuts({
|
133
133
|
move: (command, isShift) => {
|
@@ -167,6 +167,7 @@ const TemplateEditor = ({
|
|
167
167
|
save: () => onSaveTemplate && onSaveTemplate(modifiedTemplate),
|
168
168
|
remove: () => removeSchemas(getActiveSchemas().map((s) => s.id)),
|
169
169
|
esc: onEditEnd,
|
170
|
+
selectAll: () => onEdit(schemasList[pageCursor].map((s) => document.getElementById(s.id)!)),
|
170
171
|
});
|
171
172
|
}, [
|
172
173
|
activeElements,
|
@@ -215,24 +216,14 @@ const TemplateEditor = ({
|
|
215
216
|
setTimeout(() => onEdit([document.getElementById(s.id)!]));
|
216
217
|
};
|
217
218
|
|
218
|
-
const onSortEnd = (
|
219
|
-
|
220
|
-
commitSchemas(movedSchema);
|
219
|
+
const onSortEnd = (sortedSchemas: SchemaForUI[]) => {
|
220
|
+
commitSchemas(sortedSchemas);
|
221
221
|
};
|
222
222
|
|
223
223
|
const onChangeHoveringSchemaId = (id: string | null) => {
|
224
224
|
setHoveringSchemaId(id);
|
225
225
|
};
|
226
226
|
|
227
|
-
const getLastActiveSchema = () => {
|
228
|
-
if (activeElements.length === 0) return getInitialSchema();
|
229
|
-
const last = activeElements[activeElements.length - 1];
|
230
|
-
|
231
|
-
return schemasList[pageCursor].find((s) => s.id === last.id) || getInitialSchema();
|
232
|
-
};
|
233
|
-
|
234
|
-
const activeSchema = getLastActiveSchema();
|
235
|
-
|
236
227
|
if (error) {
|
237
228
|
return <Error size={size} error={error} />;
|
238
229
|
}
|
@@ -245,16 +236,13 @@ const TemplateEditor = ({
|
|
245
236
|
height={mainRef.current ? mainRef.current.scrollHeight : 0}
|
246
237
|
size={size}
|
247
238
|
pageSize={pageSizes[pageCursor]}
|
248
|
-
|
239
|
+
activeElements={activeElements}
|
249
240
|
schemas={schemasList[pageCursor]}
|
250
|
-
activeSchema={activeSchema}
|
251
241
|
changeSchemas={changeSchemas}
|
252
242
|
onSortEnd={onSortEnd}
|
253
243
|
onEdit={(id: string) => {
|
254
244
|
const editingElem = document.getElementById(id);
|
255
|
-
|
256
|
-
onEdit([editingElem]);
|
257
|
-
}
|
245
|
+
editingElem && onEdit([editingElem]);
|
258
246
|
}}
|
259
247
|
onEditEnd={onEditEnd}
|
260
248
|
addSchema={addSchema}
|
package/src/components/Error.tsx
CHANGED
@@ -17,13 +17,13 @@ const Error = ({ size, error }: { size: Size; error: Error }) => {
|
|
17
17
|
...size,
|
18
18
|
}}
|
19
19
|
>
|
20
|
-
<
|
20
|
+
<span style={{ color: '#fff', textAlign: 'center' }}>
|
21
21
|
<span style={{ fontSize: 'large', fontWeight: 'bold', borderBottom: '1px solid #fff' }}>
|
22
22
|
ERROR: {i18n('errorOccurred')}
|
23
23
|
</span>
|
24
24
|
<br />
|
25
25
|
<span style={{ fontSize: 'small' }}>*{error.message}</span>
|
26
|
-
</
|
26
|
+
</span>
|
27
27
|
</div>
|
28
28
|
);
|
29
29
|
};
|
package/src/components/Paper.tsx
CHANGED
@@ -42,14 +42,22 @@ const Paper = (porps: {
|
|
42
42
|
paperRefs.current[paperIndex] = e;
|
43
43
|
}
|
44
44
|
}}
|
45
|
+
onClick={(e) => {
|
46
|
+
if (
|
47
|
+
e.currentTarget === e.target &&
|
48
|
+
document &&
|
49
|
+
document.hasFocus() &&
|
50
|
+
document.activeElement instanceof HTMLElement
|
51
|
+
) {
|
52
|
+
document.activeElement.blur();
|
53
|
+
}
|
54
|
+
}}
|
45
55
|
style={{
|
46
56
|
fontFamily: `'${getFallbackFontName(font)}'`,
|
47
57
|
margin: `${RULER_HEIGHT * scale}px auto`,
|
48
58
|
position: 'relative',
|
49
59
|
backgroundImage: `url(${background})`,
|
50
|
-
backgroundSize:
|
51
|
-
backgroundPosition: 'center',
|
52
|
-
backgroundRepeat: 'no-repeat',
|
60
|
+
backgroundSize: `${paperSize.width}px ${paperSize.height}px`,
|
53
61
|
...paperSize,
|
54
62
|
}}
|
55
63
|
>
|
@@ -80,12 +80,11 @@ const Preview = ({ template, inputs, size, onChangeInput }: PreviewReactProps) =
|
|
80
80
|
backgrounds={backgrounds}
|
81
81
|
renderSchema={({ schema, index }) => {
|
82
82
|
const { key } = schema;
|
83
|
-
const data = input
|
84
|
-
|
83
|
+
const data = (input && input[key]) || '';
|
85
84
|
return (
|
86
85
|
<SchemaUI
|
87
|
-
key={
|
88
|
-
schema={Object.assign(schema, {
|
86
|
+
key={schema.id}
|
87
|
+
schema={Object.assign(schema, { data })}
|
89
88
|
editable={editable}
|
90
89
|
placeholder={template.sampledata ? template.sampledata[0][key] : ''}
|
91
90
|
tabIndex={index + 100}
|
package/src/components/Root.tsx
CHANGED
@@ -29,16 +29,11 @@ const Root = ({ size, scale, children }: Props, ref: Ref<HTMLDivElement>) => {
|
|
29
29
|
return (
|
30
30
|
<div
|
31
31
|
ref={ref}
|
32
|
-
style={{
|
33
|
-
fontFamily: 'Arial, Helvetica, sans-serif',
|
34
|
-
position: 'relative',
|
35
|
-
background: 'rgb(74, 74, 74)',
|
36
|
-
overflowY: 'auto',
|
37
|
-
...size,
|
38
|
-
}}
|
32
|
+
style={{ position: 'relative', background: 'rgb(74, 74, 74)', overflowY: 'auto', ...size }}
|
39
33
|
>
|
40
34
|
<div
|
41
35
|
style={{
|
36
|
+
margin: '0 auto',
|
42
37
|
width: size.width - RULER_HEIGHT * scale,
|
43
38
|
height: size.height - RULER_HEIGHT * scale,
|
44
39
|
}}
|
@@ -13,8 +13,6 @@ import qrcode from '../../assets/barcodeExamples/qrcode.png';
|
|
13
13
|
import upca from '../../assets/barcodeExamples/upca.png';
|
14
14
|
import upce from '../../assets/barcodeExamples/upce.png';
|
15
15
|
|
16
|
-
type Props = SchemaUIProps & { schema: BarcodeSchema };
|
17
|
-
|
18
16
|
const barcodeExampleImageObj: { [key: string]: string } = {
|
19
17
|
qrcode,
|
20
18
|
japanpost,
|
@@ -43,27 +41,35 @@ const SampleBarcode = ({ schema }: { schema: BarcodeSchema }) => (
|
|
43
41
|
|
44
42
|
const ErrorBarcode = () => (
|
45
43
|
<div style={{ display: 'flex', alignItems: 'center', justifyContent: 'center', height: '100%' }}>
|
46
|
-
<
|
44
|
+
<span
|
47
45
|
style={{
|
48
46
|
color: 'white',
|
49
47
|
background: 'red',
|
50
48
|
padding: '0.25rem',
|
51
49
|
fontSize: '12pt',
|
52
50
|
fontWeight: 'bold',
|
53
|
-
borderRadius:
|
51
|
+
borderRadius: 2,
|
54
52
|
}}
|
55
53
|
>
|
56
54
|
ERROR
|
57
|
-
</
|
55
|
+
</span>
|
58
56
|
</div>
|
59
57
|
);
|
60
58
|
|
61
|
-
const
|
62
|
-
|
59
|
+
const BarcodePreview = (props: { schema: BarcodeSchema; value: string }) => {
|
60
|
+
const { schema, value } = props;
|
61
|
+
|
62
|
+
if (value.length === 0) {
|
63
|
+
return null;
|
64
|
+
}
|
65
|
+
|
66
|
+
return validateBarcodeInput(schema.type as BarCodeType, value) ? (
|
63
67
|
<SampleBarcode schema={schema} />
|
64
68
|
) : (
|
65
69
|
<ErrorBarcode />
|
66
70
|
);
|
71
|
+
};
|
72
|
+
type Props = SchemaUIProps & { schema: BarcodeSchema };
|
67
73
|
|
68
74
|
const BarcodeSchemaUI = (
|
69
75
|
{ schema, editable, placeholder, tabIndex, onChange }: Props,
|
@@ -71,6 +77,22 @@ const BarcodeSchemaUI = (
|
|
71
77
|
) => {
|
72
78
|
const value = schema.data;
|
73
79
|
|
80
|
+
const style: React.CSSProperties = {
|
81
|
+
textAlign: 'center',
|
82
|
+
position: 'absolute',
|
83
|
+
zIndex: 2,
|
84
|
+
fontSize: '1rem',
|
85
|
+
color: '#000',
|
86
|
+
height: Number(schema.height) * ZOOM,
|
87
|
+
width: Number(schema.width) * ZOOM,
|
88
|
+
background: editable || value ? 'rgba(255, 255, 255, 0.8)' : 'none',
|
89
|
+
border: 'none',
|
90
|
+
display: 'flex',
|
91
|
+
alignItems: 'center',
|
92
|
+
justifyContent: 'center',
|
93
|
+
overflow: 'auto',
|
94
|
+
};
|
95
|
+
|
74
96
|
return (
|
75
97
|
<div
|
76
98
|
style={{
|
@@ -79,31 +101,24 @@ const BarcodeSchemaUI = (
|
|
79
101
|
display: 'flex',
|
80
102
|
alignItems: 'center',
|
81
103
|
justifyContent: 'center',
|
104
|
+
fontFamily: "'Open Sans', sans-serif",
|
82
105
|
}}
|
83
106
|
>
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
fontSize: 'inherit',
|
94
|
-
height: Number(schema.height) * ZOOM,
|
95
|
-
width: Number(schema.width) * ZOOM,
|
96
|
-
background: editable || value ? 'rgba(255, 255, 255, 0.8)' : 'none',
|
97
|
-
border: 'none',
|
98
|
-
}}
|
99
|
-
value={value}
|
100
|
-
onChange={(e) => onChange(e.target.value)}
|
101
|
-
/>
|
102
|
-
{value ? (
|
103
|
-
<ErrorOrSampleBarcode value={value} schema={schema} />
|
107
|
+
{editable ? (
|
108
|
+
<input
|
109
|
+
ref={ref}
|
110
|
+
tabIndex={tabIndex}
|
111
|
+
placeholder={placeholder}
|
112
|
+
style={style}
|
113
|
+
value={value}
|
114
|
+
onChange={(e) => onChange(e.target.value)}
|
115
|
+
/>
|
104
116
|
) : (
|
105
|
-
<
|
117
|
+
<div style={style}>
|
118
|
+
<span>{value}</span>
|
119
|
+
</div>
|
106
120
|
)}
|
121
|
+
<BarcodePreview value={value} schema={schema} />
|
107
122
|
</div>
|
108
123
|
);
|
109
124
|
};
|