scratch-paint 3.0.338 → 3.1.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/CHANGELOG.md +14 -0
- package/dist/scratch-paint.js +119 -304
- package/dist/scratch-paint.js.map +1 -1
- package/package.json +16 -25
- package/src/components/color-picker/color-picker.jsx +2 -1
- package/src/components/coming-soon/coming-soon.jsx +2 -1
- package/src/components/fixed-tools/fixed-tools.jsx +21 -21
- package/src/components/mode-tools/mode-tools.jsx +24 -24
- package/src/components/paint-editor/paint-editor.jsx +215 -213
- package/src/components/tool-select-base/tool-select-base.jsx +24 -22
- package/src/containers/color-indicator.jsx +2 -1
- package/src/lib/intl-shape.js +10 -0
- package/src/playground/playground.jsx +4 -2
- package/src/playground/reducers/intl.js +0 -7
- package/webpack.config.js +6 -1
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import paper from '@scratch/paper';
|
|
2
2
|
import classNames from 'classnames';
|
|
3
|
-
import {defineMessages,
|
|
3
|
+
import {defineMessages, useIntl} from 'react-intl';
|
|
4
4
|
import React from 'react';
|
|
5
5
|
import PropTypes from 'prop-types';
|
|
6
6
|
|
|
@@ -55,56 +55,29 @@ const messages = defineMessages({
|
|
|
55
55
|
}
|
|
56
56
|
});
|
|
57
57
|
|
|
58
|
-
const PaintEditorComponent = props =>
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
<div className={styles.
|
|
67
|
-
|
|
68
|
-
canRedo={props.canRedo}
|
|
69
|
-
canUndo={props.canUndo}
|
|
70
|
-
name={props.name}
|
|
71
|
-
onRedo={props.onRedo}
|
|
72
|
-
onUndo={props.onUndo}
|
|
73
|
-
onUpdateImage={props.onUpdateImage}
|
|
74
|
-
onUpdateName={props.onUpdateName}
|
|
75
|
-
/>
|
|
76
|
-
</div>
|
|
77
|
-
{/* Second Row */}
|
|
78
|
-
{isVector(props.format) ?
|
|
58
|
+
const PaintEditorComponent = props => {
|
|
59
|
+
const intl = useIntl();
|
|
60
|
+
return (
|
|
61
|
+
<div
|
|
62
|
+
className={styles.editorContainer}
|
|
63
|
+
dir={props.rtl ? 'rtl' : 'ltr'}
|
|
64
|
+
>
|
|
65
|
+
{props.canvas !== null ? ( // eslint-disable-line no-negated-condition
|
|
66
|
+
<div className={styles.editorContainerTop}>
|
|
67
|
+
{/* First row */}
|
|
79
68
|
<div className={styles.row}>
|
|
80
|
-
<
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
{
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
{/* stroke */}
|
|
93
|
-
<StrokeColorIndicatorComponent
|
|
94
|
-
onUpdateImage={props.onUpdateImage}
|
|
95
|
-
/>
|
|
96
|
-
{/* stroke width */}
|
|
97
|
-
<StrokeWidthIndicatorComponent
|
|
98
|
-
onUpdateImage={props.onUpdateImage}
|
|
99
|
-
/>
|
|
100
|
-
</InputGroup>
|
|
101
|
-
<InputGroup className={styles.modModeTools}>
|
|
102
|
-
<ModeToolsContainer
|
|
103
|
-
onUpdateImage={props.onUpdateImage}
|
|
104
|
-
/>
|
|
105
|
-
</InputGroup>
|
|
106
|
-
</div> :
|
|
107
|
-
isBitmap(props.format) ?
|
|
69
|
+
<FixedToolsContainer
|
|
70
|
+
canRedo={props.canRedo}
|
|
71
|
+
canUndo={props.canUndo}
|
|
72
|
+
name={props.name}
|
|
73
|
+
onRedo={props.onRedo}
|
|
74
|
+
onUndo={props.onUndo}
|
|
75
|
+
onUpdateImage={props.onUpdateImage}
|
|
76
|
+
onUpdateName={props.onUpdateName}
|
|
77
|
+
/>
|
|
78
|
+
</div>
|
|
79
|
+
{/* Second Row */}
|
|
80
|
+
{isVector(props.format) ?
|
|
108
81
|
<div className={styles.row}>
|
|
109
82
|
<InputGroup
|
|
110
83
|
className={classNames(
|
|
@@ -118,136 +91,151 @@ const PaintEditorComponent = props => (
|
|
|
118
91
|
className={styles.modMarginAfter}
|
|
119
92
|
onUpdateImage={props.onUpdateImage}
|
|
120
93
|
/>
|
|
94
|
+
{/* stroke */}
|
|
95
|
+
<StrokeColorIndicatorComponent
|
|
96
|
+
onUpdateImage={props.onUpdateImage}
|
|
97
|
+
/>
|
|
98
|
+
{/* stroke width */}
|
|
99
|
+
<StrokeWidthIndicatorComponent
|
|
100
|
+
onUpdateImage={props.onUpdateImage}
|
|
101
|
+
/>
|
|
121
102
|
</InputGroup>
|
|
122
103
|
<InputGroup className={styles.modModeTools}>
|
|
123
104
|
<ModeToolsContainer
|
|
124
105
|
onUpdateImage={props.onUpdateImage}
|
|
125
106
|
/>
|
|
126
107
|
</InputGroup>
|
|
127
|
-
</div> :
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
/>
|
|
151
|
-
<TextMode
|
|
152
|
-
textArea={props.textArea}
|
|
153
|
-
onUpdateImage={props.onUpdateImage}
|
|
154
|
-
/>
|
|
155
|
-
<LineMode
|
|
156
|
-
onUpdateImage={props.onUpdateImage}
|
|
157
|
-
/>
|
|
158
|
-
<OvalMode
|
|
159
|
-
onUpdateImage={props.onUpdateImage}
|
|
160
|
-
/>
|
|
161
|
-
<RectMode
|
|
162
|
-
onUpdateImage={props.onUpdateImage}
|
|
163
|
-
/>
|
|
108
|
+
</div> :
|
|
109
|
+
isBitmap(props.format) ?
|
|
110
|
+
<div className={styles.row}>
|
|
111
|
+
<InputGroup
|
|
112
|
+
className={classNames(
|
|
113
|
+
styles.row,
|
|
114
|
+
styles.modDashedBorder,
|
|
115
|
+
styles.modLabeledIconHeight
|
|
116
|
+
)}
|
|
117
|
+
>
|
|
118
|
+
{/* fill */}
|
|
119
|
+
<FillColorIndicatorComponent
|
|
120
|
+
className={styles.modMarginAfter}
|
|
121
|
+
onUpdateImage={props.onUpdateImage}
|
|
122
|
+
/>
|
|
123
|
+
</InputGroup>
|
|
124
|
+
<InputGroup className={styles.modModeTools}>
|
|
125
|
+
<ModeToolsContainer
|
|
126
|
+
onUpdateImage={props.onUpdateImage}
|
|
127
|
+
/>
|
|
128
|
+
</InputGroup>
|
|
129
|
+
</div> : null
|
|
130
|
+
}
|
|
164
131
|
</div>
|
|
165
132
|
) : null}
|
|
166
133
|
|
|
167
|
-
{
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
134
|
+
<div className={styles.topAlignRow}>
|
|
135
|
+
{/* Modes */}
|
|
136
|
+
{props.canvas !== null && isVector(props.format) ? ( // eslint-disable-line no-negated-condition
|
|
137
|
+
<div className={styles.modeSelector}>
|
|
138
|
+
<SelectMode
|
|
139
|
+
onUpdateImage={props.onUpdateImage}
|
|
140
|
+
/>
|
|
141
|
+
<ReshapeMode
|
|
142
|
+
onUpdateImage={props.onUpdateImage}
|
|
143
|
+
/>
|
|
144
|
+
<BrushMode
|
|
145
|
+
onUpdateImage={props.onUpdateImage}
|
|
146
|
+
/>
|
|
147
|
+
<EraserMode
|
|
148
|
+
onUpdateImage={props.onUpdateImage}
|
|
149
|
+
/>
|
|
150
|
+
<FillMode
|
|
151
|
+
onUpdateImage={props.onUpdateImage}
|
|
152
|
+
/>
|
|
153
|
+
<TextMode
|
|
154
|
+
textArea={props.textArea}
|
|
155
|
+
onUpdateImage={props.onUpdateImage}
|
|
156
|
+
/>
|
|
157
|
+
<LineMode
|
|
158
|
+
onUpdateImage={props.onUpdateImage}
|
|
159
|
+
/>
|
|
160
|
+
<OvalMode
|
|
161
|
+
onUpdateImage={props.onUpdateImage}
|
|
162
|
+
/>
|
|
163
|
+
<RectMode
|
|
164
|
+
onUpdateImage={props.onUpdateImage}
|
|
165
|
+
/>
|
|
166
|
+
</div>
|
|
167
|
+
) : null}
|
|
197
168
|
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
}
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
169
|
+
{props.canvas !== null && isBitmap(props.format) ? ( // eslint-disable-line no-negated-condition
|
|
170
|
+
<div className={styles.modeSelector}>
|
|
171
|
+
<BitBrushMode
|
|
172
|
+
onUpdateImage={props.onUpdateImage}
|
|
173
|
+
/>
|
|
174
|
+
<BitLineMode
|
|
175
|
+
onUpdateImage={props.onUpdateImage}
|
|
176
|
+
/>
|
|
177
|
+
<BitOvalMode
|
|
178
|
+
onUpdateImage={props.onUpdateImage}
|
|
179
|
+
/>
|
|
180
|
+
<BitRectMode
|
|
181
|
+
onUpdateImage={props.onUpdateImage}
|
|
182
|
+
/>
|
|
183
|
+
<TextMode
|
|
184
|
+
isBitmap
|
|
185
|
+
textArea={props.textArea}
|
|
186
|
+
onUpdateImage={props.onUpdateImage}
|
|
187
|
+
/>
|
|
188
|
+
<BitFillMode
|
|
189
|
+
onUpdateImage={props.onUpdateImage}
|
|
190
|
+
/>
|
|
191
|
+
<BitEraserMode
|
|
192
|
+
onUpdateImage={props.onUpdateImage}
|
|
193
|
+
/>
|
|
194
|
+
<BitSelectMode
|
|
195
|
+
onUpdateImage={props.onUpdateImage}
|
|
196
|
+
/>
|
|
197
|
+
</div>
|
|
198
|
+
) : null}
|
|
199
|
+
|
|
200
|
+
<div className={styles.controlsContainer}>
|
|
201
|
+
{/* Canvas */}
|
|
202
|
+
<ScrollableCanvas
|
|
203
|
+
canvas={props.canvas}
|
|
204
|
+
hideScrollbars={props.isEyeDropping}
|
|
205
|
+
style={styles.canvasContainer}
|
|
206
|
+
>
|
|
207
|
+
<PaperCanvas
|
|
208
|
+
canvasRef={props.setCanvas}
|
|
209
|
+
image={props.image}
|
|
210
|
+
imageFormat={props.imageFormat}
|
|
211
|
+
imageId={props.imageId}
|
|
212
|
+
rotationCenterX={props.rotationCenterX}
|
|
213
|
+
rotationCenterY={props.rotationCenterY}
|
|
214
|
+
zoomLevelId={props.zoomLevelId}
|
|
215
|
+
onUpdateImage={props.onUpdateImage}
|
|
216
|
+
/>
|
|
217
|
+
<textarea
|
|
218
|
+
className={styles.textArea}
|
|
219
|
+
ref={props.setTextArea}
|
|
220
|
+
spellCheck={false}
|
|
221
|
+
/>
|
|
222
|
+
{props.isEyeDropping &&
|
|
223
|
+
props.colorInfo !== null &&
|
|
224
|
+
!props.colorInfo.hideLoupe ? (
|
|
225
|
+
<Box className={styles.colorPickerWrapper}>
|
|
226
|
+
<Loupe
|
|
227
|
+
colorInfo={props.colorInfo}
|
|
228
|
+
pixelRatio={paper.project.view.pixelRatio}
|
|
229
|
+
/>
|
|
230
|
+
</Box>
|
|
231
|
+
) : null
|
|
232
|
+
}
|
|
233
|
+
</ScrollableCanvas>
|
|
234
|
+
<div className={styles.canvasControls}>
|
|
235
|
+
{isVector(props.format) ?
|
|
248
236
|
<Button
|
|
249
237
|
className={styles.bitmapButton}
|
|
250
|
-
onClick={props.
|
|
238
|
+
onClick={props.onSwitchToBitmap}
|
|
251
239
|
>
|
|
252
240
|
<img
|
|
253
241
|
className={styles.bitmapButtonIcon}
|
|
@@ -255,53 +243,68 @@ const PaintEditorComponent = props => (
|
|
|
255
243
|
src={bitmapIcon}
|
|
256
244
|
/>
|
|
257
245
|
<span className={styles.buttonText}>
|
|
258
|
-
{
|
|
246
|
+
{intl.formatMessage(messages.bitmap)}
|
|
259
247
|
</span>
|
|
260
|
-
</Button> :
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
className={styles.
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
248
|
+
</Button> :
|
|
249
|
+
isBitmap(props.format) ?
|
|
250
|
+
<Button
|
|
251
|
+
className={styles.bitmapButton}
|
|
252
|
+
onClick={props.onSwitchToVector}
|
|
253
|
+
>
|
|
254
|
+
<img
|
|
255
|
+
className={styles.bitmapButtonIcon}
|
|
256
|
+
draggable={false}
|
|
257
|
+
src={bitmapIcon}
|
|
258
|
+
/>
|
|
259
|
+
<span className={styles.buttonText}>
|
|
260
|
+
{intl.formatMessage(messages.vector)}
|
|
261
|
+
</span>
|
|
262
|
+
</Button> : null
|
|
263
|
+
}
|
|
264
|
+
{/* Zoom controls */}
|
|
265
|
+
<InputGroup className={styles.zoomControls}>
|
|
266
|
+
<ButtonGroup>
|
|
267
|
+
<Button
|
|
268
|
+
className={styles.buttonGroupButton}
|
|
269
|
+
onClick={props.onZoomOut}
|
|
270
|
+
>
|
|
271
|
+
<img
|
|
272
|
+
alt="Zoom Out"
|
|
273
|
+
className={styles.buttonGroupButtonIcon}
|
|
274
|
+
draggable={false}
|
|
275
|
+
src={zoomOutIcon}
|
|
276
|
+
/>
|
|
277
|
+
</Button>
|
|
278
|
+
<Button
|
|
279
|
+
className={styles.buttonGroupButton}
|
|
280
|
+
onClick={props.onZoomReset}
|
|
281
|
+
>
|
|
282
|
+
<img
|
|
283
|
+
alt="Zoom Reset"
|
|
284
|
+
className={styles.buttonGroupButtonIcon}
|
|
285
|
+
draggable={false}
|
|
286
|
+
src={zoomResetIcon}
|
|
287
|
+
/>
|
|
288
|
+
</Button>
|
|
289
|
+
<Button
|
|
290
|
+
className={styles.buttonGroupButton}
|
|
291
|
+
onClick={props.onZoomIn}
|
|
292
|
+
>
|
|
293
|
+
<img
|
|
294
|
+
alt="Zoom In"
|
|
295
|
+
className={styles.buttonGroupButtonIcon}
|
|
296
|
+
draggable={false}
|
|
297
|
+
src={zoomInIcon}
|
|
298
|
+
/>
|
|
299
|
+
</Button>
|
|
300
|
+
</ButtonGroup>
|
|
301
|
+
</InputGroup>
|
|
302
|
+
</div>
|
|
300
303
|
</div>
|
|
301
304
|
</div>
|
|
302
305
|
</div>
|
|
303
|
-
|
|
304
|
-
|
|
306
|
+
);
|
|
307
|
+
};
|
|
305
308
|
|
|
306
309
|
PaintEditorComponent.propTypes = {
|
|
307
310
|
canRedo: PropTypes.func.isRequired,
|
|
@@ -315,7 +318,6 @@ PaintEditorComponent.propTypes = {
|
|
|
315
318
|
]),
|
|
316
319
|
imageFormat: PropTypes.string,
|
|
317
320
|
imageId: PropTypes.string,
|
|
318
|
-
intl: intlShape,
|
|
319
321
|
isEyeDropping: PropTypes.bool,
|
|
320
322
|
name: PropTypes.string,
|
|
321
323
|
onRedo: PropTypes.func.isRequired,
|
|
@@ -336,4 +338,4 @@ PaintEditorComponent.propTypes = {
|
|
|
336
338
|
zoomLevelId: PropTypes.string
|
|
337
339
|
};
|
|
338
340
|
|
|
339
|
-
export default
|
|
341
|
+
export default PaintEditorComponent;
|
|
@@ -1,31 +1,34 @@
|
|
|
1
1
|
import classNames from 'classnames';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
import PropTypes from 'prop-types';
|
|
4
|
-
import {
|
|
4
|
+
import {useIntl} from 'react-intl';
|
|
5
5
|
|
|
6
6
|
import Button from '../button/button.jsx';
|
|
7
7
|
|
|
8
8
|
import styles from './tool-select-base.css';
|
|
9
9
|
|
|
10
|
-
const ToolSelectComponent = props =>
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
10
|
+
const ToolSelectComponent = props => {
|
|
11
|
+
const intl = useIntl();
|
|
12
|
+
return (
|
|
13
|
+
<Button
|
|
14
|
+
className={
|
|
15
|
+
classNames(props.className, styles.modToolSelect, {
|
|
16
|
+
[styles.isSelected]: props.isSelected
|
|
17
|
+
})
|
|
18
|
+
}
|
|
19
|
+
disabled={props.disabled}
|
|
20
|
+
title={intl.formatMessage(props.imgDescriptor)}
|
|
21
|
+
onClick={props.onMouseDown}
|
|
22
|
+
>
|
|
23
|
+
<img
|
|
24
|
+
alt={intl.formatMessage(props.imgDescriptor)}
|
|
25
|
+
className={styles.toolSelectIcon}
|
|
26
|
+
draggable={false}
|
|
27
|
+
src={props.imgSrc}
|
|
28
|
+
/>
|
|
29
|
+
</Button>
|
|
30
|
+
);
|
|
31
|
+
};
|
|
29
32
|
|
|
30
33
|
ToolSelectComponent.propTypes = {
|
|
31
34
|
className: PropTypes.string,
|
|
@@ -36,9 +39,8 @@ ToolSelectComponent.propTypes = {
|
|
|
36
39
|
id: PropTypes.string
|
|
37
40
|
}).isRequired,
|
|
38
41
|
imgSrc: PropTypes.string.isRequired,
|
|
39
|
-
intl: intlShape.isRequired,
|
|
40
42
|
isSelected: PropTypes.bool.isRequired,
|
|
41
43
|
onMouseDown: PropTypes.func.isRequired
|
|
42
44
|
};
|
|
43
45
|
|
|
44
|
-
export default
|
|
46
|
+
export default ToolSelectComponent;
|
|
@@ -2,7 +2,8 @@ import PropTypes from 'prop-types';
|
|
|
2
2
|
import React from 'react';
|
|
3
3
|
import bindAll from 'lodash.bindall';
|
|
4
4
|
import parseColor from 'parse-color';
|
|
5
|
-
import {injectIntl
|
|
5
|
+
import {injectIntl} from 'react-intl';
|
|
6
|
+
import intlShape from '../lib/intl-shape.js';
|
|
6
7
|
|
|
7
8
|
import {getSelectedLeafItems} from '../helper/selection';
|
|
8
9
|
import Formats, {isBitmap} from '../lib/format';
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import PropTypes from 'prop-types';
|
|
2
|
+
|
|
3
|
+
// intlShape was removed in react-intl@3 and replaced with a TypeScript interface.
|
|
4
|
+
// These are some of the commonly used properties from the intl object.
|
|
5
|
+
const intlShape = PropTypes.shape({
|
|
6
|
+
locale: PropTypes.string.isRequired,
|
|
7
|
+
formatMessage: PropTypes.func.isRequired
|
|
8
|
+
});
|
|
9
|
+
|
|
10
|
+
export default intlShape;
|
|
@@ -182,10 +182,12 @@ class Playground extends React.Component {
|
|
|
182
182
|
}
|
|
183
183
|
|
|
184
184
|
}
|
|
185
|
-
|
|
185
|
+
|
|
186
|
+
const root = ReactDOM.createRoot(appTarget);
|
|
187
|
+
root.render(
|
|
186
188
|
<Provider store={store}>
|
|
187
189
|
<IntlProvider>
|
|
188
190
|
<Playground />
|
|
189
191
|
</IntlProvider>
|
|
190
192
|
</Provider>
|
|
191
|
-
)
|
|
193
|
+
);
|
|
@@ -1,15 +1,8 @@
|
|
|
1
|
-
import {addLocaleData} from 'react-intl';
|
|
2
1
|
import {updateIntl as superUpdateIntl} from 'react-intl-redux';
|
|
3
2
|
import {IntlProvider, intlReducer} from 'react-intl-redux';
|
|
4
3
|
|
|
5
|
-
import localeData from 'scratch-l10n';
|
|
6
4
|
import paintMessages from 'scratch-l10n/locales/paint-editor-msgs';
|
|
7
5
|
|
|
8
|
-
Object.keys(localeData).forEach(locale => {
|
|
9
|
-
// TODO: will need to handle locales not in the default intl - see www/custom-locales
|
|
10
|
-
addLocaleData(localeData[locale].localeData);
|
|
11
|
-
});
|
|
12
|
-
|
|
13
6
|
const intlInitialState = {
|
|
14
7
|
intl: {
|
|
15
8
|
defaultLocale: 'en',
|
package/webpack.config.js
CHANGED
|
@@ -17,7 +17,12 @@ const base = {
|
|
|
17
17
|
rules: [{
|
|
18
18
|
test: /\.jsx?$/,
|
|
19
19
|
loader: 'babel-loader',
|
|
20
|
-
include:
|
|
20
|
+
include: [
|
|
21
|
+
path.resolve(__dirname, 'src'),
|
|
22
|
+
path.join(__dirname, 'node_modules/react-intl'),
|
|
23
|
+
path.join(__dirname, 'node_modules/intl-messageformat'),
|
|
24
|
+
path.join(__dirname, 'node_modules/intl-messageformat-parser')
|
|
25
|
+
],
|
|
21
26
|
options: {
|
|
22
27
|
plugins: ['transform-object-rest-spread'],
|
|
23
28
|
presets: [
|