react-image-annotate-master-custom 0.0.1

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 (73) hide show
  1. package/Annotator/index.js +164 -0
  2. package/Annotator/reducers/combine-reducers.js +14 -0
  3. package/Annotator/reducers/convert-expanding-line-to-polygon.js +73 -0
  4. package/Annotator/reducers/fix-twisted.js +4 -0
  5. package/Annotator/reducers/general-reducer.js +1073 -0
  6. package/Annotator/reducers/get-active-image.js +27 -0
  7. package/Annotator/reducers/get-implied-video-regions.js +180 -0
  8. package/Annotator/reducers/history-handler.js +38 -0
  9. package/Annotator/reducers/image-reducer.js +20 -0
  10. package/Annotator/reducers/video-reducer.js +88 -0
  11. package/ClassSelectionMenu/index.js +135 -0
  12. package/Crosshairs/index.js +53 -0
  13. package/DebugSidebarBox/index.js +20 -0
  14. package/DemoSite/Editor.js +194 -0
  15. package/DemoSite/ErrorBoundaryDialog.js +64 -0
  16. package/DemoSite/index.js +69 -0
  17. package/FullImageSegmentationAnnotator/index.js +7 -0
  18. package/HighlightBox/index.js +105 -0
  19. package/HistorySidebarBox/index.js +71 -0
  20. package/ImageCanvas/index.js +428 -0
  21. package/ImageCanvas/region-tools.js +165 -0
  22. package/ImageCanvas/styles.js +31 -0
  23. package/ImageCanvas/use-mouse.js +180 -0
  24. package/ImageCanvas/use-project-box.js +27 -0
  25. package/ImageCanvas/use-wasd-mode.js +62 -0
  26. package/ImageMask/index.js +133 -0
  27. package/ImageMask/load-image.js +25 -0
  28. package/ImageSelectorSidebarBox/index.js +60 -0
  29. package/KeyframeTimeline/get-time-string.js +27 -0
  30. package/KeyframeTimeline/index.js +233 -0
  31. package/KeyframesSelectorSidebarBox/index.js +93 -0
  32. package/LandingPage/index.js +159 -0
  33. package/MainLayout/icon-dictionary.js +104 -0
  34. package/MainLayout/index.js +359 -0
  35. package/MainLayout/styles.js +25 -0
  36. package/MainLayout/types.js +0 -0
  37. package/MainLayout/use-implied-video-regions.js +13 -0
  38. package/PointDistances/index.js +73 -0
  39. package/PreventScrollToParents/index.js +51 -0
  40. package/README.md +101 -0
  41. package/RegionLabel/index.js +197 -0
  42. package/RegionLabel/styles.js +48 -0
  43. package/RegionSelectAndTransformBoxes/index.js +166 -0
  44. package/RegionSelectorSidebarBox/index.js +248 -0
  45. package/RegionSelectorSidebarBox/styles.js +53 -0
  46. package/RegionShapes/index.js +275 -0
  47. package/RegionTags/index.js +138 -0
  48. package/SettingsDialog/index.js +52 -0
  49. package/SettingsProvider/index.js +53 -0
  50. package/Shortcuts/ShortcutField.js +46 -0
  51. package/Shortcuts/index.js +133 -0
  52. package/ShortcutsManager/index.js +155 -0
  53. package/Sidebar/index.js +69 -0
  54. package/SidebarBoxContainer/index.js +93 -0
  55. package/SmallToolButton/index.js +42 -0
  56. package/TagsSidebarBox/index.js +105 -0
  57. package/TaskDescriptionSidebarBox/index.js +58 -0
  58. package/Theme/index.js +30 -0
  59. package/VideoOrImageCanvasBackground/index.js +151 -0
  60. package/colors.js +14 -0
  61. package/hooks/use-event-callback.js +10 -0
  62. package/hooks/use-exclude-pattern.js +24 -0
  63. package/hooks/use-load-image.js +26 -0
  64. package/hooks/use-window-size.js +46 -0
  65. package/hooks/xpattern.js +1 -0
  66. package/index.js +3 -0
  67. package/lib.js +3 -0
  68. package/package.json +91 -0
  69. package/stories.js +5 -0
  70. package/utils/get-from-local-storage.js +7 -0
  71. package/utils/get-hotkey-help-text.js +9 -0
  72. package/utils/get-landmarks-with-transform.js +40 -0
  73. package/utils/set-in-local-storage.js +3 -0
@@ -0,0 +1,27 @@
1
+ import { getIn } from "seamless-immutable";
2
+ export default (function (state) {
3
+ var currentImageIndex = null,
4
+ pathToActiveImage,
5
+ activeImage;
6
+
7
+ if (state.annotationType === "image") {
8
+ currentImageIndex = state.selectedImage;
9
+
10
+ if (currentImageIndex === -1) {
11
+ currentImageIndex = null;
12
+ activeImage = null;
13
+ } else {
14
+ pathToActiveImage = ["images", currentImageIndex];
15
+ activeImage = getIn(state, pathToActiveImage);
16
+ }
17
+ } else if (state.annotationType === "video") {
18
+ pathToActiveImage = ["keyframes", state.currentVideoTime || 0];
19
+ activeImage = getIn(state, pathToActiveImage) || null;
20
+ }
21
+
22
+ return {
23
+ currentImageIndex: currentImageIndex,
24
+ pathToActiveImage: pathToActiveImage,
25
+ activeImage: activeImage
26
+ };
27
+ });
@@ -0,0 +1,180 @@
1
+ import _slicedToArray from "@babel/runtime/helpers/esm/slicedToArray";
2
+ import _objectSpread from "@babel/runtime/helpers/esm/objectSpread";
3
+ var emptyArr = [];
4
+ export default (function (keyframes, time) {
5
+ if (keyframes[time || 0]) {
6
+ return keyframes[time || 0].regions;
7
+ } // Get surrounding video keyframes
8
+
9
+
10
+ var keyframeTimes = Object.keys(keyframes).map(function (a) {
11
+ return parseInt(a);
12
+ }).filter(function (a) {
13
+ return !isNaN(a);
14
+ });
15
+ if (keyframeTimes.length === 0) return emptyArr;
16
+ keyframeTimes.sort(function (a, b) {
17
+ return a - b;
18
+ });
19
+ var nextKeyframeTimeIndex = keyframeTimes.findIndex(function (kt) {
20
+ return kt >= time;
21
+ });
22
+
23
+ if (nextKeyframeTimeIndex === -1) {
24
+ return keyframes[keyframeTimes[keyframeTimes.length - 1]].regions || emptyArr;
25
+ } else if (nextKeyframeTimeIndex === 0) {
26
+ return emptyArr;
27
+ }
28
+
29
+ var t1 = keyframeTimes[nextKeyframeTimeIndex - 1];
30
+ var prevKeyframe = keyframes[t1];
31
+ var t2 = keyframeTimes[nextKeyframeTimeIndex];
32
+ var nextKeyframe = keyframes[t2];
33
+ var prevRegionMap = {},
34
+ nextRegionMap = {};
35
+ var _iteratorNormalCompletion = true;
36
+ var _didIteratorError = false;
37
+ var _iteratorError = undefined;
38
+
39
+ try {
40
+ for (var _iterator = prevKeyframe.regions[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
41
+ var region = _step.value;
42
+ prevRegionMap[region.id] = region;
43
+ }
44
+ } catch (err) {
45
+ _didIteratorError = true;
46
+ _iteratorError = err;
47
+ } finally {
48
+ try {
49
+ if (!_iteratorNormalCompletion && _iterator.return != null) {
50
+ _iterator.return();
51
+ }
52
+ } finally {
53
+ if (_didIteratorError) {
54
+ throw _iteratorError;
55
+ }
56
+ }
57
+ }
58
+
59
+ var _iteratorNormalCompletion2 = true;
60
+ var _didIteratorError2 = false;
61
+ var _iteratorError2 = undefined;
62
+
63
+ try {
64
+ for (var _iterator2 = nextKeyframe.regions[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
65
+ var _region = _step2.value;
66
+ nextRegionMap[_region.id] = _region;
67
+ }
68
+ } catch (err) {
69
+ _didIteratorError2 = true;
70
+ _iteratorError2 = err;
71
+ } finally {
72
+ try {
73
+ if (!_iteratorNormalCompletion2 && _iterator2.return != null) {
74
+ _iterator2.return();
75
+ }
76
+ } finally {
77
+ if (_didIteratorError2) {
78
+ throw _iteratorError2;
79
+ }
80
+ }
81
+ }
82
+
83
+ var impliedRegions = []; // Weighted time coefficients for linear transition
84
+
85
+ var w1 = (t2 - time) / (t2 - t1);
86
+ var w2 = 1 - w1;
87
+
88
+ var _loop = function _loop(regionId) {
89
+ var _ref = [prevRegionMap[regionId], nextRegionMap[regionId]],
90
+ prev = _ref[0],
91
+ next = _ref[1];
92
+
93
+ if (!next) {
94
+ impliedRegions.push(_objectSpread({}, prev, {
95
+ highlighted: false,
96
+ editingLabels: false
97
+ }));
98
+ return "continue";
99
+ }
100
+
101
+ switch (prev.type) {
102
+ case "point":
103
+ {
104
+ impliedRegions.push(_objectSpread({}, prev, {
105
+ highlighted: false,
106
+ editingLabels: false,
107
+ x: prev.x * w1 + next.x * w2,
108
+ y: prev.y * w1 + next.y * w2
109
+ }));
110
+ break;
111
+ }
112
+
113
+ case "box":
114
+ {
115
+ impliedRegions.push(_objectSpread({}, prev, {
116
+ highlighted: false,
117
+ editingLabels: false,
118
+ x: prev.x * w1 + next.x * w2,
119
+ y: prev.y * w1 + next.y * w2,
120
+ w: prev.w * w1 + next.w * w2,
121
+ h: prev.h * w1 + next.h * w2
122
+ }));
123
+ break;
124
+ }
125
+
126
+ case "polygon":
127
+ {
128
+ if (next.points.length === prev.points.length) {
129
+ impliedRegions.push(_objectSpread({}, prev, {
130
+ highlighted: false,
131
+ editingLabels: false,
132
+ points: prev.points.map(function (pp, i) {
133
+ return [pp[0] * w1 + next.points[i][0] * w2, pp[1] * w1 + next.points[i][1] * w2];
134
+ })
135
+ }));
136
+ } else {
137
+ impliedRegions.push(prev);
138
+ }
139
+
140
+ break;
141
+ }
142
+
143
+ case "keypoints":
144
+ {
145
+ var newPoints = {};
146
+
147
+ for (var _i = 0, _Object$entries = Object.entries(prev.points); _i < _Object$entries.length; _i++) {
148
+ var _ref4 = _Object$entries[_i];
149
+
150
+ var _ref3 = _slicedToArray(_ref4, 2);
151
+
152
+ var pointId = _ref3[0];
153
+ var prevPoint = _ref3[1];
154
+ newPoints[pointId] = {
155
+ x: prevPoint.x * w1 + next.points[pointId].x * w2,
156
+ y: prevPoint.y * w1 + next.points[pointId].y * w2
157
+ };
158
+ }
159
+
160
+ impliedRegions.push(_objectSpread({}, prev, {
161
+ highlighted: false,
162
+ editingLabels: false,
163
+ points: newPoints
164
+ }));
165
+ break;
166
+ }
167
+
168
+ default:
169
+ break;
170
+ }
171
+ };
172
+
173
+ for (var regionId in prevRegionMap) {
174
+ var _ret = _loop(regionId);
175
+
176
+ if (_ret === "continue") continue;
177
+ }
178
+
179
+ return impliedRegions;
180
+ });
@@ -0,0 +1,38 @@
1
+ import { setIn, updateIn, asMutable, without } from "seamless-immutable";
2
+ import moment from "moment";
3
+ var typesToSaveWithHistory = {
4
+ BEGIN_BOX_TRANSFORM: "Transform/Move Box",
5
+ BEGIN_MOVE_POINT: "Move Point",
6
+ DELETE_REGION: "Delete Region"
7
+ };
8
+ export var saveToHistory = function saveToHistory(state, name) {
9
+ return updateIn(state, ["history"], function (h) {
10
+ return [{
11
+ time: moment().toDate(),
12
+ state: without(state, "history"),
13
+ name: name
14
+ }].concat((h || []).slice(0, 9));
15
+ });
16
+ };
17
+ export default (function (reducer) {
18
+ return function (state, action) {
19
+ var prevState = state;
20
+ var nextState = reducer(state, action);
21
+
22
+ if (action.type === "RESTORE_HISTORY") {
23
+ if (state.history.length > 0) {
24
+ return setIn(nextState.history[0].state, ["history"], nextState.history.slice(1));
25
+ }
26
+ } else {
27
+ if (prevState !== nextState && Object.keys(typesToSaveWithHistory).includes(action.type)) {
28
+ return setIn(nextState, ["history"], [{
29
+ time: moment().toDate(),
30
+ state: without(prevState, "history"),
31
+ name: typesToSaveWithHistory[action.type] || action.type
32
+ }].concat(nextState.history || []).slice(0, 9));
33
+ }
34
+ }
35
+
36
+ return nextState;
37
+ };
38
+ });
@@ -0,0 +1,20 @@
1
+ import { setIn } from "seamless-immutable";
2
+ import getActiveImage from "./get-active-image";
3
+ export default (function (state, action) {
4
+ var _getActiveImage = getActiveImage(state),
5
+ currentImageIndex = _getActiveImage.currentImageIndex,
6
+ pathToActiveImage = _getActiveImage.pathToActiveImage,
7
+ activeImage = _getActiveImage.activeImage;
8
+
9
+ switch (action.type) {
10
+ case "IMAGE_OR_VIDEO_LOADED":
11
+ {
12
+ return setIn(state, ["images", currentImageIndex, "pixelSize"], {
13
+ w: action.metadata.naturalWidth,
14
+ h: action.metadata.naturalHeight
15
+ });
16
+ }
17
+ }
18
+
19
+ return state;
20
+ });
@@ -0,0 +1,88 @@
1
+ import { setIn, without } from "seamless-immutable";
2
+ import getImpliedVideoRegions from "./get-implied-video-regions";
3
+ import { saveToHistory } from "./history-handler.js";
4
+ export default (function (state, action) {
5
+ var copyImpliedRegions = function copyImpliedRegions() {
6
+ return setIn(saveToHistory(state, "Add Keyframe"), ["keyframes", state.currentVideoTime || 0], {
7
+ regions: getImpliedVideoRegions(state.keyframes, state.currentVideoTime)
8
+ });
9
+ };
10
+
11
+ switch (action.type) {
12
+ case "IMAGE_OR_VIDEO_LOADED":
13
+ {
14
+ var duration = action.metadata.duration;
15
+
16
+ if (typeof duration === "number") {
17
+ return setIn(state, ["videoDuration"], duration * 1000);
18
+ }
19
+ }
20
+
21
+ case "HEADER_BUTTON_CLICKED":
22
+ {
23
+ switch (action.buttonName.toLowerCase()) {
24
+ case "play":
25
+ return setIn(state, ["videoPlaying"], true);
26
+
27
+ case "pause":
28
+ return setIn(state, ["videoPlaying"], false);
29
+ }
30
+ }
31
+
32
+ case "CHANGE_VIDEO_TIME":
33
+ {
34
+ return setIn(state, ["currentVideoTime"], action.newTime);
35
+ }
36
+
37
+ case "CHANGE_VIDEO_PLAYING":
38
+ {
39
+ return setIn(state, ["videoPlaying"], action.isPlaying);
40
+ }
41
+
42
+ case "DELETE_KEYFRAME":
43
+ {
44
+ return setIn(state, ["keyframes"], without(state.keyframes, action.time));
45
+ }
46
+
47
+ default:
48
+ break;
49
+ } // Before the user modifies regions, copy the interpolated regions over to a
50
+ // new keyframe
51
+
52
+
53
+ if (!state.keyframes[state.currentVideoTime]) {
54
+ switch (action.type) {
55
+ case "BEGIN_BOX_TRANSFORM":
56
+ case "BEGIN_MOVE_POINT":
57
+ case "BEGIN_MOVE_KEYPOINT":
58
+ case "BEGIN_MOVE_POLYGON_POINT":
59
+ case "ADD_POLYGON_POINT":
60
+ case "SELECT_REGION":
61
+ case "CHANGE_REGION":
62
+ case "DELETE_REGION":
63
+ case "OPEN_REGION_EDITOR":
64
+ return copyImpliedRegions();
65
+
66
+ case "MOUSE_DOWN":
67
+ {
68
+ switch (state.selectedTool) {
69
+ case "create-point":
70
+ case "create-polygon":
71
+ case "create-box":
72
+ case "create-keypoints":
73
+ return copyImpliedRegions();
74
+
75
+ default:
76
+ break;
77
+ }
78
+
79
+ break;
80
+ }
81
+
82
+ default:
83
+ break;
84
+ }
85
+ }
86
+
87
+ return state;
88
+ });
@@ -0,0 +1,135 @@
1
+ import React, { useEffect } from "react";
2
+ import { styled } from "@mui/material/styles";
3
+ import { createTheme, ThemeProvider } from "@mui/material/styles";
4
+ import Box from "@mui/material/Box";
5
+ import * as muiColors from "@mui/material/colors";
6
+ import SidebarBoxContainer from "../SidebarBoxContainer";
7
+ import colors from "../colors";
8
+ import BallotIcon from "@mui/icons-material/Ballot";
9
+ import capitalize from "lodash/capitalize";
10
+ import classnames from "classnames";
11
+ var theme = createTheme();
12
+ var LabelContainer = styled("div")(function (_ref) {
13
+ var theme = _ref.theme;
14
+ return {
15
+ display: "flex",
16
+ paddingTop: 4,
17
+ paddingBottom: 4,
18
+ paddingLeft: 16,
19
+ paddingRight: 16,
20
+ alignItems: "center",
21
+ cursor: "pointer",
22
+ opacity: 0.7,
23
+ backgroundColor: "#fff",
24
+ "&:hover": {
25
+ opacity: 1
26
+ },
27
+ "&.selected": {
28
+ opacity: 1,
29
+ fontWeight: "bold"
30
+ }
31
+ };
32
+ });
33
+ var Circle = styled("div")(function (_ref2) {
34
+ var theme = _ref2.theme;
35
+ return {
36
+ width: 12,
37
+ height: 12,
38
+ borderRadius: 12,
39
+ marginRight: 8
40
+ };
41
+ });
42
+ var Label = styled("div")(function (_ref3) {
43
+ var theme = _ref3.theme;
44
+ return {
45
+ fontSize: 11
46
+ };
47
+ });
48
+ var DashSep = styled("div")(function (_ref4) {
49
+ var theme = _ref4.theme;
50
+ return {
51
+ flexGrow: 1,
52
+ borderBottom: "2px dotted ".concat(muiColors.grey[300]),
53
+ marginLeft: 8,
54
+ marginRight: 8
55
+ };
56
+ });
57
+ var Number = styled("div")(function (_ref5) {
58
+ var theme = _ref5.theme;
59
+ return {
60
+ fontSize: 11,
61
+ textAlign: "center",
62
+ minWidth: 14,
63
+ paddingTop: 2,
64
+ paddingBottom: 2,
65
+ fontWeight: "bold",
66
+ color: muiColors.grey[700]
67
+ };
68
+ });
69
+ export var ClassSelectionMenu = function ClassSelectionMenu(_ref6) {
70
+ var selectedCls = _ref6.selectedCls,
71
+ regionClsList = _ref6.regionClsList,
72
+ onSelectCls = _ref6.onSelectCls;
73
+ useEffect(function () {
74
+ var keyMapping = {};
75
+
76
+ var _loop = function _loop(i) {
77
+ keyMapping[i + 1] = function () {
78
+ return onSelectCls(regionClsList[i]);
79
+ };
80
+ };
81
+
82
+ for (var i = 0; i < 9 && i < regionClsList.length; i++) {
83
+ _loop(i);
84
+ }
85
+
86
+ var onKeyDown = function onKeyDown(e) {
87
+ if (keyMapping[e.key]) {
88
+ keyMapping[e.key]();
89
+ e.preventDefault();
90
+ e.stopPropagation();
91
+ }
92
+ };
93
+
94
+ window.addEventListener("keydown", onKeyDown);
95
+ return function () {
96
+ return window.removeEventListener("keydown", onKeyDown);
97
+ };
98
+ }, [regionClsList, selectedCls]);
99
+ return React.createElement(ThemeProvider, {
100
+ theme: theme
101
+ }, React.createElement(SidebarBoxContainer, {
102
+ title: "Classifications",
103
+ subTitle: "",
104
+ icon: React.createElement(BallotIcon, {
105
+ style: {
106
+ color: muiColors.grey[700]
107
+ }
108
+ }),
109
+ expandedByDefault: true
110
+ }, regionClsList.map(function (label, index) {
111
+ return React.createElement(LabelContainer, {
112
+ className: classnames({
113
+ selected: label === selectedCls
114
+ }),
115
+ onClick: function onClick() {
116
+ return onSelectCls(label);
117
+ }
118
+ }, React.createElement(Circle, {
119
+ style: {
120
+ backgroundColor: colors[index % colors.length]
121
+ }
122
+ }), React.createElement(Label, {
123
+ className: classnames({
124
+ selected: label === selectedCls
125
+ })
126
+ }, capitalize(label)), React.createElement(DashSep, null), React.createElement(Number, {
127
+ className: classnames({
128
+ selected: label === selectedCls
129
+ })
130
+ }, index < 9 ? "Key [".concat(index + 1, "]") : ""));
131
+ }), React.createElement(Box, {
132
+ pb: 2
133
+ })));
134
+ };
135
+ export default ClassSelectionMenu;
@@ -0,0 +1,53 @@
1
+ import _slicedToArray from "@babel/runtime/helpers/esm/slicedToArray";
2
+ import React, { Fragment, useEffect, useState } from "react";
3
+ export var Crosshairs = function Crosshairs(_ref) {
4
+ var mousePosition = _ref.mousePosition,
5
+ x = _ref.x,
6
+ y = _ref.y;
7
+
8
+ var _useState = useState(),
9
+ _useState2 = _slicedToArray(_useState, 2),
10
+ forceRenderState = _useState2[0],
11
+ changeForceRenderState = _useState2[1];
12
+
13
+ if (mousePosition) {
14
+ x = mousePosition.current.x;
15
+ y = mousePosition.current.y;
16
+ }
17
+
18
+ useEffect(function () {
19
+ if (!mousePosition) return;
20
+ var interval = setInterval(function () {
21
+ if (x !== mousePosition.current.x || y !== mousePosition.current.y) {
22
+ changeForceRenderState([mousePosition.current.x, mousePosition.current.y]);
23
+ }
24
+ }, 10);
25
+ return function () {
26
+ return clearInterval(interval);
27
+ };
28
+ });
29
+ return React.createElement(Fragment, null, React.createElement("div", {
30
+ style: {
31
+ position: "absolute",
32
+ height: "100%",
33
+ width: 1,
34
+ zIndex: 10,
35
+ backgroundColor: "#f00",
36
+ left: x,
37
+ pointerEvents: "none",
38
+ top: 0
39
+ }
40
+ }), React.createElement("div", {
41
+ style: {
42
+ position: "absolute",
43
+ width: "100%",
44
+ zIndex: 10,
45
+ height: 1,
46
+ backgroundColor: "#f00",
47
+ top: y,
48
+ pointerEvents: "none",
49
+ left: 0
50
+ }
51
+ }));
52
+ };
53
+ export default Crosshairs;
@@ -0,0 +1,20 @@
1
+ import React from "react";
2
+ import SidebarBoxContainer from "../SidebarBoxContainer";
3
+ export var DebugSidebarBox = function DebugSidebarBox(_ref) {
4
+ var state = _ref.state,
5
+ lastAction = _ref.lastAction;
6
+ var image = (state.images || [])[state.selectedImage];
7
+ var region = image ? (image.regions || []).filter(function (r) {
8
+ return r.highlighted;
9
+ }) : null;
10
+ return React.createElement(SidebarBoxContainer, {
11
+ title: "Debug",
12
+ icon: React.createElement("span", null),
13
+ expandedByDefault: true
14
+ }, React.createElement("div", {
15
+ style: {
16
+ padding: 4
17
+ }
18
+ }, React.createElement("div", null, React.createElement("b", null, "region"), ":"), React.createElement("pre", null, JSON.stringify(region, null, " ")), React.createElement("div", null, React.createElement("b", null, "lastAction"), ":"), React.createElement("pre", null, JSON.stringify(lastAction, null, " ")), React.createElement("div", null, React.createElement("b", null, "mode"), ":"), React.createElement("pre", null, JSON.stringify(state.mode, null, " ")), React.createElement("div", null, React.createElement("b", null, "frame:")), React.createElement("pre", null, JSON.stringify(state.selectedImageFrameTime, null, " "))));
19
+ };
20
+ export default DebugSidebarBox;