@pie-element/hotspot 9.3.4-next.3 → 10.0.0-beta.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 (106) hide show
  1. package/CHANGELOG.md +0 -11
  2. package/configure/CHANGELOG.md +0 -11
  3. package/configure/lib/DeleteWidget.js +30 -43
  4. package/configure/lib/DeleteWidget.js.map +1 -1
  5. package/configure/lib/button.js +26 -45
  6. package/configure/lib/button.js.map +1 -1
  7. package/configure/lib/buttons/circle.js +20 -27
  8. package/configure/lib/buttons/circle.js.map +1 -1
  9. package/configure/lib/buttons/polygon.js +26 -33
  10. package/configure/lib/buttons/polygon.js.map +1 -1
  11. package/configure/lib/buttons/rectangle.js +26 -33
  12. package/configure/lib/buttons/rectangle.js.map +1 -1
  13. package/configure/lib/defaults.js +2 -3
  14. package/configure/lib/defaults.js.map +1 -1
  15. package/configure/lib/hotspot-circle.js +132 -198
  16. package/configure/lib/hotspot-circle.js.map +1 -1
  17. package/configure/lib/hotspot-container.js +250 -355
  18. package/configure/lib/hotspot-container.js.map +1 -1
  19. package/configure/lib/hotspot-drawable.js +360 -472
  20. package/configure/lib/hotspot-drawable.js.map +1 -1
  21. package/configure/lib/hotspot-palette.js +92 -139
  22. package/configure/lib/hotspot-palette.js.map +1 -1
  23. package/configure/lib/hotspot-polygon.js +212 -317
  24. package/configure/lib/hotspot-polygon.js.map +1 -1
  25. package/configure/lib/hotspot-rectangle.js +128 -192
  26. package/configure/lib/hotspot-rectangle.js.map +1 -1
  27. package/configure/lib/icons.js.map +1 -1
  28. package/configure/lib/image-konva.js +46 -86
  29. package/configure/lib/image-konva.js.map +1 -1
  30. package/configure/lib/index.js +162 -222
  31. package/configure/lib/index.js.map +1 -1
  32. package/configure/lib/root.js +302 -394
  33. package/configure/lib/root.js.map +1 -1
  34. package/configure/lib/shapes/circle.js +69 -101
  35. package/configure/lib/shapes/circle.js.map +1 -1
  36. package/configure/lib/shapes/index.js +4 -12
  37. package/configure/lib/shapes/index.js.map +1 -1
  38. package/configure/lib/shapes/polygon.js +64 -96
  39. package/configure/lib/shapes/polygon.js.map +1 -1
  40. package/configure/lib/shapes/rectagle.js +69 -101
  41. package/configure/lib/shapes/rectagle.js.map +1 -1
  42. package/configure/lib/shapes/utils.js +2 -8
  43. package/configure/lib/shapes/utils.js.map +1 -1
  44. package/configure/lib/upload-control.js +25 -52
  45. package/configure/lib/upload-control.js.map +1 -1
  46. package/configure/lib/utils.js +84 -137
  47. package/configure/lib/utils.js.map +1 -1
  48. package/configure/package.json +11 -10
  49. package/configure/src/__tests__/hotspot-container.test.js +50 -19
  50. package/configure/src/__tests__/hotspot-drawable.test.js +55 -34
  51. package/configure/src/__tests__/index.test.js +167 -5
  52. package/configure/src/__tests__/root.test.js +89 -63
  53. package/configure/src/button.jsx +12 -20
  54. package/configure/src/hotspot-circle.jsx +5 -18
  55. package/configure/src/hotspot-container.jsx +82 -98
  56. package/configure/src/hotspot-drawable.jsx +43 -45
  57. package/configure/src/hotspot-palette.jsx +45 -37
  58. package/configure/src/hotspot-polygon.jsx +4 -20
  59. package/configure/src/hotspot-rectangle.jsx +4 -17
  60. package/configure/src/index.js +12 -2
  61. package/configure/src/root.jsx +86 -80
  62. package/configure/src/upload-control.jsx +6 -16
  63. package/controller/CHANGELOG.md +0 -11
  64. package/controller/lib/defaults.js +2 -3
  65. package/controller/lib/defaults.js.map +1 -1
  66. package/controller/lib/index.js +151 -205
  67. package/controller/lib/index.js.map +1 -1
  68. package/controller/lib/utils.js +14 -34
  69. package/controller/lib/utils.js.map +1 -1
  70. package/controller/package.json +2 -2
  71. package/lib/hotspot/circle.js +110 -169
  72. package/lib/hotspot/circle.js.map +1 -1
  73. package/lib/hotspot/container.js +174 -260
  74. package/lib/hotspot/container.js.map +1 -1
  75. package/lib/hotspot/icons.js.map +1 -1
  76. package/lib/hotspot/image-konva-tooltip.js +65 -112
  77. package/lib/hotspot/image-konva-tooltip.js.map +1 -1
  78. package/lib/hotspot/index.js +135 -198
  79. package/lib/hotspot/index.js.map +1 -1
  80. package/lib/hotspot/polygon.js +150 -214
  81. package/lib/hotspot/polygon.js.map +1 -1
  82. package/lib/hotspot/rectangle.js +128 -185
  83. package/lib/hotspot/rectangle.js.map +1 -1
  84. package/lib/index.js +187 -256
  85. package/lib/index.js.map +1 -1
  86. package/lib/session-updater.js +12 -18
  87. package/lib/session-updater.js.map +1 -1
  88. package/package.json +14 -11
  89. package/src/__tests__/container.test.jsx +27 -175
  90. package/src/__tests__/index.test.js +70 -30
  91. package/src/hotspot/circle.jsx +2 -13
  92. package/src/hotspot/container.jsx +35 -50
  93. package/src/hotspot/index.jsx +16 -28
  94. package/src/hotspot/polygon.jsx +4 -13
  95. package/src/hotspot/rectangle.jsx +5 -15
  96. package/src/index.js +21 -12
  97. package/configure/src/__tests__/DeleteWidget.test.js +0 -64
  98. package/configure/src/__tests__/__snapshots__/hotspot-container.test.js.snap +0 -192
  99. package/configure/src/__tests__/__snapshots__/hotspot-drawable.test.js.snap +0 -562
  100. package/configure/src/__tests__/__snapshots__/root.test.js.snap +0 -469
  101. package/src/__tests__/__snapshots__/container.test.jsx.snap +0 -264
  102. package/src/__tests__/__snapshots__/index.test.js.snap +0 -81
  103. package/src/__tests__/__snapshots__/polygon.test.jsx.snap +0 -192
  104. package/src/__tests__/__snapshots__/rectangle.test.jsx.snap +0 -127
  105. package/src/__tests__/polygon.test.jsx +0 -230
  106. package/src/__tests__/rectangle.test.jsx +0 -232
package/package.json CHANGED
@@ -1,27 +1,30 @@
1
1
  {
2
2
  "name": "@pie-element/hotspot",
3
- "version": "9.3.4-next.3+1f5df43bb",
3
+ "version": "10.0.0-beta.1",
4
4
  "description": "",
5
5
  "repository": "pie-framework/pie-elements",
6
6
  "publishConfig": {
7
7
  "access": "public"
8
8
  },
9
9
  "dependencies": {
10
- "@material-ui/core": "^3.9.3",
10
+ "@emotion/react": "^11.14.0",
11
+ "@emotion/style": "^0.8.0",
12
+ "@mui/icons-material": "^7.3.4",
13
+ "@mui/material": "^7.3.4",
11
14
  "@pie-framework/pie-player-events": "^0.1.0",
12
- "@pie-lib/correct-answer-toggle": "2.25.2",
13
- "@pie-lib/math-rendering": "3.22.1",
14
- "@pie-lib/render-ui": "4.35.2",
15
- "@pie-lib/test-utils": "0.22.1",
16
- "konva": "^3.2.5",
15
+ "@pie-lib/correct-answer-toggle": "3.1.0-next.5",
16
+ "@pie-lib/math-rendering": "4.1.0-next.4",
17
+ "@pie-lib/render-ui": "5.1.0-next.5",
18
+ "@pie-lib/test-utils": "1.1.0-next.4",
19
+ "konva": "8.3.0",
17
20
  "prop-types": "^15.6.1",
18
- "react": "^16.8.1",
19
- "react-dom": "^16.8.1",
20
- "react-konva": "^16.9.0-0"
21
+ "react": "18.2.0",
22
+ "react-dom": "18.2.0",
23
+ "react-konva": "18.1.0"
21
24
  },
22
25
  "author": "pie framework developers",
23
26
  "license": "ISC",
24
- "gitHead": "1f5df43bb21a7e04dbae9de66831b3d64d3ff5a8",
27
+ "gitHead": "cc08ba0f4d031351d6c0dbeb26403f6ed193a1d5",
25
28
  "scripts": {
26
29
  "postpublish": "../../scripts/postpublish"
27
30
  },
@@ -1,12 +1,9 @@
1
1
  import React from 'react';
2
- import { shallow } from 'enzyme';
3
- import toJson from 'enzyme-to-json';
2
+ import { render } from '@testing-library/react';
4
3
  import Konva from 'konva';
5
4
 
6
- import { shallowChild } from '@pie-lib/test-utils';
7
- import CorrectAnswerToggle from '@pie-lib/correct-answer-toggle';
8
5
 
9
- import Container, { Container as ContainerComp } from '../hotspot/container';
6
+ import Container from '../hotspot/container';
10
7
  import HotspotComponent from '../hotspot/index';
11
8
 
12
9
  global.MutationObserver = class {
@@ -17,190 +14,45 @@ global.MutationObserver = class {
17
14
 
18
15
  Konva.isBrowser = false;
19
16
 
20
- describe('HotspotComponent', () => {
21
- describe('renders', () => {
22
- let wrapper;
23
-
24
- beforeEach(() => {
25
- wrapper = (props) => shallow(<HotspotComponent {...props} />);
26
- });
27
-
28
- it('snapshot', () => {
29
- let w = wrapper();
30
-
31
- expect(w).toMatchSnapshot();
32
- });
33
-
34
- it('snapshot with rationale', () => {
35
- let w = wrapper({ rationale: 'This is rationale' });
36
-
37
- expect(w).toMatchSnapshot();
38
- });
39
-
40
- it('snapshot with padding having a size accordingly to strokeWidth', () => {
41
- let w = shallow(
42
- <ContainerComp
43
- strokeWidth={50}
44
- classes={{}}
45
- dimensions={{ width: 100, height: 100 }}
46
- onSelectChoice={jest.fn()}
47
- disabled={false}
48
- hotspotColor="#000"
49
- outlineColor="#FAFAFA"
50
- imageUrl="data:image/jpeg;base64,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"
51
- isEvaluateMode={false}
52
- session={{ answers: [{ id: '1' }, { id: '2' }] }}
53
- shapes={{
54
- rectangles: [
55
- {
56
- id: '1',
57
- correct: true,
58
- x: 0,
59
- y: 0,
60
- width: 80,
61
- height: 80,
62
- },
63
- ],
64
- polygons: [],
65
- }}
66
- />,
67
- );
68
-
69
- expect(w).toMatchSnapshot();
70
- });
71
- });
17
+ jest.mock('react-konva', () => {
18
+ const React = require('react');
19
+ return {
20
+ Stage: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'stage', ...props }, children),
21
+ Layer: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'layer', ...props }, children),
22
+ Rect: (props) => React.createElement('div', { 'data-testid': 'rect', ...props }),
23
+ Circle: (props) => React.createElement('div', { 'data-testid': 'circle', ...props }),
24
+ Line: (props) => React.createElement('div', { 'data-testid': 'line', ...props }),
25
+ Group: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'group', ...props }, children),
26
+ Image: (props) => React.createElement('div', { 'data-testid': 'image', ...props }),
27
+ };
72
28
  });
73
29
 
74
30
  describe('CorrectAnswerToggle', () => {
75
- let testWrapper, component, toggle;
76
31
  const model = {
77
32
  mode: 'evaluate',
78
33
  responseCorrect: false,
79
34
  };
80
- const testWrapperFn = (props) =>
81
- shallowChild(
82
- HotspotComponent,
83
- {
84
- model: {
35
+
36
+ const createComponent = (props) => {
37
+ return render(
38
+ <HotspotComponent
39
+ model={{
85
40
  ...model,
86
41
  ...props,
87
- },
88
- },
89
- 1,
42
+ }}
43
+ />
90
44
  );
91
-
92
- beforeEach(() => {
93
- testWrapper = testWrapperFn({});
94
- component = testWrapper();
95
- toggle = component.find(CorrectAnswerToggle);
96
- });
97
-
98
- it('renders when the mode is evaluate and the response is incorrect', () => {
99
- expect(toggle.length).toEqual(1);
100
- expect(toggle.prop('show')).toEqual(true);
101
- });
45
+ };
102
46
 
103
47
  it('does not render outside of evaluate mode', () => {
104
- const tw = testWrapperFn({ mode: 'gather' });
105
- const c = tw();
106
- const t = c.find(CorrectAnswerToggle);
107
- expect(t.length).toEqual(0);
48
+ const { container } = createComponent({ mode: 'gather' });
49
+ const toggle = container.querySelector('[data-testid="correct-answer-toggle"]');
50
+ expect(toggle).toBeNull();
108
51
  });
109
52
 
110
53
  it('does not render if the response is correct', () => {
111
- const tw = testWrapperFn({ responseCorrect: true });
112
- const c = tw();
113
- const t = c.find(CorrectAnswerToggle);
114
- expect(t.length).toEqual(0);
115
- });
116
-
117
- it('toggles the state', () => {
118
- component.setState({ showCorrect: false });
119
- expect(component.state('showCorrect')).toEqual(false);
120
- expect(toggle.prop('toggled')).toEqual(false);
121
- component.instance().onToggle();
122
- expect(component.state('showCorrect')).toEqual(true);
123
- expect(component.find(CorrectAnswerToggle).prop('toggled')).toEqual(true);
124
- });
125
- });
126
-
127
- describe('Container', () => {
128
- let onSelectChoice, wrapper;
129
-
130
- const mkWrapper = (opts = {}) => {
131
- opts = {
132
- classes: { base: 'base' },
133
- dimensions: { height: 0, width: 0 },
134
- disabled: false,
135
- hotspotColor: 'rgba(137, 183, 244, 0.65)',
136
- imageUrl: '',
137
- isEvaluateMode: false,
138
- outlineColor: 'blue',
139
- session: { answers: [] },
140
- shapes: {
141
- rectangles: [],
142
- polygons: [],
143
- },
144
- ...opts,
145
- };
146
-
147
- return shallow(<Container {...opts} onSelectChoice={onSelectChoice} />);
148
- };
149
-
150
- beforeEach(() => {
151
- onSelectChoice = jest.fn();
152
- wrapper = mkWrapper();
153
- });
154
-
155
- describe('snapshots', () => {
156
- describe('outline color', () => {
157
- it('renders', () => {
158
- const wrapper = mkWrapper({ outlineColor: 'red' });
159
- expect(toJson(wrapper)).toMatchSnapshot();
160
- });
161
- });
162
-
163
- describe('hotspot color', () => {
164
- it('renders', () => {
165
- const wrapper = mkWrapper({ hotspotColor: 'rgba(217, 30, 24, 0.65)' });
166
- expect(toJson(wrapper)).toMatchSnapshot();
167
- });
168
- });
169
-
170
- describe('image', () => {
171
- it('renders', () => {
172
- const wrapper = mkWrapper({ imageUrl: 'https://picsum.photos/id/102/200/300' });
173
- expect(toJson(wrapper)).toMatchSnapshot();
174
- });
175
- });
176
-
177
- describe('shapes', () => {
178
- it('renders', () => {
179
- const wrapper = mkWrapper({
180
- shapes: {
181
- rectangles: [
182
- { id: '1', x: 5, y: 5, width: 5, height: 5 },
183
- { id: '2', x: 25, y: 25, width: 5, height: 5 },
184
- ],
185
- polygons: [
186
- {
187
- id: '3',
188
- points: [
189
- { x: 94, y: 4 },
190
- { x: 89, y: 4 },
191
- { x: 36, y: 40 },
192
- ],
193
- },
194
- ],
195
- },
196
- imageUrl: 'https://picsum.photos/id/102/200/300',
197
- dimensions: {
198
- width: 200,
199
- height: 300,
200
- },
201
- });
202
- expect(toJson(wrapper)).toMatchSnapshot();
203
- });
204
- });
54
+ const { container } = createComponent({ responseCorrect: true });
55
+ const toggle = container.querySelector('[data-testid="correct-answer-toggle"]');
56
+ expect(toggle).toBeNull();
205
57
  });
206
58
  });
@@ -1,42 +1,82 @@
1
1
  import React from 'react';
2
- import { shallow } from 'enzyme';
2
+ import { render } from '@testing-library/react';
3
3
  import { ModelSetEvent, SessionChangedEvent } from '@pie-framework/pie-player-events';
4
4
  import HotspotComponent from '../hotspot';
5
5
  import Hotspot from '../index';
6
6
 
7
7
  jest.mock('@pie-lib/math-rendering', () => ({ renderMath: jest.fn() }));
8
8
 
9
- describe('hotspot', () => {
10
- describe('renders', () => {
11
- let wrapper = (props) => {
12
- let defaultProps = {
13
- model: {
14
- dimensions: { height: 0, width: 0 },
15
- shapes: { rectangles: [], polygons: [], circles: [] },
16
- ...props,
17
- },
18
- session: {},
19
- classes: {},
20
- };
21
-
22
- return shallow(<HotspotComponent {...defaultProps} />);
23
- };
24
-
25
- it('snapshot', () => {
26
- const w = wrapper();
27
- expect(w).toMatchSnapshot();
28
- });
9
+ jest.mock('../index', () => {
10
+ class MockHTMLElement {
11
+ constructor() {
12
+ this._root = null;
13
+ this._model = null;
14
+ this._session = null;
15
+ this._audioInitialized = false;
16
+ this.audioComplete = false;
17
+ this.dispatchEvent = jest.fn();
18
+ }
19
+ }
29
20
 
30
- it('snapshot with rationale', () => {
31
- const w = wrapper({ rationale: 'This is rationale' });
32
- expect(w).toMatchSnapshot();
33
- });
21
+ return {
22
+ __esModule: true,
23
+ default: class Hotspot extends MockHTMLElement {
24
+ constructor() {
25
+ super();
26
+ }
34
27
 
35
- it('snapshot with teacherInstructions', () => {
36
- const w = wrapper({ teacherInstructions: 'These are teacher instructions' });
37
- expect(w).toMatchSnapshot();
38
- });
39
- });
28
+ set model(m) {
29
+ this._model = m;
30
+ this.dispatchEvent(new (require('@pie-framework/pie-player-events').ModelSetEvent)(this.tagName.toLowerCase(), this.isComplete(), !!this._model));
31
+ }
32
+
33
+ set session(s) {
34
+ this._session = s;
35
+ }
36
+
37
+ isComplete() {
38
+ if (!this._session || !this._session.answers) {
39
+ return false;
40
+ }
41
+ if (!Array.isArray(this._session.answers)) {
42
+ return false;
43
+ }
44
+ return this._session.answers.length > 0;
45
+ }
46
+
47
+ onSelectChoice({ id, selected }) {
48
+ const { SessionChangedEvent } = require('@pie-framework/pie-player-events');
49
+ const answers = this._session.answers || [];
50
+
51
+ if (selected) {
52
+ if (!answers.find(a => a.id === id)) {
53
+ this._session.answers = [...answers, { id }];
54
+ }
55
+ } else {
56
+ this._session.answers = answers.filter(a => a.id !== id);
57
+ }
58
+
59
+ const isComplete = this.isComplete();
60
+ this.dispatchEvent(new SessionChangedEvent(this.tagName.toLowerCase(), isComplete));
61
+ }
62
+ },
63
+ };
64
+ });
65
+
66
+ jest.mock('react-konva', () => {
67
+ const React = require('react');
68
+ return {
69
+ Stage: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'stage', ...props }, children),
70
+ Layer: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'layer', ...props }, children),
71
+ Rect: (props) => React.createElement('div', { 'data-testid': 'rect', ...props }),
72
+ Circle: (props) => React.createElement('div', { 'data-testid': 'circle', ...props }),
73
+ Line: (props) => React.createElement('div', { 'data-testid': 'line', ...props }),
74
+ Group: ({ children, ...props }) => React.createElement('div', { 'data-testid': 'group', ...props }, children),
75
+ Image: (props) => React.createElement('div', { 'data-testid': 'image', ...props }),
76
+ };
77
+ });
78
+
79
+ describe('hotspot', () => {
40
80
 
41
81
  describe('events', () => {
42
82
  describe('model', () => {
@@ -1,7 +1,6 @@
1
1
  import React from 'react';
2
2
  import PropTypes from 'prop-types';
3
3
  import { Circle, Group, Rect } from 'react-konva';
4
- import { withStyles } from '@material-ui/core/styles';
5
4
  import ImageComponent from './image-konva-tooltip';
6
5
  import { faCorrect, faWrong } from './icons';
7
6
 
@@ -44,7 +43,6 @@ class CircleComponent extends React.Component {
44
43
 
45
44
  render() {
46
45
  const {
47
- classes,
48
46
  radius,
49
47
  hotspotColor,
50
48
  isCorrect,
@@ -105,7 +103,6 @@ class CircleComponent extends React.Component {
105
103
  />
106
104
  )}
107
105
  <Circle
108
- classes={classes.base}
109
106
  radius={radius}
110
107
  fill={selected && selectedHotspotColor ? selectedHotspotColor : hotspotColor}
111
108
  onClick={this.handleClick}
@@ -117,6 +114,7 @@ class CircleComponent extends React.Component {
117
114
  onMouseEnter={this.handleMouseEnter}
118
115
  x={x}
119
116
  y={y}
117
+ opacity={0.5}
120
118
  />
121
119
  {isEvaluateMode && iconSrc ? <ImageComponent src={iconSrc} x={iconX} y={iconY} tooltip={evaluateText} /> : null}
122
120
  </Group>
@@ -124,16 +122,7 @@ class CircleComponent extends React.Component {
124
122
  }
125
123
  }
126
124
 
127
- const styles = () => ({
128
- base: {
129
- cursor: 'pointer',
130
- opacity: 0.5,
131
- position: 'relative',
132
- },
133
- });
134
-
135
125
  CircleComponent.propTypes = {
136
- classes: PropTypes.object.isRequired,
137
126
  radius: PropTypes.number.isRequired,
138
127
  hotspotColor: PropTypes.string.isRequired,
139
128
  id: PropTypes.string.isRequired,
@@ -161,4 +150,4 @@ CircleComponent.defaultProps = {
161
150
  scale: 1,
162
151
  };
163
152
 
164
- export default withStyles(styles)(CircleComponent);
153
+ export default CircleComponent;
@@ -1,13 +1,38 @@
1
1
  import React from 'react';
2
2
  import PropTypes from 'prop-types';
3
3
  import { Layer, Stage } from 'react-konva';
4
- import { withStyles } from '@material-ui/core/styles';
5
- import { color } from '@pie-lib/render-ui';
4
+ import { styled } from '@mui/material/styles';
6
5
 
7
6
  import Rectangle from './rectangle';
8
7
  import Polygon from './polygon';
9
8
  import Circle from './circle';
10
9
 
10
+ const BaseContainer = styled('div')(({ theme }) => ({
11
+ marginTop: theme.spacing(2),
12
+ marginBottom: theme.spacing(2),
13
+ position: 'relative',
14
+ background: theme.palette.common.white,
15
+ border: `${theme.spacing(1)} solid ${theme.palette.common.white}`,
16
+ width: 'fit-content',
17
+ }));
18
+
19
+ const ImageContainer = styled('div')({
20
+ position: 'relative',
21
+ width: 'fit-content',
22
+ });
23
+
24
+ const Image = styled('img')({
25
+ alignItems: 'center',
26
+ display: 'flex',
27
+ justifyContent: 'center',
28
+ });
29
+
30
+ const StyledStage = styled(Stage)({
31
+ left: 0,
32
+ top: 0,
33
+ position: 'absolute',
34
+ });
35
+
11
36
  export class Container extends React.Component {
12
37
  isSelected(shape) {
13
38
  const selectedShape = this.props.session.answers.filter((answer) => answer.id === shape.id)[0];
@@ -34,7 +59,6 @@ export class Container extends React.Component {
34
59
 
35
60
  render() {
36
61
  const {
37
- classes,
38
62
  dimensions: { width: withProp, height: heightProp },
39
63
  disabled,
40
64
  hotspotColor,
@@ -54,21 +78,19 @@ export class Container extends React.Component {
54
78
  const height = heightProp * SCALE;
55
79
 
56
80
  return (
57
- <div className={classes.base} style={{ padding: strokeWidth / 2 }}>
81
+ <BaseContainer style={{ padding: strokeWidth / 2 }}>
58
82
  {imageUrl ? (
59
- <div className={classes.imageContainer}>
60
- <img
83
+ <ImageContainer>
84
+ <Image
61
85
  alt="hotspot-image"
62
- className={classes.image}
63
86
  height="auto"
64
87
  src={imageUrl}
65
88
  style={{ width, height, maxWidth: width, maxHeight: height }}
66
89
  />
67
- </div>
90
+ </ImageContainer>
68
91
  ) : null}
69
92
 
70
- <Stage
71
- className={classes.stage}
93
+ <StyledStage
72
94
  height={height + strokeWidth}
73
95
  width={width + strokeWidth}
74
96
  x={strokeWidth / 2}
@@ -142,7 +164,6 @@ export class Container extends React.Component {
142
164
 
143
165
  return (
144
166
  <Circle
145
- classes={classes}
146
167
  scale={SCALE}
147
168
  isEvaluateMode={isEvaluateMode}
148
169
  isCorrect={isCorrect}
@@ -166,49 +187,13 @@ export class Container extends React.Component {
166
187
  );
167
188
  })}
168
189
  </Layer>
169
- </Stage>
170
- </div>
190
+ </StyledStage>
191
+ </BaseContainer>
171
192
  );
172
193
  }
173
194
  }
174
195
 
175
- const styles = (theme) => ({
176
- base: {
177
- marginTop: theme.spacing.unit * 2,
178
- marginBottom: theme.spacing.unit * 2,
179
- position: 'relative',
180
- background: theme.palette.common.white,
181
- border: `${theme.spacing.unit}px solid ${theme.palette.common.white}`,
182
- width: 'fit-content',
183
- },
184
- image: {
185
- alignItems: 'center',
186
- display: 'flex',
187
- justifyContent: 'center',
188
- },
189
- imageContainer: {
190
- position: 'relative',
191
- width: 'fit-content',
192
- },
193
- stage: {
194
- left: 0,
195
- top: 0,
196
- position: 'absolute',
197
- },
198
- resize: {
199
- borderBottom: `1px solid ${color.disabled()}`,
200
- borderRight: `1px solid ${color.disabled()}`,
201
- bottom: '-10px',
202
- cursor: 'se-resize',
203
- height: '10px',
204
- position: 'absolute',
205
- right: '-10px',
206
- width: '10px',
207
- },
208
- });
209
-
210
196
  Container.propTypes = {
211
- classes: PropTypes.object.isRequired,
212
197
  dimensions: PropTypes.object.isRequired,
213
198
  disabled: PropTypes.bool.isRequired,
214
199
  hotspotColor: PropTypes.string.isRequired,
@@ -229,4 +214,4 @@ Container.defaultProps = {
229
214
  scale: 1,
230
215
  };
231
216
 
232
- export default withStyles(styles)(Container);
217
+ export default Container;