kitchen-simulator 5.0.0-test.12 → 5.0.0-test.13
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/package.json +12 -3
- package/src/_renderer.jsx +3 -3
- package/src/index.html.ejs +226 -0
- package/src/@history.js +0 -3
- package/src/CrossSignOn.jsx +0 -94
- package/src/renderer.jsx +0 -466
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "kitchen-simulator",
|
|
3
|
-
"version": "5.0.0-test.
|
|
3
|
+
"version": "5.0.0-test.13",
|
|
4
4
|
"description": "It is a kitchen simulator.",
|
|
5
5
|
"main": "src/index.js",
|
|
6
6
|
"module": "src/index.js",
|
|
@@ -14,8 +14,17 @@
|
|
|
14
14
|
},
|
|
15
15
|
|
|
16
16
|
"files": [
|
|
17
|
-
"src
|
|
18
|
-
"src
|
|
17
|
+
"src/_renderer.jsx",
|
|
18
|
+
"src/AppContext.js",
|
|
19
|
+
"src/constants.js",
|
|
20
|
+
"src/index.js",
|
|
21
|
+
"src/index.html.ejs",
|
|
22
|
+
"src/KitchenConfigurator.jsx",
|
|
23
|
+
"src/KitchenConfiguratorApp.jsx",
|
|
24
|
+
"src/models.js",
|
|
25
|
+
"src/shared-style.js",
|
|
26
|
+
"src/version.js",
|
|
27
|
+
|
|
19
28
|
"src/catalog",
|
|
20
29
|
"src/utils",
|
|
21
30
|
"src/actions",
|
package/src/_renderer.jsx
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
2
|
import KitchenConfiguratorApp from './KitchenConfiguratorApp.jsx'; // webpack alias points to ../src
|
|
3
|
-
import mockProps from './mockProps.json';
|
|
4
|
-
import mockCategoryData from './categoryData.json';
|
|
5
|
-
import mockDataBundle from './dataBundle.json';
|
|
3
|
+
import mockProps from './mocks/mockProps.json';
|
|
4
|
+
import mockCategoryData from './mocks/categoryData.json';
|
|
5
|
+
import mockDataBundle from './mocks/dataBundle.json';
|
|
6
6
|
import ReactDOM from 'react-dom';
|
|
7
7
|
|
|
8
8
|
// --- renderer props ---
|
|
@@ -0,0 +1,226 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html>
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8" />
|
|
5
|
+
<title><%= htmlWebpackPlugin.options.title %></title>
|
|
6
|
+
<link rel="stylesheet" type="text/css" href="/assets/fonts/style.css" />
|
|
7
|
+
<link
|
|
8
|
+
rel="icon"
|
|
9
|
+
type="image/jpg"
|
|
10
|
+
href="/assets/img/rta/rta_logo_box_blue_ico.jpg"
|
|
11
|
+
id="favicon_icon_jpg"
|
|
12
|
+
/>
|
|
13
|
+
<link
|
|
14
|
+
rel="icon"
|
|
15
|
+
type="image/svg"
|
|
16
|
+
href="/assets/img/rta/rta_logo_box_blue_ico.svg"
|
|
17
|
+
id="favicon_icon_svg"
|
|
18
|
+
/>
|
|
19
|
+
<link
|
|
20
|
+
rel="shortcut icon"
|
|
21
|
+
type="image/jpg"
|
|
22
|
+
href="/assets/img/rta/rta_logo_box_blue_ico.jpg"
|
|
23
|
+
id="favicon_shortcut_jpg"
|
|
24
|
+
/>
|
|
25
|
+
<link
|
|
26
|
+
rel="shortcut icon"
|
|
27
|
+
type="image/svg"
|
|
28
|
+
href="/assets/img/rta/rta_logo_box_blue_ico.svg"
|
|
29
|
+
id="favicon_shortcut_svg"
|
|
30
|
+
/>
|
|
31
|
+
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
|
32
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
|
33
|
+
<link
|
|
34
|
+
href="https://fonts.googleapis.com/css2?family=Open+Sans:ital,wght@0,300..800;1,300..800&display=swap"
|
|
35
|
+
rel="stylesheet"
|
|
36
|
+
/>
|
|
37
|
+
<style>
|
|
38
|
+
* {
|
|
39
|
+
box-sizing: border-box;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
html,
|
|
43
|
+
body,
|
|
44
|
+
#app {
|
|
45
|
+
width: 100%;
|
|
46
|
+
height: 100%;
|
|
47
|
+
padding: 0;
|
|
48
|
+
margin: 0;
|
|
49
|
+
font-family: 'Milliard Book';
|
|
50
|
+
font-weight: normal;
|
|
51
|
+
position: absolute;
|
|
52
|
+
left: 0;
|
|
53
|
+
top: 0;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
#error {
|
|
57
|
+
position: relative;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
::-webkit-scrollbar {
|
|
61
|
+
width: 2px;
|
|
62
|
+
border-radius: 2px;
|
|
63
|
+
position: absolute;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
::-webkit-scrollbar-track-piece {
|
|
67
|
+
background-color: #fff;
|
|
68
|
+
border-radius: 1px;
|
|
69
|
+
position: absolute;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
::-webkit-scrollbar-thumb:vertical {
|
|
73
|
+
height: 30px;
|
|
74
|
+
background-color: rgb(193, 202, 228);
|
|
75
|
+
}
|
|
76
|
+
::-webkit-scrollbar-thumb {
|
|
77
|
+
background-color: rgb(220, 220, 220);
|
|
78
|
+
border-radius: 5px;
|
|
79
|
+
transition: all 0.3s;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
::-webkit-scrollbar-thumb:hover {
|
|
83
|
+
background-color: rgb(193, 202, 228);
|
|
84
|
+
border-radius: 5px;
|
|
85
|
+
transition: all 0.3s;
|
|
86
|
+
}
|
|
87
|
+
</style>
|
|
88
|
+
<!-- Hotjar Tracking Code for New DIY -->
|
|
89
|
+
<script>
|
|
90
|
+
(function (h, o, t, j, a, r) {
|
|
91
|
+
h.hj =
|
|
92
|
+
h.hj ||
|
|
93
|
+
function () {
|
|
94
|
+
(h.hj.q = h.hj.q || []).push(arguments);
|
|
95
|
+
};
|
|
96
|
+
h._hjSettings = { hjid: 5088152, hjsv: 6 };
|
|
97
|
+
a = o.getElementsByTagName('head')[0];
|
|
98
|
+
r = o.createElement('script');
|
|
99
|
+
r.async = 1;
|
|
100
|
+
r.src = t + h._hjSettings.hjid + j + h._hjSettings.hjsv;
|
|
101
|
+
a.appendChild(r);
|
|
102
|
+
})(window, document, 'https://static.hotjar.com/c/hotjar-', '.js?sv=');
|
|
103
|
+
</script>
|
|
104
|
+
</head>
|
|
105
|
+
|
|
106
|
+
<body>
|
|
107
|
+
<div id="app" style="display: none">
|
|
108
|
+
<div
|
|
109
|
+
style="
|
|
110
|
+
width: 100vw;
|
|
111
|
+
height: 100vh;
|
|
112
|
+
display: flex;
|
|
113
|
+
flex-direction: column;
|
|
114
|
+
align-items: center;
|
|
115
|
+
justify-content: center;
|
|
116
|
+
"
|
|
117
|
+
>
|
|
118
|
+
<img
|
|
119
|
+
id="kc_spinner"
|
|
120
|
+
style="height: 60px"
|
|
121
|
+
alt="Loading"
|
|
122
|
+
src="/assets/img/loading/loading.gif"
|
|
123
|
+
/>
|
|
124
|
+
</div>
|
|
125
|
+
</div>
|
|
126
|
+
<div id="error" style="z-index: -1"></div>
|
|
127
|
+
<!-- Start of LiveChat (www.livechat.com) code -->
|
|
128
|
+
<script>
|
|
129
|
+
function injectThertastore() {
|
|
130
|
+
// --- LiveChat SCRIPT ---
|
|
131
|
+
const liveScript = document.createElement('script');
|
|
132
|
+
liveScript.innerHTML = `
|
|
133
|
+
window.__lc = window.__lc || {};
|
|
134
|
+
window.__lc.license = 3185312;
|
|
135
|
+
(function (n, t, c) {
|
|
136
|
+
function i(n) { return e._h ? e._h.apply(null, n) : e._q.push(n); }
|
|
137
|
+
var e = {
|
|
138
|
+
_q: [], _h: null, _v: '2.0',
|
|
139
|
+
on: function () { i(['on', c.call(arguments)]); },
|
|
140
|
+
once: function () { i(['once', c.call(arguments)]); },
|
|
141
|
+
off: function () { i(['off', c.call(arguments)]); },
|
|
142
|
+
get: function () {
|
|
143
|
+
if (!e._h)
|
|
144
|
+
throw new Error("[LiveChatWidget] You can't use getters before load.");
|
|
145
|
+
return i(['get', c.call(arguments)]);
|
|
146
|
+
},
|
|
147
|
+
call: function () { i(['call', c.call(arguments)]); },
|
|
148
|
+
init: function () {
|
|
149
|
+
var n = t.createElement('script');
|
|
150
|
+
n.async = true;
|
|
151
|
+
n.type = 'text/javascript';
|
|
152
|
+
n.src = 'https://cdn.livechatinc.com/tracking.js';
|
|
153
|
+
t.head.appendChild(n);
|
|
154
|
+
}
|
|
155
|
+
};
|
|
156
|
+
!n.__lc.asyncInit && e.init();
|
|
157
|
+
n.LiveChatWidget = n.LiveChatWidget || e;
|
|
158
|
+
})(window, document, [].slice);
|
|
159
|
+
`;
|
|
160
|
+
document.body.appendChild(liveScript);
|
|
161
|
+
|
|
162
|
+
// --- LiveChat NOSCRIPT ---
|
|
163
|
+
const noscript = document.createElement('noscript');
|
|
164
|
+
noscript.innerHTML = `
|
|
165
|
+
<a href="https://www.livechat.com/chat-with/3185312/" rel="nofollow">
|
|
166
|
+
Chat with us
|
|
167
|
+
</a>, powered by
|
|
168
|
+
<a href="https://www.livechat.com/?welcome" rel="noopener nofollow" target="_blank">
|
|
169
|
+
LiveChat
|
|
170
|
+
</a>
|
|
171
|
+
`;
|
|
172
|
+
document.body.appendChild(noscript);
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
function injectPrimecabinetry() {
|
|
176
|
+
// --- Richpanel SCRIPT ---
|
|
177
|
+
const richpanelScript = document.createElement('script');
|
|
178
|
+
richpanelScript.innerHTML = `
|
|
179
|
+
window.richpanel||(window.richpanel=[]),window.richpanel.q=[],
|
|
180
|
+
mth=["track","debug","atr"],
|
|
181
|
+
sk=function(e){return function(){
|
|
182
|
+
a=Array.prototype.slice.call(arguments);
|
|
183
|
+
a.unshift(e);
|
|
184
|
+
window.richpanel.q.push(a)
|
|
185
|
+
}};
|
|
186
|
+
for(var i=0;mth.length>i;i++)window.richpanel[mth[i]]=sk(mth[i]);
|
|
187
|
+
window.richpanel.load=function(e){
|
|
188
|
+
var i=document,
|
|
189
|
+
n=i.getElementsByTagName("script")[0],
|
|
190
|
+
r=i.createElement("script");
|
|
191
|
+
r.type="text/javascript";
|
|
192
|
+
r.async=true;
|
|
193
|
+
r.src="https://cdn.richpanel.com/js/richpanel-root.js?appClientId=primecabinetry2965";
|
|
194
|
+
n.parentNode.insertBefore(r,n)
|
|
195
|
+
};
|
|
196
|
+
window.richpanel.ensure_rpuid="";
|
|
197
|
+
richpanel.load("primecabinetry2965");
|
|
198
|
+
`;
|
|
199
|
+
document.body.appendChild(richpanelScript);
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
// brand → injection function mapping
|
|
203
|
+
const brandInjectors = {
|
|
204
|
+
thertastore: injectThertastore,
|
|
205
|
+
primecabinetry: injectPrimecabinetry
|
|
206
|
+
// future brands go here
|
|
207
|
+
};
|
|
208
|
+
|
|
209
|
+
// extract brand from URL
|
|
210
|
+
const brand = window.location.pathname.split('/')[1];
|
|
211
|
+
|
|
212
|
+
// pick injector
|
|
213
|
+
const injector = brandInjectors[brand];
|
|
214
|
+
|
|
215
|
+
if (injector) {
|
|
216
|
+
injector();
|
|
217
|
+
} else {
|
|
218
|
+
console.warn(
|
|
219
|
+
`[Brand Injection] Unknown brand "${brand}". Defaulting to Thertastore.`
|
|
220
|
+
);
|
|
221
|
+
brandInjectors['thertastore']();
|
|
222
|
+
}
|
|
223
|
+
</script>
|
|
224
|
+
<!-- End of LiveChat code -->
|
|
225
|
+
</body>
|
|
226
|
+
</html>
|
package/src/@history.js
DELETED
package/src/CrossSignOn.jsx
DELETED
|
@@ -1,94 +0,0 @@
|
|
|
1
|
-
import React, { useEffect, useState } from 'react';
|
|
2
|
-
import ls from 'localstorage-slim';
|
|
3
|
-
import {
|
|
4
|
-
LOCAL_STORAGE_CUSTOMER_INFO,
|
|
5
|
-
LOCAL_STORAGE_ORIGINAL_TOKEN,
|
|
6
|
-
LOCAL_STORAGE_TOKEN_NAME,
|
|
7
|
-
LOCAL_STORAGE_TOKEN_VALUE
|
|
8
|
-
} from './constants.js';
|
|
9
|
-
import { base64Decode } from './utils/helper.js';
|
|
10
|
-
|
|
11
|
-
export const LOG_PREFIX = `[Cross Sign On]`;
|
|
12
|
-
export const QUERY_PARAM_TOKEN = 'token';
|
|
13
|
-
export const ENCODED_QUERY_PARAM_TOKEN = 'details';
|
|
14
|
-
|
|
15
|
-
try {
|
|
16
|
-
console.log(`${LOG_PREFIX} Clearing local storage`);
|
|
17
|
-
ls.clear();
|
|
18
|
-
} catch (e) {
|
|
19
|
-
console.log(`${LOG_PREFIX} Error clearing local storage`, e);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
function extractAccessTokenFromUrl() {
|
|
23
|
-
try {
|
|
24
|
-
const url = new URL(window.location.href);
|
|
25
|
-
const token = url.searchParams.get(QUERY_PARAM_TOKEN);
|
|
26
|
-
const encodedToken = url.searchParams.get(ENCODED_QUERY_PARAM_TOKEN);
|
|
27
|
-
|
|
28
|
-
if (!token && !encodedToken) {
|
|
29
|
-
console.log(`${LOG_PREFIX} No access token found in URL`);
|
|
30
|
-
return undefined;
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
if (token) {
|
|
34
|
-
ls.set(LOCAL_STORAGE_ORIGINAL_TOKEN, token);
|
|
35
|
-
ls.set(LOCAL_STORAGE_TOKEN_VALUE, token);
|
|
36
|
-
ls.set(LOCAL_STORAGE_TOKEN_NAME, 'token=');
|
|
37
|
-
return token;
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
try {
|
|
41
|
-
const decoded = base64Decode(encodedToken);
|
|
42
|
-
const parsed = JSON.parse(decoded);
|
|
43
|
-
ls.set(LOCAL_STORAGE_ORIGINAL_TOKEN, encodedToken);
|
|
44
|
-
if (parsed.token) {
|
|
45
|
-
ls.set(LOCAL_STORAGE_TOKEN_VALUE, parsed.token);
|
|
46
|
-
}
|
|
47
|
-
ls.set(LOCAL_STORAGE_TOKEN_NAME, 'details=');
|
|
48
|
-
|
|
49
|
-
const customerInfo = {
|
|
50
|
-
email: parsed.email,
|
|
51
|
-
firstName: parsed.first_name,
|
|
52
|
-
lastName: parsed.last_name
|
|
53
|
-
};
|
|
54
|
-
ls.set(LOCAL_STORAGE_CUSTOMER_INFO, customerInfo);
|
|
55
|
-
|
|
56
|
-
return parsed;
|
|
57
|
-
} catch (e) {
|
|
58
|
-
return undefined;
|
|
59
|
-
}
|
|
60
|
-
} catch (e) {
|
|
61
|
-
console.error(`${LOG_PREFIX} Error extracting access token from URL`, e);
|
|
62
|
-
return undefined;
|
|
63
|
-
}
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
function extractAccessTokenFromLocalStorage() {
|
|
67
|
-
const token = ls.get(LOCAL_STORAGE_ORIGINAL_TOKEN);
|
|
68
|
-
if (!token || typeof token !== 'string') return undefined;
|
|
69
|
-
return token;
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
const CrossSignOn = ({ App }) => {
|
|
73
|
-
const [accessToken, setAccessToken] = useState(() => {
|
|
74
|
-
return extractAccessTokenFromUrl() || extractAccessTokenFromLocalStorage();
|
|
75
|
-
});
|
|
76
|
-
|
|
77
|
-
useEffect(() => {
|
|
78
|
-
const handleTokenChange = () => {
|
|
79
|
-
const newToken =
|
|
80
|
-
extractAccessTokenFromUrl() || extractAccessTokenFromLocalStorage();
|
|
81
|
-
setAccessToken(newToken);
|
|
82
|
-
};
|
|
83
|
-
|
|
84
|
-
window.addEventListener('token-changed', handleTokenChange);
|
|
85
|
-
|
|
86
|
-
return () => {
|
|
87
|
-
window.removeEventListener('token-changed', handleTokenChange);
|
|
88
|
-
};
|
|
89
|
-
}, []);
|
|
90
|
-
|
|
91
|
-
return <App accessToken={accessToken} />;
|
|
92
|
-
};
|
|
93
|
-
|
|
94
|
-
export default CrossSignOn;
|
package/src/renderer.jsx
DELETED
|
@@ -1,466 +0,0 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
|
-
import ReactDOM from 'react-dom';
|
|
3
|
-
import ContainerDimensions from 'react-container-dimensions';
|
|
4
|
-
import Immutable, { Map } from 'immutable';
|
|
5
|
-
import immutableDevtools from 'immutable-devtools';
|
|
6
|
-
import { createStore } from 'redux';
|
|
7
|
-
import { Provider } from 'react-redux';
|
|
8
|
-
import ReactGA from 'react-ga4';
|
|
9
|
-
import { hotjar } from 'react-hotjar';
|
|
10
|
-
import * as Sentry from '@sentry/react';
|
|
11
|
-
import browserHistory from './@history.js';
|
|
12
|
-
import * as history from 'history';
|
|
13
|
-
import AppContext from './AppContext.js';
|
|
14
|
-
import { HashRouter, Route, Router, Switch } from 'react-router-dom';
|
|
15
|
-
import exporter from './catalog/utils/exporter';
|
|
16
|
-
import axios from 'axios';
|
|
17
|
-
import MyCatalog from './catalog/mycatalog';
|
|
18
|
-
import Login from './components/login/Login.js';
|
|
19
|
-
import Register from './components/login/Register.js';
|
|
20
|
-
import {
|
|
21
|
-
API_SERVER_URL,
|
|
22
|
-
ERROR_DATABASE,
|
|
23
|
-
MODE,
|
|
24
|
-
NO_DATA_DATABASE,
|
|
25
|
-
TOE_KICK_MOLDING
|
|
26
|
-
} from './constants.js'; // import { Progress } from 'antd';
|
|
27
|
-
import ToolbarScreenshotButton from '../src/ui/toolbar-screenshot-button.jsx';
|
|
28
|
-
import MobileDetect from 'mobile-detect';
|
|
29
|
-
import * as zlib from 'browserify-zlib';
|
|
30
|
-
import Buffer from 'buffer';
|
|
31
|
-
import { getPathInfo, isEmpty } from './utils/helper.js';
|
|
32
|
-
|
|
33
|
-
import {
|
|
34
|
-
KitchenConfigurator,
|
|
35
|
-
Models as PlannerModels,
|
|
36
|
-
Plugins as PlannerPlugins,
|
|
37
|
-
reducer as PlannerReducer
|
|
38
|
-
} from './index'; //KitchenConfigurator
|
|
39
|
-
import { newProject } from './actions/project-actions.js';
|
|
40
|
-
import { SVGLoader } from 'three/examples/jsm/loaders/SVGLoader';
|
|
41
|
-
import CrossSignOn from './CrossSignOn.jsx';
|
|
42
|
-
import { QueryClient, QueryClientProvider } from 'react-query';
|
|
43
|
-
import { ReactQueryDevtools } from 'react-query/devtools';
|
|
44
|
-
import {
|
|
45
|
-
render2DItem,
|
|
46
|
-
render3DApplianceItem,
|
|
47
|
-
render3DItem,
|
|
48
|
-
render3DLightingItem
|
|
49
|
-
} from './catalog/utils/item-loader'; // Axios config
|
|
50
|
-
|
|
51
|
-
// Axios config
|
|
52
|
-
axios.defaults.baseURL = API_SERVER_URL;
|
|
53
|
-
|
|
54
|
-
const md = new MobileDetect(window.navigator.userAgent);
|
|
55
|
-
const isMobile = md.mobile();
|
|
56
|
-
if (isMobile === null) {
|
|
57
|
-
document.getElementById('app').style.display = 'block';
|
|
58
|
-
} else alert('The Kitchen Design software is only available from Desktop use');
|
|
59
|
-
//define state
|
|
60
|
-
let AppState = Map({
|
|
61
|
-
KitchenConfigurator: new PlannerModels.State()
|
|
62
|
-
});
|
|
63
|
-
|
|
64
|
-
console.log('Version: 378.45-202509_DIY-364-mbox-crash');
|
|
65
|
-
ReactGA.initialize([
|
|
66
|
-
{
|
|
67
|
-
trackingId: 'G-YK2JCC9F9G' // https://dev.addovisuals.com
|
|
68
|
-
},
|
|
69
|
-
{
|
|
70
|
-
trackingId: 'G-3Y44W0RY2E' // https://demo.kc.addovisuals.com/
|
|
71
|
-
},
|
|
72
|
-
{
|
|
73
|
-
trackingId: 'G-M2VD74KP44' // https://rtastore.diydesignspace.com/
|
|
74
|
-
}
|
|
75
|
-
]);
|
|
76
|
-
|
|
77
|
-
hotjar.initialize('3010506', '6');
|
|
78
|
-
|
|
79
|
-
isProduction &&
|
|
80
|
-
Sentry.init({
|
|
81
|
-
dsn: process.env.SENTRY_DSN,
|
|
82
|
-
environment: process.env.SENTRY_ENVIRONMENT
|
|
83
|
-
});
|
|
84
|
-
|
|
85
|
-
//define reducer
|
|
86
|
-
let reducer = (state, action) => {
|
|
87
|
-
state = state || AppState;
|
|
88
|
-
state = state.update('KitchenConfigurator', plannerState =>
|
|
89
|
-
PlannerReducer(plannerState, action)
|
|
90
|
-
);
|
|
91
|
-
return state;
|
|
92
|
-
};
|
|
93
|
-
|
|
94
|
-
let blackList =
|
|
95
|
-
isProduction === true
|
|
96
|
-
? []
|
|
97
|
-
: ['UPDATE_MOUSE_COORDS', 'UPDATE_ZOOM_SCALE', 'UPDATE_2D_CAMERA'];
|
|
98
|
-
|
|
99
|
-
if (!isProduction) {
|
|
100
|
-
console.info(
|
|
101
|
-
'Environment is in development and these actions will be blacklisted',
|
|
102
|
-
blackList
|
|
103
|
-
);
|
|
104
|
-
console.info('Enable Chrome custom formatter for Immutable pretty print');
|
|
105
|
-
immutableDevtools(Immutable);
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
//init store
|
|
109
|
-
let store = createStore(
|
|
110
|
-
reducer,
|
|
111
|
-
null,
|
|
112
|
-
!isProduction && window.devToolsExtension
|
|
113
|
-
? window.devToolsExtension({
|
|
114
|
-
features: {
|
|
115
|
-
pause: true, // start/pause recording of dispatched actions
|
|
116
|
-
lock: true, // lock/unlock dispatching actions and side effects
|
|
117
|
-
persist: true, // persist states on page reloading
|
|
118
|
-
export: true, // export history of actions in a file
|
|
119
|
-
import: 'custom', // import history of actions from a file
|
|
120
|
-
jump: true, // jump back and forth (time travelling)
|
|
121
|
-
skip: true, // skip (cancel) actions
|
|
122
|
-
reorder: true, // drag and drop actions in the history list
|
|
123
|
-
dispatch: true, // dispatch custom actions or action creators
|
|
124
|
-
test: true // generate tests for the selected actions
|
|
125
|
-
},
|
|
126
|
-
actionsBlacklist: blackList,
|
|
127
|
-
maxAge: 999999
|
|
128
|
-
})
|
|
129
|
-
: f => f
|
|
130
|
-
);
|
|
131
|
-
|
|
132
|
-
let plugins = [PlannerPlugins.Keyboard(), PlannerPlugins.ConsoleDebugger()];
|
|
133
|
-
|
|
134
|
-
let toolbarButtons = [ToolbarScreenshotButton];
|
|
135
|
-
|
|
136
|
-
let categoryData;
|
|
137
|
-
if (isMobile === null) {
|
|
138
|
-
sessionStorage.setItem('visualizerName', getPathInfo(1));
|
|
139
|
-
axios
|
|
140
|
-
.get(`${API_SERVER_URL}/api/dealer/${getPathInfo(1)}/config`)
|
|
141
|
-
.then(async res => {
|
|
142
|
-
const { success, id, logoImg, companyUrl, config } = res.data;
|
|
143
|
-
let configdata = JSON.parse(config);
|
|
144
|
-
|
|
145
|
-
if (
|
|
146
|
-
success === false ||
|
|
147
|
-
(id === 0 && logoImg === '' && companyUrl === '')
|
|
148
|
-
) {
|
|
149
|
-
alert('No Catalog');
|
|
150
|
-
return;
|
|
151
|
-
}
|
|
152
|
-
await axios
|
|
153
|
-
.post(
|
|
154
|
-
`${API_SERVER_URL}/api/planner/read/planner`,
|
|
155
|
-
{
|
|
156
|
-
type: MODE === 'staging' ? 2 : 1
|
|
157
|
-
},
|
|
158
|
-
{
|
|
159
|
-
responseType: 'arraybuffer'
|
|
160
|
-
}
|
|
161
|
-
)
|
|
162
|
-
.then(async response => {
|
|
163
|
-
const unzip_data = JSON.parse(
|
|
164
|
-
zlib.unzipSync(new Buffer.Buffer.from(response.data)).toString()
|
|
165
|
-
);
|
|
166
|
-
const { data, appliances, lighting, furnishing, success } =
|
|
167
|
-
unzip_data;
|
|
168
|
-
if (success === false) {
|
|
169
|
-
console.log(NO_DATA_DATABASE);
|
|
170
|
-
}
|
|
171
|
-
if (success === 'error') {
|
|
172
|
-
alert(ERROR_DATABASE);
|
|
173
|
-
}
|
|
174
|
-
await axios
|
|
175
|
-
.post(
|
|
176
|
-
`${API_SERVER_URL}/api/toolbar/getCategoryData`,
|
|
177
|
-
{
|
|
178
|
-
type: MODE === 'staging' ? 2 : 1
|
|
179
|
-
},
|
|
180
|
-
{
|
|
181
|
-
responseType: 'arraybuffer'
|
|
182
|
-
}
|
|
183
|
-
)
|
|
184
|
-
.then(response => {
|
|
185
|
-
categoryData = JSON.parse(
|
|
186
|
-
zlib.unzipSync(new Buffer.Buffer.from(response.data)).toString()
|
|
187
|
-
);
|
|
188
|
-
const { catalogs, colorAlias, subgroups } = categoryData.data;
|
|
189
|
-
let door_color_alias = [];
|
|
190
|
-
let subgroup_ids = catalogs
|
|
191
|
-
.filter(item => item.id == id)[0]
|
|
192
|
-
.manufacturer_subgroup_ids.split(',');
|
|
193
|
-
let door_color_alias_ids = [];
|
|
194
|
-
subgroups.forEach(subgroup => {
|
|
195
|
-
if (subgroup_ids.some(id => id == subgroup.id.toString())) {
|
|
196
|
-
subgroup.door_color_alias_ids.split(',').forEach(item => {
|
|
197
|
-
item != '' && door_color_alias_ids.push(item);
|
|
198
|
-
});
|
|
199
|
-
}
|
|
200
|
-
});
|
|
201
|
-
colorAlias.forEach(
|
|
202
|
-
color =>
|
|
203
|
-
door_color_alias_ids.some(id => id == color.id.toString()) &&
|
|
204
|
-
door_color_alias.push(color)
|
|
205
|
-
);
|
|
206
|
-
const doorStyleData = categoryData.data.doorStyles.items;
|
|
207
|
-
categoryData.data.doorStyles.items = doorStyleData.treeStruct;
|
|
208
|
-
// construct a doorStyle variable
|
|
209
|
-
door_color_alias.forEach(dca => {
|
|
210
|
-
doorStyleData.doorColorData.forEach(dc => {
|
|
211
|
-
// convert string into integer.
|
|
212
|
-
dc.door_style_id = parseInt(dc.door_style_id);
|
|
213
|
-
|
|
214
|
-
// find the original for the alias.
|
|
215
|
-
if (dc.id !== dca.door_color_id) return;
|
|
216
|
-
dc.name = dca.alias_name;
|
|
217
|
-
dc.color_sku_alias = dca.sku_alias_name;
|
|
218
|
-
|
|
219
|
-
// judge the door style of the current door color
|
|
220
|
-
doorStyleData.treeStruct.forEach(el => {
|
|
221
|
-
el.items.forEach(
|
|
222
|
-
elem =>
|
|
223
|
-
dc.door_style_id === elem.id &&
|
|
224
|
-
(dc.door_style_name = elem.name)
|
|
225
|
-
);
|
|
226
|
-
});
|
|
227
|
-
|
|
228
|
-
// convert string into array
|
|
229
|
-
dca.alias_installation_type = isEmpty(
|
|
230
|
-
dca.alias_installation_type
|
|
231
|
-
)
|
|
232
|
-
? []
|
|
233
|
-
: dca.alias_installation_type
|
|
234
|
-
.split(',')
|
|
235
|
-
.map(item => parseInt(item));
|
|
236
|
-
|
|
237
|
-
// add door color to doorStyle variable according to 'alias_installation_type' of its alias
|
|
238
|
-
categoryData.data.doorStyles.items.forEach(item => {
|
|
239
|
-
if (
|
|
240
|
-
dca.alias_installation_type.some(ait => ait === item.id)
|
|
241
|
-
)
|
|
242
|
-
item.items.forEach(ds => {
|
|
243
|
-
if (ds.name === dc.door_style_name) ds.items.push(dc);
|
|
244
|
-
});
|
|
245
|
-
});
|
|
246
|
-
});
|
|
247
|
-
});
|
|
248
|
-
|
|
249
|
-
let molding = [];
|
|
250
|
-
let toeMoldingData = [];
|
|
251
|
-
let cabinets = categoryData.data.cabinets;
|
|
252
|
-
cabinets[cabinets.length - 1].items.forEach(index => {
|
|
253
|
-
if (index.name.toLowerCase().includes('molding')) {
|
|
254
|
-
index.items.forEach(item => {
|
|
255
|
-
molding.push(item);
|
|
256
|
-
});
|
|
257
|
-
}
|
|
258
|
-
// store all toe kick molding templates
|
|
259
|
-
if (index.name.includes(TOE_KICK_MOLDING)) {
|
|
260
|
-
index.items.forEach(item => {
|
|
261
|
-
toeMoldingData.push(item);
|
|
262
|
-
});
|
|
263
|
-
}
|
|
264
|
-
});
|
|
265
|
-
categoryData.data.toeMoldingData = toeMoldingData;
|
|
266
|
-
const promises = molding.map(child => {
|
|
267
|
-
return new Promise((resolve, reject) => {
|
|
268
|
-
const url = child?.shape_svg;
|
|
269
|
-
if (!url) {
|
|
270
|
-
// Skip if no SVG URL available
|
|
271
|
-
return resolve();
|
|
272
|
-
}
|
|
273
|
-
|
|
274
|
-
const loader = new SVGLoader();
|
|
275
|
-
loader.load(
|
|
276
|
-
url,
|
|
277
|
-
data => {
|
|
278
|
-
child.data = {
|
|
279
|
-
paths: data.paths,
|
|
280
|
-
svg_width: data.xml?.viewBox?.animVal?.width ?? 0,
|
|
281
|
-
svg_height: data.xml?.viewBox?.animVal?.height ?? 0
|
|
282
|
-
};
|
|
283
|
-
resolve();
|
|
284
|
-
},
|
|
285
|
-
null,
|
|
286
|
-
error => {
|
|
287
|
-
console.error(error);
|
|
288
|
-
reject(error);
|
|
289
|
-
}
|
|
290
|
-
);
|
|
291
|
-
});
|
|
292
|
-
});
|
|
293
|
-
return Promise.all(promises);
|
|
294
|
-
});
|
|
295
|
-
|
|
296
|
-
// Load Outline SVG Data
|
|
297
|
-
let svgLoadPromises = data.map(async item => {
|
|
298
|
-
if (item.outline) {
|
|
299
|
-
try {
|
|
300
|
-
const response = await fetch(item.outline, {
|
|
301
|
-
cache: 'no-store'
|
|
302
|
-
});
|
|
303
|
-
const svgText = await response.text();
|
|
304
|
-
|
|
305
|
-
const loader = new SVGLoader();
|
|
306
|
-
const parsed = loader.parse(svgText);
|
|
307
|
-
|
|
308
|
-
if (isEmpty(parsed.paths)) return null;
|
|
309
|
-
|
|
310
|
-
return {
|
|
311
|
-
paths: parsed.paths,
|
|
312
|
-
svgWidth:
|
|
313
|
-
parseFloat(parsed.xml.getAttribute('width')) ||
|
|
314
|
-
parsed.xml.viewBox?.animVal?.width ||
|
|
315
|
-
0,
|
|
316
|
-
svgHeight:
|
|
317
|
-
parseFloat(parsed.xml.getAttribute('height')) ||
|
|
318
|
-
parsed.xml.viewBox?.animVal?.height ||
|
|
319
|
-
0,
|
|
320
|
-
reverse: !!parseFloat(parsed.xml.getAttribute('height'))
|
|
321
|
-
? false
|
|
322
|
-
: true
|
|
323
|
-
};
|
|
324
|
-
} catch (err) {
|
|
325
|
-
console.error('Failed to load SVG:', item.outline, err);
|
|
326
|
-
return null;
|
|
327
|
-
}
|
|
328
|
-
} else {
|
|
329
|
-
return null;
|
|
330
|
-
}
|
|
331
|
-
});
|
|
332
|
-
|
|
333
|
-
let outlineSVGData = await Promise.all(svgLoadPromises);
|
|
334
|
-
// End: Load Outline SVG Data
|
|
335
|
-
|
|
336
|
-
const Item = [];
|
|
337
|
-
|
|
338
|
-
data.forEach((obj, index) => {
|
|
339
|
-
Item.push(
|
|
340
|
-
exporter({
|
|
341
|
-
...obj,
|
|
342
|
-
type: 'cabinet',
|
|
343
|
-
outlineSVGData: outlineSVGData[index],
|
|
344
|
-
render2DItem,
|
|
345
|
-
render3DItem
|
|
346
|
-
})
|
|
347
|
-
);
|
|
348
|
-
});
|
|
349
|
-
appliances.forEach(obj => {
|
|
350
|
-
Item.push(
|
|
351
|
-
exporter({
|
|
352
|
-
...obj,
|
|
353
|
-
render2DItem,
|
|
354
|
-
render3DItem: render3DApplianceItem,
|
|
355
|
-
type: 'appliance'
|
|
356
|
-
})
|
|
357
|
-
);
|
|
358
|
-
});
|
|
359
|
-
lighting.forEach(obj => {
|
|
360
|
-
Item.push(
|
|
361
|
-
exporter({
|
|
362
|
-
...obj,
|
|
363
|
-
type: 'lighting',
|
|
364
|
-
render2DItem,
|
|
365
|
-
render3DItem: render3DLightingItem
|
|
366
|
-
})
|
|
367
|
-
);
|
|
368
|
-
});
|
|
369
|
-
furnishing.forEach(obj => {
|
|
370
|
-
Item.push(
|
|
371
|
-
exporter({
|
|
372
|
-
...obj,
|
|
373
|
-
type: 'furnishing',
|
|
374
|
-
render2DItem,
|
|
375
|
-
render3DItem: render3DApplianceItem
|
|
376
|
-
})
|
|
377
|
-
);
|
|
378
|
-
});
|
|
379
|
-
|
|
380
|
-
for (let x in Item) MyCatalog.registerElement(Item[x]);
|
|
381
|
-
|
|
382
|
-
let MainComponent = (props, width, height) => (
|
|
383
|
-
<KitchenConfigurator
|
|
384
|
-
catalog={MyCatalog}
|
|
385
|
-
width={width}
|
|
386
|
-
height={height}
|
|
387
|
-
{...props}
|
|
388
|
-
logoImage={logoImg}
|
|
389
|
-
companyURL={companyUrl}
|
|
390
|
-
plugins={plugins}
|
|
391
|
-
toolbarButtons={toolbarButtons}
|
|
392
|
-
stateExtractor={state => state.get('KitchenConfigurator')}
|
|
393
|
-
categoryData={categoryData}
|
|
394
|
-
data={data}
|
|
395
|
-
configData={configdata}
|
|
396
|
-
/>
|
|
397
|
-
);
|
|
398
|
-
|
|
399
|
-
const queryClient = new QueryClient();
|
|
400
|
-
|
|
401
|
-
const MainApp = props => (
|
|
402
|
-
<QueryClientProvider client={queryClient}>
|
|
403
|
-
<ReactQueryDevtools initialIsOpen={false} />
|
|
404
|
-
<AppContext.Provider>
|
|
405
|
-
<Provider store={store}>
|
|
406
|
-
<ContainerDimensions>
|
|
407
|
-
{({ width, height }) => (
|
|
408
|
-
<HashRouter history={history.createHashHistory()}>
|
|
409
|
-
<Router history={browserHistory}>
|
|
410
|
-
<Switch>
|
|
411
|
-
<Route
|
|
412
|
-
exact
|
|
413
|
-
path="/:visualizerName/"
|
|
414
|
-
name="kc"
|
|
415
|
-
render={routeProps => (
|
|
416
|
-
<MainComponent
|
|
417
|
-
{...routeProps}
|
|
418
|
-
{...props}
|
|
419
|
-
width={width}
|
|
420
|
-
height={height}
|
|
421
|
-
/>
|
|
422
|
-
)}
|
|
423
|
-
/>
|
|
424
|
-
<Route path="/login" render={() => <Login />} />
|
|
425
|
-
<Route
|
|
426
|
-
path="/register"
|
|
427
|
-
render={() => <Register />}
|
|
428
|
-
/>
|
|
429
|
-
<Route
|
|
430
|
-
path="/:visualizerName/project/:role/:token/:pid"
|
|
431
|
-
render={routeProps => (
|
|
432
|
-
<MainComponent
|
|
433
|
-
{...routeProps}
|
|
434
|
-
{...props}
|
|
435
|
-
width={width}
|
|
436
|
-
height={height}
|
|
437
|
-
/>
|
|
438
|
-
)}
|
|
439
|
-
/>
|
|
440
|
-
</Switch>
|
|
441
|
-
</Router>
|
|
442
|
-
</HashRouter>
|
|
443
|
-
)}
|
|
444
|
-
</ContainerDimensions>
|
|
445
|
-
</Provider>
|
|
446
|
-
</AppContext.Provider>
|
|
447
|
-
</QueryClientProvider>
|
|
448
|
-
);
|
|
449
|
-
|
|
450
|
-
setTimeout(() => {
|
|
451
|
-
ReactDOM.render(
|
|
452
|
-
<CrossSignOn App={MainApp} />,
|
|
453
|
-
document.getElementById('app')
|
|
454
|
-
);
|
|
455
|
-
}, 100);
|
|
456
|
-
})
|
|
457
|
-
.catch(err => {
|
|
458
|
-
alert(
|
|
459
|
-
'Something wrong happened. Do you want to clear the cache and restart the app?'
|
|
460
|
-
);
|
|
461
|
-
console.log('Failed to load Category Data in src/renderer.jsx', err);
|
|
462
|
-
sessionStorage.clear();
|
|
463
|
-
store.dispatch(newProject());
|
|
464
|
-
});
|
|
465
|
-
});
|
|
466
|
-
}
|