Compare commits

..

40 Commits

Author SHA1 Message Date
8f32f29c03 Merge pull request 'lavoce' (#35) from lavoce into main
Reviewed-on: #35
2026-01-08 04:52:16 +00:00
5a7d64a05b Merge pull request 'fix: resize add log card' (#34) from lavoce into main
Reviewed-on: #34
2026-01-07 03:33:48 +00:00
e74b802a60 Merge pull request 'lavoce' (#33) from lavoce into main
Reviewed-on: #33
2026-01-06 11:30:27 +00:00
f436865b7f Merge pull request 'lavoce' (#32) from lavoce into main
Reviewed-on: #32
2026-01-05 03:41:39 +00:00
48437c3c50 Merge pull request 'lavoce' (#30) from lavoce into main
Reviewed-on: #30
2025-12-31 03:20:51 +00:00
a33c9b3b92 Merge pull request 'lavoce' (#29) from lavoce into main
Reviewed-on: #29
2025-12-23 05:22:06 +00:00
58d1f5c7ab Merge pull request 'Repair and replace svg' (#28) from lavoce into main
Reviewed-on: #28
2025-12-22 09:38:05 +00:00
c10a5bf62d Merge pull request 'lavoce' (#27) from lavoce into main
Reviewed-on: #27
2025-12-22 09:28:34 +00:00
6cc5042956 Merge pull request 'repair' (#26) from lavoce into main
Reviewed-on: #26
2025-11-28 07:17:06 +00:00
5079f8d316 Merge pull request 'lavoce' (#25) from lavoce into main
Reviewed-on: #25
2025-11-28 07:12:41 +00:00
7073390de7 Merge pull request 'lavoce' (#24) from lavoce into main
Reviewed-on: #24
2025-11-28 05:50:36 +00:00
4226a24e79 Merge pull request 'lavoce' (#23) from lavoce into main
Reviewed-on: #23
2025-11-28 05:10:26 +00:00
038009433f Merge pull request 'lavoce' (#22) from lavoce into main
Reviewed-on: #22
2025-11-25 03:50:54 +00:00
64ba51b17c Merge pull request 'lavoce' (#21) from lavoce into main
Reviewed-on: #21
2025-11-20 03:44:05 +00:00
47d0638a42 Merge pull request 'lavoce' (#20) from lavoce into main
Reviewed-on: #20
2025-11-19 01:05:19 +00:00
d8c5f3ed44 Merge pull request 'lavoce' (#19) from lavoce into main
Reviewed-on: #19
2025-11-18 00:26:36 +00:00
affd9146bb Merge pull request 'lavoce' (#18) from lavoce into main
Reviewed-on: #18
2025-11-17 08:27:39 +00:00
4022b3f8f4 Merge pull request 'lavoce' (#17) from lavoce into main
Reviewed-on: #17
2025-11-10 07:57:17 +00:00
446a4e2b95 Merge pull request 'lavoce' (#16) from lavoce into main
Reviewed-on: #16
2025-11-10 06:33:35 +00:00
83a475c708 Merge pull request 'Repair beautiful apps' (#15) from lavoce into main
Reviewed-on: #15
2025-11-04 10:01:47 +00:00
ab1c510a77 Merge pull request 'Repair bg-signin' (#14) from lavoce into main
Reviewed-on: #14
2025-11-04 08:48:59 +00:00
59859c6d18 Update public/web.config 2025-11-04 07:03:57 +00:00
2bd27937dc Update public/web.config 2025-11-04 07:02:55 +00:00
1058c660d6 Update public/web.config 2025-11-04 07:01:10 +00:00
35b2167791 Update public/web.config 2025-11-04 06:53:05 +00:00
ec676983d0 Update .gitignore 2025-11-04 06:51:39 +00:00
c07c5f8235 Update .gitignore 2025-11-04 06:47:31 +00:00
b32ad97034 Merge pull request 'Add side bar menus mobile mode' (#13) from lavoce into main
Reviewed-on: #13
2025-11-04 06:42:09 +00:00
76244f6f6e Merge pull request 'lavoce' (#12) from lavoce into main
Reviewed-on: #12
2025-11-04 06:23:15 +00:00
0a128cbb3c Merge pull request 'lavoce' (#11) from lavoce into main
Reviewed-on: #11
2025-10-28 09:47:36 +00:00
bd4ab26680 Merge pull request 'lavoce' (#10) from lavoce into main
Reviewed-on: #10
2025-10-28 04:48:54 +00:00
3e728a1ff5 Merge pull request 'lavoce' (#9) from lavoce into main
Reviewed-on: #9
2025-10-27 03:48:58 +00:00
9db143972e Merge pull request 'lavoce' (#8) from lavoce into main
Reviewed-on: #8
2025-10-25 09:19:36 +00:00
029ea269a7 Merge pull request 'lavoce' (#7) from lavoce into main
Reviewed-on: #7
2025-10-24 05:43:32 +00:00
4cdaa042da Merge pull request 'lavoce' (#6) from lavoce into main
Reviewed-on: #6
2025-10-23 07:28:11 +00:00
56af2a16c0 Merge pull request 'update file svg to src assets' (#5) from lavoce into main
Reviewed-on: #5
2025-10-23 04:52:13 +00:00
deadf2ffb4 Merge pull request 'lavoce' (#4) from lavoce into main
Reviewed-on: #4
2025-10-23 04:27:57 +00:00
4da80c7089 Merge pull request 'lavoce' (#3) from lavoce into main
Reviewed-on: #3
2025-10-22 05:59:57 +00:00
56e3ce78a6 Merge pull request 'lavoce' (#2) from lavoce into main
Reviewed-on: #2
2025-10-20 04:06:02 +00:00
7c2a019dd2 Merge pull request 'lavoce' (#1) from lavoce into main
Reviewed-on: #1
2025-09-17 08:39:35 +00:00
30 changed files with 1968 additions and 3200 deletions

View File

@@ -4,7 +4,3 @@ VITE_MQTT_SERVER=ws://localhost:1884
VITE_MQTT_USERNAME=
VITE_MQTT_PASSWORD=
VITE_KEY_SESSION=PetekRombonganPetekMorekMorakMarek
# VITE_WHATSAPP_URL=http://192.168.1.10:9531/qrview
VITE_WHATSAPP_URL=http://localhost:9531/qrview
# VITE_WHATSAPP_URL=https://117.102.231.130:9531/qrview

1
.gitignore vendored
View File

@@ -6,6 +6,7 @@ yarn-debug.log*
yarn-error.log*
pnpm-debug.log*
lerna-debug.log*
*.config
node_modules
dist

View File

@@ -1,48 +1,48 @@
{
"name": "antd-vite-react-call-of-duty",
"homepage": "/dashboard/home",
"private": true,
"version": "1.0.0",
"type": "module",
"scripts": {
"dev": "vite --host 0.0.0.0 --port 8592",
"build": "vite build",
"lint": "eslint . --ext js,jsx --report-unused-disable-directives --max-warnings 0",
"preview": "vite preview"
},
"dependencies": {
"@ant-design/icons": "^6.0.0",
"@nivo/line": "^0.88.0",
"@nivo/pie": "^0.88.0",
"antd": "^5.15.2",
"axios": "^1.8.4",
"browser-image-compression": "^2.0.2",
"crypto-js": "^4.2.0",
"dayjs": "^1.11.13",
"exceljs": "^4.4.0",
"file-saver": "^2.0.5",
"html2canvas": "^1.4.1",
"jspdf": "^3.0.4",
"jspdf-autotable": "^5.0.2",
"mqtt": "^5.14.0",
"qrcode": "^1.5.4",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"react-icons": "^4.11.0",
"react-router-dom": "^6.22.3",
"react-svg": "^16.3.0",
"recharts": "^3.6.0",
"sweetalert2": "^11.17.2"
},
"devDependencies": {
"@types/react": "^18.2.64",
"@types/react-dom": "^18.2.21",
"@vitejs/plugin-react": "^4.2.1",
"eslint": "^8.57.0",
"eslint-plugin-react": "^7.34.0",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-react-refresh": "^0.4.5",
"vite": "^5.1.6"
},
"packageManager": "pnpm@10.2.1+sha512.398035c7bd696d0ba0b10a688ed558285329d27ea994804a52bad9167d8e3a72bcb993f9699585d3ca25779ac64949ef422757a6c31102c12ab932e5cbe5cc92"
"name": "antd-vite-react-sypiu",
"homepage": "/dashboard/home",
"private": true,
"version": "1.0.0",
"type": "module",
"scripts": {
"dev": "vite",
"build": "vite build",
"lint": "eslint . --ext js,jsx --report-unused-disable-directives --max-warnings 0",
"preview": "vite preview"
},
"dependencies": {
"@ant-design/icons": "^6.0.0",
"@nivo/line": "^0.88.0",
"@nivo/pie": "^0.88.0",
"antd": "^5.15.2",
"axios": "^1.8.4",
"browser-image-compression": "^2.0.2",
"crypto-js": "^4.2.0",
"dayjs": "^1.11.13",
"exceljs": "^4.4.0",
"file-saver": "^2.0.5",
"html2canvas": "^1.4.1",
"jspdf": "^3.0.4",
"jspdf-autotable": "^5.0.2",
"mqtt": "^5.14.0",
"qrcode": "^1.5.4",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"react-icons": "^4.11.0",
"react-router-dom": "^6.22.3",
"react-svg": "^16.3.0",
"recharts": "^3.6.0",
"sweetalert2": "^11.17.2"
},
"devDependencies": {
"@types/react": "^18.2.64",
"@types/react-dom": "^18.2.21",
"@vitejs/plugin-react": "^4.2.1",
"eslint": "^8.57.0",
"eslint-plugin-react": "^7.34.0",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-react-refresh": "^0.4.5",
"vite": "^5.1.6"
},
"packageManager": "pnpm@10.2.1+sha512.398035c7bd696d0ba0b10a688ed558285329d27ea994804a52bad9167d8e3a72bcb993f9699585d3ca25779ac64949ef422757a6c31102c12ab932e5cbe5cc92"
}

View File

@@ -3,7 +3,7 @@
<system.webServer>
<rewrite>
<rules>
<rule name="reactViteSypiu">
<rule name="CallOfDuty">
<match url=".*" />
<conditions logicalGrouping="MatchAll">
<add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />

View File

@@ -36,7 +36,6 @@ import IndexNotification from './pages/notification/IndexNotification';
import IndexRole from './pages/role/IndexRole';
import IndexUser from './pages/user/IndexUser';
import IndexContact from './pages/contact/IndexContact';
import IndexWhatsAppControl from './pages/whatsAppControl/IndexWhatsAppControl';
import DetailNotificationTab from './pages/notificationDetail/IndexNotificationDetail';
import IndexVerificationSparepart from './pages/verificationSparepart/IndexVerificationSparepart';
@@ -145,10 +144,6 @@ const App = () => {
<Route index element={<IndexUser />} />
</Route>
<Route path="/whatsapp-control" element={<ProtectedRoute />}>
<Route index element={<IndexWhatsAppControl />} />
</Route>
<Route path="/contact" element={<ProtectedRoute />}>
<Route index element={<IndexContact />} />
</Route>

View File

@@ -82,34 +82,6 @@ const resendChatAllUser = async (notificationId) => {
return response.data;
};
// Searching
const searchData = async (queryParams) => {
const response = await SendRequest({
method: 'get',
prefix: `notification?criteria=${queryParams}`,
});
return response.data;
};
// Reminder Monthly
const reminderMonthly = async (id, queryParams) => {
const response = await SendRequest({
method: 'post',
prefix: `notifikasi-wa/reminder-monthly/${id}`,
params: queryParams,
});
return response.data;
};
const reminderCustom= async (id, queryParams) => {
const response = await SendRequest({
method: 'post',
prefix: `notifikasi-wa/reminder-custom/${id}`,
params: queryParams,
});
return response.data;
};
export {
getAllNotification,
getNotificationById,
@@ -120,7 +92,4 @@ export {
resendNotificationToUser,
resendChatByUser,
resendChatAllUser,
searchData,
reminderMonthly,
reminderCustom,
};

View File

@@ -1,12 +0,0 @@
import { SendRequest } from '../components/Global/ApiRequest';
const resetWA = async () => {
const response = await SendRequest({
method: 'post',
prefix: `notifikasi-wa/restart-wa`,
});
return response.data;
};
export { resetWA };

View File

@@ -37,14 +37,17 @@
<rect x="461.861" y="211.956" width="62.018" height="9.968" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px;" x="561" y="309.954" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Heater Temp SP</text>
<rect x="461.861" y="221.924" width="62.018" height="17.46" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="609.476" y="330.521" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">°F</text>
<rect x="461.424" y="242.149" width="62.018" height="9.968" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px; stroke-width: 1;" x="567.471" y="352.188" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Heater Temp</text>
<rect x="461.424" y="252.117" width="62.018" height="17.46" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="608.947" y="373.755" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">°F</text>
<rect x="535.456" y="242.272" width="62.018" height="9.968" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px; stroke-width: 1;" x="659" y="352.363" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Heater Temp</text>
<rect x="535.456" y="252.24" width="62.018" height="17.46" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="698.476" y="373.93" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">°C</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1; font-weight: bold;" x="748" y="347.676" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">HEATER</text>
<path style="fill: none; stroke: rgb(0, 0, 0); stroke-width: 1.525; transform-origin: 678.512px 258.693px;" d="M 678.467 229.321 L 678.558 288.066" transform="matrix(0, 1.184039, -0.844567, 0, -0.000022, -0.000005)"/>
@@ -107,10 +110,12 @@
<rect x="427.269" y="377.282" width="62.018" height="9.968" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px; stroke-width: 1;" x="532.167" y="545.681" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Dew Temp</text>
<rect x="427.269" y="387.25" width="62.018" height="17.46" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="567.643" y="567.248" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">°C</text>
<rect x="427.27" y="412.201" width="62.018" height="9.968" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px; stroke-width: 1;" x="532.168" y="595.681" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Dew Temp</text>
<rect x="427.27" y="422.169" width="62.018" height="17.46" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="567.644" y="617.248" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">°F</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 9px; stroke-width: 1; text-anchor: middle; font-weight: bolder;" x="602.463" y="573.003" transform="matrix(0.826913, 0, 0, 0.698383, 24.207672, -7.192523)">AIR<tspan x="602.4630126953125" dy="1em"></tspan>OUTLET</text>
<g transform="matrix(-0.387768, 0, 0, -0.200385, 743.634644, -199.991287)" style="transform-origin: 72.2405px 412.5px;">
@@ -174,36 +179,43 @@
<rect x="43.443" y="280.75" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="53.987" y="423.091" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RUN HOUR</text>
<rect x="126.135" y="280.75" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225" y="424.066" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.443" y="308.191" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; stroke-width: 1; font-weight: bold;" x="53.987" y="461.382" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">PURGE HOUR</text>
<rect x="126.135" y="308.191" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225" y="463.357" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.443" y="333.129" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; font-weight: 700; white-space: pre;" x="53.987" y="498.091" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">HEATER HOUR</text>
<rect x="126.135" y="333.129" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225" y="499.066" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.65" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(248, 213, 14);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; font-weight: 700; white-space: pre; stroke-width: 1;" x="54.237" y="536.777" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Alarm Info</text>
<rect x="126.341" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4501">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225.25" y="537.752" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.443" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="56.987" y="250.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT or LT Dry</text>
<rect x="126.135" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, -3.902357, 3.138935)" id="c_4022">#######</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">LT Dry</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177" y="251.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT Dry</text>
<rect x="43.443" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; stroke-width: 1; font-weight: bold;" x="53.987" y="288.876" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Opmode</text>
<rect x="126.135" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, -0.902357, 3.138935)" id="c_4015">#####</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">HTD</text>
<rect x="43.443" y="214.051" width="165.383" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; font-weight: 700; white-space: pre; stroke-width: 1;" x="53.987" y="322.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Step</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="233" y="323.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">s</text>
<rect x="43.443" y="241.422" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; font-weight: 700; white-space: pre; stroke-width: 1;" x="54.237" y="364.271" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Cycle Timer</text>
<rect x="126.341" y="241.068" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225.25" y="365.246" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">s</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; font-weight: 700; white-space: pre; stroke-width: 1;" x="141.894" y="324.069" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Time</text>
<rect x="870.356" y="142.816" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="1060.06" y="224.103" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Dryer Status</text>
<rect x="870.356" y="170.304" width="82.691" height="42.35" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
@@ -217,10 +229,17 @@
<rect x="870.356" y="344.9" width="82.691" height="42.35" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.702" cy="366.997" rx="20.673" ry="17.46"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="380.451" y="296.591" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="379.214" y="423.395" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.623" cy="320.662" rx="13.582" ry="12.517" id="c_4021"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="897.237" y="299.014" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.772" cy="233.876" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="896" y="425.818" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 35px; stroke-width: 1; font-weight: bold;" x="348.875" y="78.242" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">AIR DRYER UNIT A (01-CL-10532-A)</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 1.386371, 4.000207)">HTLS</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, -1.613663, 3.937793)">BLWR</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.447" y="617.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4005">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.446" y="567.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4004">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="653.279" y="373.97" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4001">####.##</text>
@@ -232,16 +251,11 @@
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177.05" y="323.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4008">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="168.775" y="365.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4007">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="92.151" y="325.554" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_4006">##</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_4018"/>
<ellipse style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(255, 172, 63);" cx="640.283" cy="271.689" rx="9.717" ry="7.689" id="c_4019"/>
<ellipse style="fill: rgb(63, 255, 69); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.254" cy="192.696" rx="20.673" ry="17.46" id="c_4016"/>
<ellipse style="fill: rgb(255, 159, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="279.12" rx="20.673" ry="17.46" id="c_4017"/>
<ellipse style="fill: rgb(255, 63, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="366.862" rx="20.673" ry="17.46" id="c_4020"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_4018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517" id="c_4018"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517" id="c_4021"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="763.772" cy="237.876" rx="13.582" ry="12.517" id="c_4021"/>
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id=""/> -->
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="320.687" rx="13.582" ry="12.517" id="-2"/> -->
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="763.418" cy="322.259" rx="13.582" ry="12.517" id="c_-2"/> -->
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="763.418" cy="237.483" rx="13.582" ry="12.517" id="c_-3"/> -->
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.685" cy="322.259" rx="13.582" ry="12.517" id="c_4018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.031" cy="234.094" rx="13.582" ry="12.517" id="c_4021"/>
</svg>

Before

Width:  |  Height:  |  Size: 41 KiB

After

Width:  |  Height:  |  Size: 41 KiB

View File

@@ -186,16 +186,17 @@
<rect x="43.65" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(248, 213, 14);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; font-weight: 700; white-space: pre; stroke-width: 1;" x="54.237" y="536.777" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Alarm Info</text>
<rect x="126.341" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5501">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225.25" y="537.752" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.443" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="56.987" y="250.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT or LT Dry</text>
<rect x="126.135" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, -3.902357, 3.138935)" id="c_5022">#######</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">LT Dry</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177" y="251.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT Dry</text>
<rect x="43.443" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; stroke-width: 1; font-weight: bold;" x="53.987" y="288.876" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Opmode</text>
<rect x="126.135" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 0.097643, 3.138935)" id="c_5015">#####</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">HTD</text>
<rect x="43.443" y="214.051" width="165.383" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; font-weight: 700; white-space: pre; stroke-width: 1;" x="53.987" y="322.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Step</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="233" y="323.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">s</text>
@@ -217,10 +218,16 @@
<rect x="870.356" y="344.9" width="82.691" height="42.35" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.702" cy="366.997" rx="20.673" ry="17.46"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="380.451" y="296.591" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="379.214" y="423.395" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="897.237" y="299.014" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.772" cy="233.876" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="896" y="425.818" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 35px; stroke-width: 1; font-weight: bold;" x="348.875" y="78.242" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">AIR DRYER UNIT B (01-CL-10535-B)</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 1.386371, 4.000207)">HTLS</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, -1.613663, 3.937793)">BLWR</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.447" y="617.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5005">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.446" y="567.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5004">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="653.279" y="373.97" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5001">####.##</text>
@@ -232,16 +239,12 @@
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177.05" y="323.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5008">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="168.775" y="365.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5007">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="92.151" y="325.554" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_5006">##</text>
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.517" rx="13.582" ry="12.517" id=""/> -->
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_5018"/>
<ellipse style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(255, 172, 63);" cx="640.283" cy="271.689" rx="9.717" ry="7.689" id="c_5019"/>
<ellipse style="fill: rgb(63, 255, 69); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.254" cy="192.696" rx="20.673" ry="17.46" id="c_5016"/>
<ellipse style="fill: rgb(255, 159, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="279.12" rx="20.673" ry="17.46" id="c_5017"/>
<ellipse style="fill: rgb(255, 63, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="366.862" rx="20.673" ry="17.46" id="c_5020"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_5018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517" id="c_5018"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517" id="c_5021"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.772" cy="233.876" rx="13.582" ry="12.517" id="c_5021"/>
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="320.662" rx="13.582" ry="12.517" id=""/> -->
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="763.418" cy="322.125" rx="13.582" ry="12.517" id="c_-2"/> -->
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.418" cy="234.26" rx="13.582" ry="12.517" id="c_-3"/> -->
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.623" cy="320.662" rx="13.582" ry="12.517" id="c_5021"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.685" cy="322.259" rx="13.582" ry="12.517" id="c_5018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.031" cy="234.094" rx="13.582" ry="12.517" id="c_5021"/>
</svg>

Before

Width:  |  Height:  |  Size: 41 KiB

After

Width:  |  Height:  |  Size: 41 KiB

View File

@@ -186,16 +186,17 @@
<rect x="43.65" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(248, 213, 14);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; font-weight: 700; white-space: pre; stroke-width: 1;" x="54.237" y="536.777" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Alarm Info</text>
<rect x="126.341" y="360.147" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6501">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="159.3" y="537.792" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="225.25" y="537.752" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">H</text>
<rect x="43.443" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="56.987" y="250.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT or LT Dry</text>
<rect x="126.135" y="160.275" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, -3.902357, 3.138935)" id="c_6022">#######</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="180.05" y="251.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">LT Dry</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177" y="251.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">RT Dry</text>
<rect x="43.443" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.763;"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; stroke-width: 1; font-weight: bold;" x="53.987" y="288.876" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Opmode</text>
<rect x="126.135" y="187.715" width="82.691" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, -1.902357, 3.138935)" id="c_6015">#####</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">HTD</text>
<rect x="43.443" y="214.051" width="165.383" height="27.103" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 13px; font-weight: 700; white-space: pre; stroke-width: 1;" x="53.987" y="322.585" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">Step</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="233" y="323.56" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">s</text>
@@ -217,10 +218,17 @@
<rect x="870.356" y="344.9" width="82.691" height="42.35" style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.702" cy="366.997" rx="20.673" ry="17.46"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="380.451" y="296.591" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="379.214" y="423.395" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="897.237" y="299.014" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">REGEN</text>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.772" cy="233.876" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 14px; stroke-width: 1; font-weight: bold;" x="896" y="425.818" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">DRYING</text>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517"/>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 35px; stroke-width: 1; font-weight: bold;" x="348.875" y="78.242" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)">AIR DRYER UNIT C (01-CL-10539-C)</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, 1.386371, 4.000207)">HTLS</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="183.349" y="288.807" transform="matrix(0.826913, 0, 0, 0.698383, -1.613663, 3.937793)">BLWR</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.447" y="617.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6005">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="522.446" y="567.288" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6004">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 12px; stroke-width: 1;" x="653.279" y="373.97" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6001">####.##</text>
@@ -232,16 +240,12 @@
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="177.05" y="323.6" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6008">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="168.775" y="365.807" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6007">####.##</text>
<text style="white-space: pre; fill: rgb(51, 51, 51); font-family: Arial, sans-serif; font-size: 15px; stroke-width: 1;" x="92.151" y="325.554" transform="matrix(0.826913, 0, 0, 0.698383, 2.097643, 3.138935)" id="c_6006">##</text>
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.517" rx="13.582" ry="12.517" id=""/> -->
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_6018"/>
<ellipse style="stroke: rgb(0, 0, 0); stroke-width: 0.763; fill: rgb(255, 172, 63);" cx="640.283" cy="271.689" rx="9.717" ry="7.689" id="c_6019"/>
<ellipse style="fill: rgb(63, 255, 69); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.254" cy="192.696" rx="20.673" ry="17.46" id="c_6016"/>
<ellipse style="fill: rgb(255, 159, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="279.12" rx="20.673" ry="17.46" id="c_6017"/>
<ellipse style="fill: rgb(255, 63, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="911.352" cy="366.862" rx="20.673" ry="17.46" id="c_6020"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="336.418" cy="237.483" rx="13.582" ry="12.517" id="c_6018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.96" cy="322.354" rx="13.582" ry="12.517" id="c_6018"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.016" rx="13.582" ry="12.517" id="c_6021"/>
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.418" cy="237.483" rx="13.582" ry="12.517" id="c_6021"/>
<!-- <ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="763.418" cy="322.692" rx="13.582" ry="12.517" id="c_-2"/> -->
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.418" cy="321.095" rx="13.582" ry="12.517" id=""/> -->
<!-- <ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="761.418" cy="237.483" rx="13.582" ry="12.517" id="c_-3"/> -->
<ellipse style="fill: rgb(255, 204, 63); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.685" cy="322.259" rx="13.582" ry="12.517" id="c_6018"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="335.623" cy="320.662" rx="13.582" ry="12.517" id="c_6021"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.763;" cx="762.031" cy="234.094" rx="13.582" ry="12.517" id="c_6021"/>
</svg>

Before

Width:  |  Height:  |  Size: 41 KiB

After

Width:  |  Height:  |  Size: 41 KiB

File diff suppressed because it is too large Load Diff

Before

Width:  |  Height:  |  Size: 177 KiB

After

Width:  |  Height:  |  Size: 177 KiB

File diff suppressed because it is too large Load Diff

Before

Width:  |  Height:  |  Size: 177 KiB

After

Width:  |  Height:  |  Size: 177 KiB

File diff suppressed because it is too large Load Diff

Before

Width:  |  Height:  |  Size: 177 KiB

After

Width:  |  Height:  |  Size: 177 KiB

View File

@@ -3,12 +3,12 @@
<defs>
<bx:grid x="0" y="0" width="25" height="25"/>
</defs>
<rect x="12.259" y="8.086" width="924.818" height="441.914" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<rect x="25" y="66.111" width="900" height="358.889" style="stroke: rgb(0, 0, 0); fill: rgb(255, 255, 255);"/>
<rect x="75.168" y="97.354" width="100.126" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="75.168" y="118.75" width="100.126" height="43.75" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="150.26" cy="129.561" rx="11.265" ry="9.613"/>
<g transform="matrix(1.133434, 0, 0, 1.08014, 15.782269, 151.992333)" style="">
<rect x="12.226" y="12.005" width="924.818" height="476.396" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<rect x="25" y="75" width="900" height="400" style="stroke: rgb(0, 0, 0); fill: rgb(255, 255, 255);"/>
<rect x="50" y="100.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="50" y="125" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="125.124" cy="137.355" rx="11.269" ry="10.987"/>
<g transform="matrix(1.13391, 0, 0, 1.234446, -9.410634, 162.99009)" style="">
<path style="fill: rgb(0, 0, 0); stroke-width: 1;" d="M 363.181 109.151 L 363.181 110.989 L 460.721 110.989 L 469.183 107.313 L 469.183 105.958 L 460.721 109.151 L 363.181 109.151 Z"/>
<path style="fill: rgb(115, 135, 166); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 361.061 109.151 L 361.061 53.909 L 462.836 53.909 L 462.836 109.151 L 361.061 109.151 Z"/>
<path style="fill: rgb(166, 186, 217); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 445.801 105.475 L 445.801 57.586 L 454.374 57.586 L 454.374 105.475 L 445.801 105.475 Z"/>
@@ -53,31 +53,31 @@
<path style="fill: rgb(89, 109, 140); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 462.836 53.909 L 471.299 50.233 L 471.299 105.475 L 462.836 109.151 L 462.836 53.909 Z"/>
<path style="fill: rgb(191, 211, 242); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 462.836 53.909 L 471.299 50.233 L 369.521 50.233 L 361.061 53.909 L 462.836 53.909 Z"/>
</g>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre;" x="56" y="116.982" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">AirDryer A</text>
<rect x="75.168" y="140.625" width="99.958" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.368" y="141.716" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.949" y="168.123" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.007" y="167.208" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)" id="c_4009">####</text>
<rect x="75" y="206.73" width="100.126" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="75" y="228.125" width="100.126" height="43.75" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="150.092" cy="238.935" rx="11.265" ry="9.613"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="241.982" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">AirDryer B</text>
<rect x="75" y="250" width="99.958" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="266.716" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="293.123" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="292.208" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)" id="c_5009">####</text>
<rect x="75" y="316.104" width="100.126" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="75" y="337.5" width="100.126" height="43.75" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="150.092" cy="348.311" rx="11.265" ry="9.613"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="366.982" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">AirDryer C</text>
<rect x="75" y="359.375" width="99.958" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="391.716" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="418.123" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="417.208" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)" id="c_6009">####</text>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 275.084 118.75 L 375.042 118.75 L 375.042 250 L 425.021 250"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 275.084 228.125 L 375.042 228.125 L 375.042 250 L 425.021 250"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 275.084 337.5 L 375.042 337.5 L 375.042 250 L 425.021 250"/>
<g transform="matrix(0.99958, 0, 0, 0.875, 75.168186, -78.125439)" style="">
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre;" x="56" y="116.982">AirDryer A</text>
<rect x="50" y="150" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.368" y="141.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.949" y="168.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.007" y="167.208">####</text>
<rect x="49.832" y="225.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="49.832" y="250" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="124.956" cy="262.355" rx="11.269" ry="10.987"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="241.982">AirDryer B</text>
<rect x="49.832" y="275" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="266.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="293.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="292.208">####</text>
<rect x="49.832" y="350.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="49.832" y="375" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="124.956" cy="387.355" rx="11.269" ry="10.987"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="366.982">AirDryer C</text>
<rect x="49.832" y="400" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="391.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="418.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="417.208">####</text>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 250 125 L 350 125 L 350 275 L 400 275"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 250 250 L 350 250 L 350 275 L 400 275"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 250 375 L 350 375 L 350 275 L 400 275"/>
<g transform="matrix(1, 0, 0, 1, 49.999999, -99.999998)" style="">
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 717.857 292.93 L 717.857 292.651 L 717.857 292.442 L 717.857 292.163 L 717.857 291.954 L 717.857 291.744 L 717.857 291.535 L 717.857 291.396 L 717.914 291.186 L 717.914 291.046 L 717.972 290.907 L 718.029 290.837 L 718.086 290.698 L 718.143 290.558 L 718.201 290.488 L 718.258 290.419 L 718.372 290.349 L 718.487 290.279 L 718.602 290.209 L 718.716 290.14 L 718.888 290.14 L 719.06 290.07 L 719.231 290.07 L 719.46 290 L 719.632 290 L 719.919 290 L 720.147 290 L 720.434 290 L 720.72 290 L 721.063 290 L 721.407 290 L 721.751 290 L 722.151 290 L 770.706 290 L 771.106 290 L 771.45 290 L 771.794 290 L 772.137 290 L 772.423 290 L 772.71 290 L 772.939 290 L 773.225 290 L 773.397 290.07 L 773.626 290.07 L 773.798 290.14 L 773.969 290.14 L 774.141 290.209 L 774.256 290.279 L 774.37 290.349 L 774.485 290.419 L 774.599 290.488 L 774.657 290.558 L 774.714 290.698 L 774.771 290.837 L 774.828 290.977 L 774.886 291.117 L 774.943 291.256 L 774.943 291.465 L 775 291.674 L 775 291.884 L 775 292.093 L 775 292.303 L 775 292.581 L 775 292.86 L 775 293.209 L 775 293.488 L 775 335.558 L 775 335.907 L 775 336.256 L 775 336.604 L 775 336.884 L 775 337.163 L 775 337.442 L 775 337.72 L 775 337.93 L 774.943 338.14 L 774.943 338.349 L 774.943 338.488 L 774.886 338.628 L 774.886 338.767 L 774.828 338.907 L 774.771 339.047 L 774.714 339.117 L 774.657 339.256 L 774.599 339.326 L 774.485 339.396 L 774.427 339.465 L 774.313 339.465 L 774.198 339.535 L 774.084 339.535 L 773.969 339.604 L 773.798 339.604 L 773.683 339.604 L 773.511 339.604 L 773.339 339.674 L 773.168 339.674 L 772.939 339.674 L 772.71 339.674 L 772.481 339.674 L 721.579 339.674 L 721.235 339.674 L 720.892 339.674 L 720.663 339.674 L 720.377 339.674 L 720.09 339.604 L 719.861 339.604 L 719.69 339.604 L 719.46 339.604 L 719.289 339.535 L 719.117 339.535 L 718.945 339.465 L 718.831 339.465 L 718.659 339.396 L 718.544 339.326 L 718.43 339.256 L 718.372 339.117 L 718.258 339.047 L 718.201 338.907 L 718.143 338.767 L 718.086 338.628 L 718.029 338.488 L 717.972 338.349 L 717.914 338.14 L 717.914 337.93 L 717.914 337.72 L 717.857 337.442 L 717.857 337.163 L 717.857 336.884 L 717.857 336.604 L 717.857 336.256 L 717.857 335.907 L 717.857 335.558 L 717.857 292.93 Z"/>
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 732.114 339.674 L 760.743 339.674 L 760.743 342.884 L 732.114 342.884 L 732.114 339.674 Z"/>
<path style="fill: rgb(67, 67, 67); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 722.151 299.419 L 722.151 299.07 L 722.151 298.791 L 722.151 298.442 L 722.151 298.163 L 722.151 297.954 L 722.151 297.675 L 722.209 297.465 L 722.209 297.256 L 722.209 297.046 L 722.266 296.837 L 722.323 296.698 L 722.323 296.558 L 722.381 296.419 L 722.495 296.279 L 722.553 296.209 L 722.61 296.07 L 722.725 296 L 722.838 295.93 L 722.953 295.86 L 723.067 295.791 L 723.239 295.791 L 723.354 295.721 L 723.526 295.721 L 723.754 295.651 L 723.926 295.651 L 724.155 295.651 L 724.385 295.651 L 724.671 295.651 L 724.9 295.651 L 725.243 295.651 L 725.53 295.651 L 725.873 295.651 L 767.557 295.651 L 767.843 295.651 L 768.129 295.651 L 768.358 295.651 L 768.587 295.651 L 768.816 295.651 L 769.045 295.721 L 769.217 295.721 L 769.389 295.791 L 769.561 295.791 L 769.675 295.86 L 769.79 295.86 L 769.962 295.93 L 770.076 296 L 770.133 296.07 L 770.247 296.139 L 770.305 296.209 L 770.362 296.349 L 770.419 296.419 L 770.477 296.558 L 770.534 296.698 L 770.591 296.837 L 770.591 296.907 L 770.649 297.046 L 770.649 297.256 L 770.649 297.396 L 770.706 297.604 L 770.706 297.744 L 770.706 297.954 L 770.706 298.163 L 770.706 298.442 L 770.706 298.651 L 770.706 298.861 L 770.706 327.744 L 770.706 328.093 L 770.706 328.372 L 770.706 328.581 L 770.706 328.861 L 770.763 329.07 L 770.763 329.279 L 770.763 329.488 L 770.763 329.628 L 770.763 329.838 L 770.763 329.977 L 770.706 330.117 L 770.706 330.186 L 770.649 330.326 L 770.649 330.465 L 770.591 330.535 L 770.534 330.604 L 770.477 330.674 L 770.419 330.744 L 770.305 330.814 L 770.19 330.883 L 770.076 330.883 L 769.962 330.883 L 769.79 330.953 L 769.618 330.953 L 769.446 330.953 L 769.274 331.023 L 769.045 331.023 L 768.759 331.023 L 768.53 331.023 L 768.244 331.023 L 767.9 331.023 L 767.557 331.023 L 725.873 331.023 L 725.53 331.023 L 725.243 331.023 L 724.9 331.023 L 724.671 331.023 L 724.385 331.023 L 724.155 331.023 L 723.926 331.023 L 723.754 331.023 L 723.526 331.023 L 723.354 331.023 L 723.239 331.023 L 723.067 330.953 L 722.953 330.953 L 722.838 330.883 L 722.725 330.814 L 722.61 330.744 L 722.553 330.674 L 722.495 330.604 L 722.381 330.465 L 722.323 330.326 L 722.323 330.186 L 722.266 330.046 L 722.209 329.838 L 722.209 329.628 L 722.209 329.419 L 722.151 329.209 L 722.151 328.93 L 722.151 328.651 L 722.151 328.302 L 722.151 327.954 L 722.151 327.604 L 722.151 327.186 L 722.151 299.419 Z"/>
@@ -96,17 +96,17 @@
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 697.566 291.592 L 692.847 291.592 L 692.847 292.643 L 697.566 292.643 L 697.566 291.592 Z"/>
<circle style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" cx="890.673" cy="114.148" r="1.051" transform="matrix(1.142857, 0, 0, 1.000013, -320.346635, 178.493448)"/>
</g>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 549.968 228.125 L 599.947 228.125 L 599.947 184.375 L 749.884 184.375"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 549.968 228.125 L 599.947 228.125 L 599.947 359.375 L 749.884 359.375"/>
<rect x="424.853" y="140.506" width="125.116" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="425.021" y="162.5" width="124.947" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="425.352" y="167.628" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">PLC AirDryer</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="426.101" y="192.839" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">IP : 192.168.0.3</text>
<rect x="749.884" y="96.756" width="125.116" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="750.053" y="118.75" width="124.947" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="759.52" y="117.628" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">PC Station</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.269" y="142.839" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">IP : 192.168.0.2</text>
<g transform="matrix(0.99958, 0, 0, 0.875, 75.168186, 96.875524)" style="">
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 525 250 L 575 250 L 575 200 L 725 200"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 525 250 L 575 250 L 575 400 L 725 400"/>
<rect x="399.832" y="149.864" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="400" y="175" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="425.352" y="167.628">PLC AirDryer</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="426.101" y="192.839">IP : 192.168.0.3</text>
<rect x="725" y="99.864" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="725.168" y="125" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="759.52" y="117.628">PC Station</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.269" y="142.839">IP : 192.168.0.2</text>
<g transform="matrix(1, 0, 0, 1, 49.999999, 99.999998)" style="">
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 717.857 292.93 L 717.857 292.651 L 717.857 292.442 L 717.857 292.163 L 717.857 291.954 L 717.857 291.744 L 717.857 291.535 L 717.857 291.396 L 717.914 291.186 L 717.914 291.046 L 717.972 290.907 L 718.029 290.837 L 718.086 290.698 L 718.143 290.558 L 718.201 290.488 L 718.258 290.419 L 718.372 290.349 L 718.487 290.279 L 718.602 290.209 L 718.716 290.14 L 718.888 290.14 L 719.06 290.07 L 719.231 290.07 L 719.46 290 L 719.632 290 L 719.919 290 L 720.147 290 L 720.434 290 L 720.72 290 L 721.063 290 L 721.407 290 L 721.751 290 L 722.151 290 L 770.706 290 L 771.106 290 L 771.45 290 L 771.794 290 L 772.137 290 L 772.423 290 L 772.71 290 L 772.939 290 L 773.225 290 L 773.397 290.07 L 773.626 290.07 L 773.798 290.14 L 773.969 290.14 L 774.141 290.209 L 774.256 290.279 L 774.37 290.349 L 774.485 290.419 L 774.599 290.488 L 774.657 290.558 L 774.714 290.698 L 774.771 290.837 L 774.828 290.977 L 774.886 291.117 L 774.943 291.256 L 774.943 291.465 L 775 291.674 L 775 291.884 L 775 292.093 L 775 292.303 L 775 292.581 L 775 292.86 L 775 293.209 L 775 293.488 L 775 335.558 L 775 335.907 L 775 336.256 L 775 336.604 L 775 336.884 L 775 337.163 L 775 337.442 L 775 337.72 L 775 337.93 L 774.943 338.14 L 774.943 338.349 L 774.943 338.488 L 774.886 338.628 L 774.886 338.767 L 774.828 338.907 L 774.771 339.047 L 774.714 339.117 L 774.657 339.256 L 774.599 339.326 L 774.485 339.396 L 774.427 339.465 L 774.313 339.465 L 774.198 339.535 L 774.084 339.535 L 773.969 339.604 L 773.798 339.604 L 773.683 339.604 L 773.511 339.604 L 773.339 339.674 L 773.168 339.674 L 772.939 339.674 L 772.71 339.674 L 772.481 339.674 L 721.579 339.674 L 721.235 339.674 L 720.892 339.674 L 720.663 339.674 L 720.377 339.674 L 720.09 339.604 L 719.861 339.604 L 719.69 339.604 L 719.46 339.604 L 719.289 339.535 L 719.117 339.535 L 718.945 339.465 L 718.831 339.465 L 718.659 339.396 L 718.544 339.326 L 718.43 339.256 L 718.372 339.117 L 718.258 339.047 L 718.201 338.907 L 718.143 338.767 L 718.086 338.628 L 718.029 338.488 L 717.972 338.349 L 717.914 338.14 L 717.914 337.93 L 717.914 337.72 L 717.857 337.442 L 717.857 337.163 L 717.857 336.884 L 717.857 336.604 L 717.857 336.256 L 717.857 335.907 L 717.857 335.558 L 717.857 292.93 Z"/>
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 732.114 339.674 L 760.743 339.674 L 760.743 342.884 L 732.114 342.884 L 732.114 339.674 Z"/>
<path style="fill: rgb(67, 67, 67); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 722.151 299.419 L 722.151 299.07 L 722.151 298.791 L 722.151 298.442 L 722.151 298.163 L 722.151 297.954 L 722.151 297.675 L 722.209 297.465 L 722.209 297.256 L 722.209 297.046 L 722.266 296.837 L 722.323 296.698 L 722.323 296.558 L 722.381 296.419 L 722.495 296.279 L 722.553 296.209 L 722.61 296.07 L 722.725 296 L 722.838 295.93 L 722.953 295.86 L 723.067 295.791 L 723.239 295.791 L 723.354 295.721 L 723.526 295.721 L 723.754 295.651 L 723.926 295.651 L 724.155 295.651 L 724.385 295.651 L 724.671 295.651 L 724.9 295.651 L 725.243 295.651 L 725.53 295.651 L 725.873 295.651 L 767.557 295.651 L 767.843 295.651 L 768.129 295.651 L 768.358 295.651 L 768.587 295.651 L 768.816 295.651 L 769.045 295.721 L 769.217 295.721 L 769.389 295.791 L 769.561 295.791 L 769.675 295.86 L 769.79 295.86 L 769.962 295.93 L 770.076 296 L 770.133 296.07 L 770.247 296.139 L 770.305 296.209 L 770.362 296.349 L 770.419 296.419 L 770.477 296.558 L 770.534 296.698 L 770.591 296.837 L 770.591 296.907 L 770.649 297.046 L 770.649 297.256 L 770.649 297.396 L 770.706 297.604 L 770.706 297.744 L 770.706 297.954 L 770.706 298.163 L 770.706 298.442 L 770.706 298.651 L 770.706 298.861 L 770.706 327.744 L 770.706 328.093 L 770.706 328.372 L 770.706 328.581 L 770.706 328.861 L 770.763 329.07 L 770.763 329.279 L 770.763 329.488 L 770.763 329.628 L 770.763 329.838 L 770.763 329.977 L 770.706 330.117 L 770.706 330.186 L 770.649 330.326 L 770.649 330.465 L 770.591 330.535 L 770.534 330.604 L 770.477 330.674 L 770.419 330.744 L 770.305 330.814 L 770.19 330.883 L 770.076 330.883 L 769.962 330.883 L 769.79 330.953 L 769.618 330.953 L 769.446 330.953 L 769.274 331.023 L 769.045 331.023 L 768.759 331.023 L 768.53 331.023 L 768.244 331.023 L 767.9 331.023 L 767.557 331.023 L 725.873 331.023 L 725.53 331.023 L 725.243 331.023 L 724.9 331.023 L 724.671 331.023 L 724.385 331.023 L 724.155 331.023 L 723.926 331.023 L 723.754 331.023 L 723.526 331.023 L 723.354 331.023 L 723.239 331.023 L 723.067 330.953 L 722.953 330.953 L 722.838 330.883 L 722.725 330.814 L 722.61 330.744 L 722.553 330.674 L 722.495 330.604 L 722.381 330.465 L 722.323 330.326 L 722.323 330.186 L 722.266 330.046 L 722.209 329.838 L 722.209 329.628 L 722.209 329.419 L 722.151 329.209 L 722.151 328.93 L 722.151 328.651 L 722.151 328.302 L 722.151 327.954 L 722.151 327.604 L 722.151 327.186 L 722.151 299.419 Z"/>
@@ -125,13 +125,13 @@
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 697.566 291.592 L 692.847 291.592 L 692.847 292.643 L 697.566 292.643 L 697.566 291.592 Z"/>
<circle style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" cx="890.673" cy="114.148" r="1.051" transform="matrix(1.142857, 0, 0, 1.000013, -320.346635, 178.493448)"/>
</g>
<rect x="749.716" y="271.756" width="125.116" height="21.994" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="749.884" y="293.75" width="124.947" height="21.875" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="760.352" y="317.628" transform="matrix(0.99958, 0, 0, 0.875, 25.188995, 9.375002)">PC Server</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.1" y="317.975" transform="matrix(0.99958, 0, 0, 0.875, 22.190208, 31.131118)">IP : 192.168.0.99<tspan x="751.0999755859375" dy="1em"></tspan></text>
<rect x="724.832" y="299.864" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="725" y="325" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="760.352" y="317.628">PC Server</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.1" y="317.975" transform="matrix(1, 0, 0, 1, -3.000031, 24.863983)">IP : xxx.xxx.xx.xx<tspan x="751.0999755859375" dy="1em"></tspan></text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 30px; white-space: pre; stroke-width: 1;" x="316.458" y="50.984">OVERVIEW AIR DRYER</text>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 0, 0);" d="M 649.927 75 L 649.927 109.235 L 649.927 240.485 L 649.927 425"/>
<g transform="matrix(0.999579, 0, 0, 0.777807, -1032.377984, 48.060908)" style="">
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 0, 0);" d="M 625 75 L 625 114.125 L 625 264.125 L 625 475"/>
<g transform="matrix(0.999999, 0, 0, 0.888921, -1058.006891, 44.212168)" style="">
<g id="Group_Base" transform="matrix(1, 0, 0, 1, 1236.05109, 62.756969)">
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M4.392,105.741h62.834v2.253H4.392V105.741z"/>
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M0,112.498l1.014-1.126H2.14v-11.261H1.014L0,98.984h4.392v13.514H0z "/>
@@ -234,7 +234,7 @@
<path fill="#B2B2B2" stroke="#4C4C4C" stroke-width="0.25" d="M31.418,1.466l1.576-1.464l2.252,2.365L33.67,3.943L31.418,1.466z"/>
</g>
</g>
<g transform="matrix(0.999579, 0, 0, 0.777807, -1035.419488, 157.436745)" style="">
<g transform="matrix(0.999999, 0, 0, 0.888921, -1061.049982, 169.212228)" style="">
<g id="group-1" transform="matrix(1, 0, 0, 1, 1236.05109, 62.756969)">
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M4.392,105.741h62.834v2.253H4.392V105.741z"/>
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M0,112.498l1.014-1.126H2.14v-11.261H1.014L0,98.984h4.392v13.514H0z "/>
@@ -337,7 +337,7 @@
<path fill="#B2B2B2" stroke="#4C4C4C" stroke-width="0.25" d="M31.418,1.466l1.576-1.464l2.252,2.365L33.67,3.943L31.418,1.466z"/>
</g>
</g>
<g transform="matrix(0.999579, 0, 0, 0.777807, -1035.419366, 266.810713)" style="">
<g transform="matrix(0.999999, 0, 0, 0.888921, -1061.04986, 294.212174)" style="">
<g id="group-9" transform="matrix(1, 0, 0, 1, 1236.05109, 62.756969)">
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M4.392,105.741h62.834v2.253H4.392V105.741z"/>
<path fill="#4C4C4C" stroke="#4C4C4C" stroke-width="0.25" d="M0,112.498l1.014-1.126H2.14v-11.261H1.014L0,98.984h4.392v13.514H0z "/>

Before

Width:  |  Height:  |  Size: 57 KiB

After

Width:  |  Height:  |  Size: 56 KiB

View File

@@ -3,12 +3,12 @@
<defs>
<bx:grid x="0" y="0" width="25" height="25"/>
</defs>
<rect y="12.005" width="924.818" height="437.995" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);" x="12.012"/>
<rect y="59" width="900" height="375" style="stroke: rgb(0, 0, 0); fill: rgb(255, 255, 255);" x="25"/>
<rect x="75" y="98.845" width="100.147" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="75" y="121.667" width="100.147" height="46.667" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="150.108" cy="133.198" rx="11.267" ry="10.255"/>
<g transform="matrix(1.115917, 0, 0, 1.04224, 14.334309, 48.503848)" style="">
<rect x="12.226" y="12.005" width="924.818" height="462.995" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<rect x="25" y="75" width="900" height="375" style="stroke: rgb(0, 0, 0); fill: rgb(255, 255, 255);"/>
<rect x="50" y="100.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="50" y="125" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="125.124" cy="137.355" rx="11.269" ry="10.987"/>
<g transform="matrix(1.116151, 0, 0, 1.116686, -10.678418, 46.611243)" style="">
<path style="fill: rgb(204, 204, 204); stroke-width: 1;" d="M 166.356 47.81 L 278.348 47.81 L 278.348 114.973 L 166.356 114.973 L 166.356 47.81 Z"/>
<path style="fill: rgb(199, 199, 199); stroke-width: 1;" d="M 166.356 95.477 L 278.348 67.396 L 278.348 114.973 L 166.356 114.973 L 166.356 95.477 Z"/>
<path style="fill: rgb(194, 194, 194); stroke-width: 1;" d="M 166.356 98.16 L 278.348 70.258 L 278.348 114.973 L 166.356 114.973 L 166.356 98.16 Z"/>
@@ -47,7 +47,7 @@
<path style="fill: rgb(76, 76, 76); stroke-width: 1;" d="M 210.637 66.859 L 222.296 84.566 L 222.296 74.729 L 217.139 66.859 L 210.637 66.859 Z"/>
<path style="fill: none; stroke: rgb(255, 255, 255); stroke-width: 2;" d="M 222.969 50.046 L 275.434 50.046"/>
</g>
<g transform="matrix(1.133672, 0, 0, 1.15215, 15.601832, 157.124169)" style="">
<g transform="matrix(1.13391, 0, 0, 1.234446, -9.410634, 162.99009)" style="">
<path style="fill: rgb(0, 0, 0); stroke-width: 1;" d="M 363.181 109.151 L 363.181 110.989 L 460.721 110.989 L 469.183 107.313 L 469.183 105.958 L 460.721 109.151 L 363.181 109.151 Z"/>
<path style="fill: rgb(115, 135, 166); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 361.061 109.151 L 361.061 53.909 L 462.836 53.909 L 462.836 109.151 L 361.061 109.151 Z"/>
<path style="fill: rgb(166, 186, 217); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 445.801 105.475 L 445.801 57.586 L 454.374 57.586 L 454.374 105.475 L 445.801 105.475 Z"/>
@@ -92,28 +92,28 @@
<path style="fill: rgb(89, 109, 140); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 462.836 53.909 L 471.299 50.233 L 471.299 105.475 L 462.836 109.151 L 462.836 53.909 Z"/>
<path style="fill: rgb(191, 211, 242); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 462.836 53.909 L 471.299 50.233 L 369.521 50.233 L 361.061 53.909 L 462.836 53.909 Z"/>
</g>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre;" x="56" y="116.982" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">COMPRESSOR A</text>
<rect x="75" y="145" width="99.979" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.368" y="141.716" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.949" y="168.123" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.007" y="167.208" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)" id="c_1012">####</text>
<rect x="74.832" y="215.511" width="100.147" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="74.832" y="238.333" width="100.147" height="46.667" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="149.941" cy="249.865" rx="11.267" ry="10.255"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="241.982" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">COMPRESSOR B</text>
<rect x="74.832" y="261.667" width="99.979" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="266.716" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="293.123" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="292.208" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)" id="c_2012">####</text>
<rect x="74.832" y="332.178" width="100.147" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="74.832" y="355" width="100.147" height="46.667" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="149.941" cy="366.531" rx="11.267" ry="10.255"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="366.982" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">COMPRESSOR C</text>
<rect x="74.832" y="378.333" width="99.979" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="391.716" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="418.123" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="417.208" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)" id="c_3012">####</text>
<g transform="matrix(1.115917, 0, 0, 1.04224, 14.334339, 165.170587)" style="">
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre;" x="56" y="116.982">COMPRESSOR A</text>
<rect x="50" y="150" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0);"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.368" y="141.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.949" y="168.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.007" y="167.208">####</text>
<rect x="49.832" y="225.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="49.832" y="250" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="124.956" cy="262.355" rx="11.269" ry="10.987"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="241.982">COMPRESSOR B</text>
<rect x="49.832" y="275" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="266.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="293.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="292.208">####</text>
<rect x="49.832" y="350.548" width="100.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="49.832" y="375" width="100.168" height="50" style="stroke: rgb(0, 0, 0); stroke-width: 0.693; fill: rgb(244, 248, 248);"/>
<ellipse style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 0.693;" cx="124.956" cy="387.355" rx="11.269" ry="10.987"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="55.832" y="366.982">COMPRESSOR C</text>
<rect x="49.832" y="400" width="100" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="56.2" y="391.716">On/Off</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="120.781" y="418.123">H</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 15px; white-space: pre; stroke-width: 1;" x="55.839" y="417.208">####</text>
<g transform="matrix(1.116151, 0, 0, 1.116686, -10.678391, 171.611261)" style="">
<path style="fill: rgb(204, 204, 204); stroke-width: 1;" d="M 166.356 47.81 L 278.348 47.81 L 278.348 114.973 L 166.356 114.973 L 166.356 47.81 Z"/>
<path style="fill: rgb(199, 199, 199); stroke-width: 1;" d="M 166.356 95.477 L 278.348 67.396 L 278.348 114.973 L 166.356 114.973 L 166.356 95.477 Z"/>
<path style="fill: rgb(194, 194, 194); stroke-width: 1;" d="M 166.356 98.16 L 278.348 70.258 L 278.348 114.973 L 166.356 114.973 L 166.356 98.16 Z"/>
@@ -152,7 +152,7 @@
<path style="fill: rgb(76, 76, 76); stroke-width: 1;" d="M 210.637 66.859 L 222.296 84.566 L 222.296 74.729 L 217.139 66.859 L 210.637 66.859 Z"/>
<path style="fill: none; stroke: rgb(255, 255, 255); stroke-width: 2;" d="M 222.969 50.046 L 275.434 50.046"/>
</g>
<g transform="matrix(1.115917, 0, 0, 1.04224, 14.334345, 281.837234)" style="">
<g transform="matrix(1.116151, 0, 0, 1.116686, -10.678387, 296.611283)" style="">
<path style="fill: rgb(204, 204, 204); stroke-width: 1;" d="M 166.356 47.81 L 278.348 47.81 L 278.348 114.973 L 166.356 114.973 L 166.356 47.81 Z"/>
<path style="fill: rgb(199, 199, 199); stroke-width: 1;" d="M 166.356 95.477 L 278.348 67.396 L 278.348 114.973 L 166.356 114.973 L 166.356 95.477 Z"/>
<path style="fill: rgb(194, 194, 194); stroke-width: 1;" d="M 166.356 98.16 L 278.348 70.258 L 278.348 114.973 L 166.356 114.973 L 166.356 98.16 Z"/>
@@ -191,10 +191,10 @@
<path style="fill: rgb(76, 76, 76); stroke-width: 1;" d="M 210.637 66.859 L 222.296 84.566 L 222.296 74.729 L 217.139 66.859 L 210.637 66.859 Z"/>
<path style="fill: none; stroke: rgb(255, 255, 255); stroke-width: 2;" d="M 222.969 50.046 L 275.434 50.046"/>
</g>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 324.947 121.667 L 374.937 121.667 L 374.937 261.667 L 424.926 261.667"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 324.947 238.333 L 374.937 238.333 L 374.937 261.667 L 424.926 261.667"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 324.947 355 L 374.937 355 L 374.937 261.667 L 424.926 261.667"/>
<g transform="matrix(0.99979, 0, 0, 0.933333, 75.000027, -88.333371)" style="">
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 300 125 L 350 125 L 350 275 L 400 275"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 300 250 L 350 250 L 350 275 L 400 275"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 4, 255);" d="M 300 375 L 350 375 L 350 275 L 400 275"/>
<g transform="matrix(1, 0, 0, 1, 49.999999, -99.999998)" style="">
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 717.857 292.93 L 717.857 292.651 L 717.857 292.442 L 717.857 292.163 L 717.857 291.954 L 717.857 291.744 L 717.857 291.535 L 717.857 291.396 L 717.914 291.186 L 717.914 291.046 L 717.972 290.907 L 718.029 290.837 L 718.086 290.698 L 718.143 290.558 L 718.201 290.488 L 718.258 290.419 L 718.372 290.349 L 718.487 290.279 L 718.602 290.209 L 718.716 290.14 L 718.888 290.14 L 719.06 290.07 L 719.231 290.07 L 719.46 290 L 719.632 290 L 719.919 290 L 720.147 290 L 720.434 290 L 720.72 290 L 721.063 290 L 721.407 290 L 721.751 290 L 722.151 290 L 770.706 290 L 771.106 290 L 771.45 290 L 771.794 290 L 772.137 290 L 772.423 290 L 772.71 290 L 772.939 290 L 773.225 290 L 773.397 290.07 L 773.626 290.07 L 773.798 290.14 L 773.969 290.14 L 774.141 290.209 L 774.256 290.279 L 774.37 290.349 L 774.485 290.419 L 774.599 290.488 L 774.657 290.558 L 774.714 290.698 L 774.771 290.837 L 774.828 290.977 L 774.886 291.117 L 774.943 291.256 L 774.943 291.465 L 775 291.674 L 775 291.884 L 775 292.093 L 775 292.303 L 775 292.581 L 775 292.86 L 775 293.209 L 775 293.488 L 775 335.558 L 775 335.907 L 775 336.256 L 775 336.604 L 775 336.884 L 775 337.163 L 775 337.442 L 775 337.72 L 775 337.93 L 774.943 338.14 L 774.943 338.349 L 774.943 338.488 L 774.886 338.628 L 774.886 338.767 L 774.828 338.907 L 774.771 339.047 L 774.714 339.117 L 774.657 339.256 L 774.599 339.326 L 774.485 339.396 L 774.427 339.465 L 774.313 339.465 L 774.198 339.535 L 774.084 339.535 L 773.969 339.604 L 773.798 339.604 L 773.683 339.604 L 773.511 339.604 L 773.339 339.674 L 773.168 339.674 L 772.939 339.674 L 772.71 339.674 L 772.481 339.674 L 721.579 339.674 L 721.235 339.674 L 720.892 339.674 L 720.663 339.674 L 720.377 339.674 L 720.09 339.604 L 719.861 339.604 L 719.69 339.604 L 719.46 339.604 L 719.289 339.535 L 719.117 339.535 L 718.945 339.465 L 718.831 339.465 L 718.659 339.396 L 718.544 339.326 L 718.43 339.256 L 718.372 339.117 L 718.258 339.047 L 718.201 338.907 L 718.143 338.767 L 718.086 338.628 L 718.029 338.488 L 717.972 338.349 L 717.914 338.14 L 717.914 337.93 L 717.914 337.72 L 717.857 337.442 L 717.857 337.163 L 717.857 336.884 L 717.857 336.604 L 717.857 336.256 L 717.857 335.907 L 717.857 335.558 L 717.857 292.93 Z"/>
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 732.114 339.674 L 760.743 339.674 L 760.743 342.884 L 732.114 342.884 L 732.114 339.674 Z"/>
<path style="fill: rgb(67, 67, 67); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 722.151 299.419 L 722.151 299.07 L 722.151 298.791 L 722.151 298.442 L 722.151 298.163 L 722.151 297.954 L 722.151 297.675 L 722.209 297.465 L 722.209 297.256 L 722.209 297.046 L 722.266 296.837 L 722.323 296.698 L 722.323 296.558 L 722.381 296.419 L 722.495 296.279 L 722.553 296.209 L 722.61 296.07 L 722.725 296 L 722.838 295.93 L 722.953 295.86 L 723.067 295.791 L 723.239 295.791 L 723.354 295.721 L 723.526 295.721 L 723.754 295.651 L 723.926 295.651 L 724.155 295.651 L 724.385 295.651 L 724.671 295.651 L 724.9 295.651 L 725.243 295.651 L 725.53 295.651 L 725.873 295.651 L 767.557 295.651 L 767.843 295.651 L 768.129 295.651 L 768.358 295.651 L 768.587 295.651 L 768.816 295.651 L 769.045 295.721 L 769.217 295.721 L 769.389 295.791 L 769.561 295.791 L 769.675 295.86 L 769.79 295.86 L 769.962 295.93 L 770.076 296 L 770.133 296.07 L 770.247 296.139 L 770.305 296.209 L 770.362 296.349 L 770.419 296.419 L 770.477 296.558 L 770.534 296.698 L 770.591 296.837 L 770.591 296.907 L 770.649 297.046 L 770.649 297.256 L 770.649 297.396 L 770.706 297.604 L 770.706 297.744 L 770.706 297.954 L 770.706 298.163 L 770.706 298.442 L 770.706 298.651 L 770.706 298.861 L 770.706 327.744 L 770.706 328.093 L 770.706 328.372 L 770.706 328.581 L 770.706 328.861 L 770.763 329.07 L 770.763 329.279 L 770.763 329.488 L 770.763 329.628 L 770.763 329.838 L 770.763 329.977 L 770.706 330.117 L 770.706 330.186 L 770.649 330.326 L 770.649 330.465 L 770.591 330.535 L 770.534 330.604 L 770.477 330.674 L 770.419 330.744 L 770.305 330.814 L 770.19 330.883 L 770.076 330.883 L 769.962 330.883 L 769.79 330.953 L 769.618 330.953 L 769.446 330.953 L 769.274 331.023 L 769.045 331.023 L 768.759 331.023 L 768.53 331.023 L 768.244 331.023 L 767.9 331.023 L 767.557 331.023 L 725.873 331.023 L 725.53 331.023 L 725.243 331.023 L 724.9 331.023 L 724.671 331.023 L 724.385 331.023 L 724.155 331.023 L 723.926 331.023 L 723.754 331.023 L 723.526 331.023 L 723.354 331.023 L 723.239 331.023 L 723.067 330.953 L 722.953 330.953 L 722.838 330.883 L 722.725 330.814 L 722.61 330.744 L 722.553 330.674 L 722.495 330.604 L 722.381 330.465 L 722.323 330.326 L 722.323 330.186 L 722.266 330.046 L 722.209 329.838 L 722.209 329.628 L 722.209 329.419 L 722.151 329.209 L 722.151 328.93 L 722.151 328.651 L 722.151 328.302 L 722.151 327.954 L 722.151 327.604 L 722.151 327.186 L 722.151 299.419 Z"/>
@@ -213,17 +213,17 @@
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 697.566 291.592 L 692.847 291.592 L 692.847 292.643 L 697.566 292.643 L 697.566 291.592 Z"/>
<circle style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" cx="890.673" cy="114.148" r="1.051" transform="matrix(1.142857, 0, 0, 1.000013, -320.346635, 178.493448)"/>
</g>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 549.901 238.333 L 599.89 238.333 L 599.89 191.667 L 749.858 191.667"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 549.901 238.333 L 599.89 238.333 L 599.89 355 L 749.858 355"/>
<rect x="424.759" y="144.873" width="125.142" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="424.926" y="168.333" width="124.974" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="417.352" y="167.628" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">PLC Compressor</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="426.101" y="192.839" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">IP : 192.168.0.1</text>
<rect x="749.858" y="98.206" width="125.142" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="750.026" y="121.667" width="124.974" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="759.52" y="117.628" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">PC Station</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.269" y="142.839" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">IP : 192.168.0.2</text>
<g transform="matrix(0.99979, 0, 0, 0.933333, 75.000027, 75.000027)" style="">
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 525 250 L 575 250 L 575 200 L 725 200"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(6, 255, 0);" d="M 525 250 L 575 250 L 575 375 L 725 375"/>
<rect x="399.832" y="149.864" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="400" y="175" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="417.352" y="167.628">PLC Compressor</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="426.101" y="192.839">IP : 192.168.0.1</text>
<rect x="725" y="99.864" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="725.168" y="125" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="759.52" y="117.628">PC Station</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.269" y="142.839">IP : 192.168.0.2</text>
<g transform="matrix(1, 0, 0, 1, 49.999999, 74.999996)" style="">
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 717.857 292.93 L 717.857 292.651 L 717.857 292.442 L 717.857 292.163 L 717.857 291.954 L 717.857 291.744 L 717.857 291.535 L 717.857 291.396 L 717.914 291.186 L 717.914 291.046 L 717.972 290.907 L 718.029 290.837 L 718.086 290.698 L 718.143 290.558 L 718.201 290.488 L 718.258 290.419 L 718.372 290.349 L 718.487 290.279 L 718.602 290.209 L 718.716 290.14 L 718.888 290.14 L 719.06 290.07 L 719.231 290.07 L 719.46 290 L 719.632 290 L 719.919 290 L 720.147 290 L 720.434 290 L 720.72 290 L 721.063 290 L 721.407 290 L 721.751 290 L 722.151 290 L 770.706 290 L 771.106 290 L 771.45 290 L 771.794 290 L 772.137 290 L 772.423 290 L 772.71 290 L 772.939 290 L 773.225 290 L 773.397 290.07 L 773.626 290.07 L 773.798 290.14 L 773.969 290.14 L 774.141 290.209 L 774.256 290.279 L 774.37 290.349 L 774.485 290.419 L 774.599 290.488 L 774.657 290.558 L 774.714 290.698 L 774.771 290.837 L 774.828 290.977 L 774.886 291.117 L 774.943 291.256 L 774.943 291.465 L 775 291.674 L 775 291.884 L 775 292.093 L 775 292.303 L 775 292.581 L 775 292.86 L 775 293.209 L 775 293.488 L 775 335.558 L 775 335.907 L 775 336.256 L 775 336.604 L 775 336.884 L 775 337.163 L 775 337.442 L 775 337.72 L 775 337.93 L 774.943 338.14 L 774.943 338.349 L 774.943 338.488 L 774.886 338.628 L 774.886 338.767 L 774.828 338.907 L 774.771 339.047 L 774.714 339.117 L 774.657 339.256 L 774.599 339.326 L 774.485 339.396 L 774.427 339.465 L 774.313 339.465 L 774.198 339.535 L 774.084 339.535 L 773.969 339.604 L 773.798 339.604 L 773.683 339.604 L 773.511 339.604 L 773.339 339.674 L 773.168 339.674 L 772.939 339.674 L 772.71 339.674 L 772.481 339.674 L 721.579 339.674 L 721.235 339.674 L 720.892 339.674 L 720.663 339.674 L 720.377 339.674 L 720.09 339.604 L 719.861 339.604 L 719.69 339.604 L 719.46 339.604 L 719.289 339.535 L 719.117 339.535 L 718.945 339.465 L 718.831 339.465 L 718.659 339.396 L 718.544 339.326 L 718.43 339.256 L 718.372 339.117 L 718.258 339.047 L 718.201 338.907 L 718.143 338.767 L 718.086 338.628 L 718.029 338.488 L 717.972 338.349 L 717.914 338.14 L 717.914 337.93 L 717.914 337.72 L 717.857 337.442 L 717.857 337.163 L 717.857 336.884 L 717.857 336.604 L 717.857 336.256 L 717.857 335.907 L 717.857 335.558 L 717.857 292.93 Z"/>
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 732.114 339.674 L 760.743 339.674 L 760.743 342.884 L 732.114 342.884 L 732.114 339.674 Z"/>
<path style="fill: rgb(67, 67, 67); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 722.151 299.419 L 722.151 299.07 L 722.151 298.791 L 722.151 298.442 L 722.151 298.163 L 722.151 297.954 L 722.151 297.675 L 722.209 297.465 L 722.209 297.256 L 722.209 297.046 L 722.266 296.837 L 722.323 296.698 L 722.323 296.558 L 722.381 296.419 L 722.495 296.279 L 722.553 296.209 L 722.61 296.07 L 722.725 296 L 722.838 295.93 L 722.953 295.86 L 723.067 295.791 L 723.239 295.791 L 723.354 295.721 L 723.526 295.721 L 723.754 295.651 L 723.926 295.651 L 724.155 295.651 L 724.385 295.651 L 724.671 295.651 L 724.9 295.651 L 725.243 295.651 L 725.53 295.651 L 725.873 295.651 L 767.557 295.651 L 767.843 295.651 L 768.129 295.651 L 768.358 295.651 L 768.587 295.651 L 768.816 295.651 L 769.045 295.721 L 769.217 295.721 L 769.389 295.791 L 769.561 295.791 L 769.675 295.86 L 769.79 295.86 L 769.962 295.93 L 770.076 296 L 770.133 296.07 L 770.247 296.139 L 770.305 296.209 L 770.362 296.349 L 770.419 296.419 L 770.477 296.558 L 770.534 296.698 L 770.591 296.837 L 770.591 296.907 L 770.649 297.046 L 770.649 297.256 L 770.649 297.396 L 770.706 297.604 L 770.706 297.744 L 770.706 297.954 L 770.706 298.163 L 770.706 298.442 L 770.706 298.651 L 770.706 298.861 L 770.706 327.744 L 770.706 328.093 L 770.706 328.372 L 770.706 328.581 L 770.706 328.861 L 770.763 329.07 L 770.763 329.279 L 770.763 329.488 L 770.763 329.628 L 770.763 329.838 L 770.763 329.977 L 770.706 330.117 L 770.706 330.186 L 770.649 330.326 L 770.649 330.465 L 770.591 330.535 L 770.534 330.604 L 770.477 330.674 L 770.419 330.744 L 770.305 330.814 L 770.19 330.883 L 770.076 330.883 L 769.962 330.883 L 769.79 330.953 L 769.618 330.953 L 769.446 330.953 L 769.274 331.023 L 769.045 331.023 L 768.759 331.023 L 768.53 331.023 L 768.244 331.023 L 767.9 331.023 L 767.557 331.023 L 725.873 331.023 L 725.53 331.023 L 725.243 331.023 L 724.9 331.023 L 724.671 331.023 L 724.385 331.023 L 724.155 331.023 L 723.926 331.023 L 723.754 331.023 L 723.526 331.023 L 723.354 331.023 L 723.239 331.023 L 723.067 330.953 L 722.953 330.953 L 722.838 330.883 L 722.725 330.814 L 722.61 330.744 L 722.553 330.674 L 722.495 330.604 L 722.381 330.465 L 722.323 330.326 L 722.323 330.186 L 722.266 330.046 L 722.209 329.838 L 722.209 329.628 L 722.209 329.419 L 722.151 329.209 L 722.151 328.93 L 722.151 328.651 L 722.151 328.302 L 722.151 327.954 L 722.151 327.604 L 722.151 327.186 L 722.151 299.419 Z"/>
@@ -242,10 +242,10 @@
<path style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" d="M 697.566 291.592 L 692.847 291.592 L 692.847 292.643 L 697.566 292.643 L 697.566 291.592 Z"/>
<circle style="fill: rgb(255, 255, 255); stroke: rgb(76, 76, 76); stroke-width: 2;" cx="890.673" cy="114.148" r="1.051" transform="matrix(1.142857, 0, 0, 1.000013, -320.346635, 178.493448)"/>
</g>
<rect x="749.69" y="261.667" width="125.142" height="23.46" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="749.858" y="285.127" width="124.974" height="23.333" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="760.352" y="292.764" transform="matrix(0.99979, 0, 0, 0.933333, 25.010492, 5.000001)">PC Server</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.1" y="317.975" transform="matrix(0.99979, 0, 0, 0.933333, 22.011123, 5.000001)">IP : 192.168.0.99<tspan x="751.0999755859375" dy="1em"></tspan></text>
<rect x="724.832" y="275" width="125.168" height="25.136" style="stroke: rgb(0, 0, 0); fill: rgb(120, 231, 228); stroke-width: 0.693;"/>
<rect x="725" y="300.136" width="125" height="25" style="fill: rgb(216, 216, 216); stroke: rgb(0, 0, 0); stroke-width: 1;"/>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="760.352" y="292.764">PC Server</text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 12px; white-space: pre; stroke-width: 1;" x="751.1" y="317.975" transform="matrix(1, 0, 0, 1, -3, 0)">IP : xxx.xxx.xx.xx<tspan x="751.0999755859375" dy="1em"></tspan></text>
<text style="fill: rgb(51, 51, 51); font-family: Bahnschrift; font-size: 30px; white-space: pre; stroke-width: 1;" x="312.458" y="50.984">OVERVIEW COMPRESSOR</text>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 0, 0);" d="M 649.879 60.253 L 649.879 99.16 L 649.879 248.324 L 649.879 433.164"/>
<path style="fill: none; stroke-width: 1.386; stroke-dasharray: 6, 4; stroke: rgb(0, 0, 0);" d="M 625 75 L 625 114.125 L 625 264.125 L 625 450"/>
</svg>

Before

Width:  |  Height:  |  Size: 46 KiB

After

Width:  |  Height:  |  Size: 45 KiB

View File

@@ -1,52 +0,0 @@
import { Input } from "antd";
import { useEffect, useState, useRef } from "react";
const InputNumber = ({
name,
value = 0,
onChange,
...props
}) => {
const [inputValue, setInputValue] = useState(
value !== null && value !== undefined ? value.toString() : ''
);
useEffect(() => {
const newValue = value !== null && value !== undefined ? value.toString() : '';
setInputValue(newValue);
}, [value]);
const handleChange = (e) => {
const rawValue = e.target.value;
if (/^\d*$/.test(rawValue)) {
setInputValue(rawValue);
const numValue = rawValue === '' ? 0 : parseInt(rawValue, 10);
// Kirim event object sintetis yang konsisten dengan handler biasa
onChange?.({
target: {
name: name,
value: numValue
}
});
}
};
const handleFocus = (e) => {
// Pilih semua teks saat fokus (opsional)
e.target.select();
};
return (
<Input
{...props}
name={name} // Teruskan name ke input
value={inputValue}
onChange={handleChange}
onFocus={handleFocus}
style={{ textAlign: 'left' }}
/>
);
};
export { InputNumber };

View File

@@ -10,8 +10,7 @@ const topics = [
'PIU_COD/COMPRESSOR/OVERVIEW',
'PIU_COD/COMPRESSOR/COMPRESSOR_A',
'PIU_COD/COMPRESSOR/COMPRESSOR_B',
'PIU_COD/COMPRESSOR/COMPRESSOR_C',
'PIU_COD/ERROR_CODE/SIM',
'PIU_COD/COMPRESSOR/COMPRESSOR_C'
];
const options = {
keepalive: 30,
@@ -74,101 +73,29 @@ const listenMessage = (callback) => {
});
};
const colorIds = ['c_1023', 'c_2023', 'c_2023'];
const StatusColor = (el, num) => {
switch (num) {
case 1:
el.style.fill = 'orange';
break;
case 2:
el.style.fill = 'rgb(7,250,14)';
break;
default:
el.style.fill = 'rgb(216,216,216)';
}
};
const dryerIds = ['c_4018', 'c_4021', 'c_5018', 'c_5021', 'c_6018', 'c_6021'];
const handleBoolean = (svg, el, value) => {
if (!dryerIds.includes(el.id)) {
el.style.display = value ? '' : 'none';
return;
}
const i = dryerIds.indexOf(el.id);
const id1 = dryerIds[i - (i % 2)];
const id2 = dryerIds[i - (i % 2) + 1];
const els1 = svg.querySelectorAll(`#${id1}`);
const els2 = svg.querySelectorAll(`#${id2}`);
if (!els1 || !els2) return;
els1.forEach(el => {
el.style.fill = value ? 'rgb(216,216,216)' : 'rgb(255, 204, 63)';
});
els2.forEach(el => {
el.style.fill = value ? 'rgb(255, 204, 63)' : 'rgb(216,216,216)';
});
};
const handleNumber = (el, value) => {
const num = Number(value);
if (colorIds.includes(el.id)) {
StatusColor(el, num);
} else {
el.textContent = num.toFixed(2);
}
};
const handleOther = (el, value) => {
el.textContent = value;
};
const setValSvg = (listenTopic, svg) => {
client.on('message', (topic, message) => {
// console.log(topic ,' = ', listenTopic);
if (topic === listenTopic) {
const objChanel = JSON.parse(message);
Object.entries(objChanel).forEach(([key, value]) => {
// console.log(key, value);
const el = svg.getElementById(key);
if (!el) return;
// else if (el.id === 'c_2014' || el.id === 'c_2024') {
// el.setAttribute('text-anchor', 'middle');
// el.setAttribute('x', '10%');
// }
if (typeof value === 'boolean') {
handleBoolean(svg, el, value);
} else if (!isNaN(value)) {
handleNumber(el, value);
} else {
handleOther(el, value);
if (el) {
if (value === true) {
el.style.display = ''; // sembunyikan
} else if (value === false) {
el.style.display = 'none';
} else if (!isNaN(value)) {
el.textContent = Number(value ?? 0.0).toFixed(2);
} else {
el.textContent = value;
}
}
});
const target = svg.querySelector('text[x="225.25"][y="537.752"]');
if (target) target.remove();
}
});
};
// === NOTIFICATION LISTENER ===
const notifListeners = [];
const onNotifUpdate = (callback) => {
notifListeners.push(callback);
};
client.on('message', (topic, message) => {
if (topic === import.meta.env.VITE_MQTT_TOPIC_COD) {
try {
const payload = JSON.parse(message.toString());
notifListeners.forEach((cb) => cb(payload));
} catch (err) {
console.error('Invalid notif payload', err);
}
}
});
export { publishMessage, listenMessage, setValSvg, onNotifUpdate };
export { publishMessage, listenMessage, setValSvg };

View File

@@ -20,19 +20,6 @@ const NotifOk = ({ icon, title, message }) => {
});
};
const NotifSmall = ({ icon, title, message }) => {
Swal.fire({
toast: true,
position: 'top-end',
icon: icon,
title: title,
text: message,
showConfirmButton: false,
timer: 2000,
timerProgressBar: true,
});
};
const NotifConfirmDialog = ({
icon,
title,
@@ -80,4 +67,4 @@ const QuestionConfirmSubmit = ({ icon, title, message, onConfirm, onCancel }) =>
});
};
export { NotifAlert, NotifOk, NotifSmall, NotifConfirmDialog, QuestionConfirmSubmit };
export { NotifAlert, NotifOk, NotifConfirmDialog, QuestionConfirmSubmit };

View File

@@ -7,7 +7,6 @@ import {
DatabaseOutlined,
SettingOutlined,
UserOutlined,
GlobalOutlined,
AntDesignOutlined,
ShoppingCartOutlined,
ShoppingOutlined,
@@ -37,14 +36,6 @@ import {
} from '@ant-design/icons';
const { Text } = Typography;
const host = window.location.hostname;
const isLocal =
host === '127.0.0.1' ||
host === 'localhost' ||
host.startsWith('192.168.') ||
host.startsWith('10.') ||
host.startsWith('172.');
const allItems = [
{
@@ -234,19 +225,6 @@ const allItems = [
</Link>
),
},
...(isLocal
? [
{
key: 'whatsapp-control',
icon: <GlobalOutlined style={{ fontSize: '19px' }} />,
label: (
<Link to="/whatsapp-control" className="fontMenus">
WhatsApp Control
</Link>
),
},
]
: []),
// {
// key: 'jadwal-shift',
// icon: <CalendarOutlined style={{ fontSize: '19px' }} />,
@@ -272,7 +250,6 @@ const LayoutMenu = () => {
if (pathname === '/dashboard/home') return 'home';
if (pathname === '/user') return 'user';
if (pathname === '/role') return 'role';
if (pathname === '/whatsapp-control') return 'whatsapp-control';
if (pathname === '/notification') return 'notification';
if (pathname === '/jadwal-shift') return 'jadwal-shift';
if (pathname === '/contact') return 'contact';

View File

@@ -13,7 +13,6 @@ const DetailContact = memo(function DetailContact(props) {
id: '',
name: '',
phone: '',
email: '',
is_active: true,
};
@@ -35,22 +34,6 @@ const DetailContact = memo(function DetailContact(props) {
[name]: value,
}));
}
if (name === 'email') {
const email = value.trim();
setFormData((prev) => ({
...prev,
[name]: email,
}));
setErrors((prev) => ({
...prev,
email:
email && !/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email)
? 'Format email tidak valid'
: '',
}));
}
};
@@ -68,7 +51,6 @@ const DetailContact = memo(function DetailContact(props) {
const validationRules = [
{ field: 'name', label: 'Contact Name', required: true },
{ field: 'phone', label: 'Phone', required: true },
{ field: 'email', label: 'Email', required: false },
];
if (
@@ -102,23 +84,10 @@ const DetailContact = memo(function DetailContact(props) {
return;
}
// Validasi Email
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (formData.email && !emailRegex.test(formData.email.trim())) {
NotifOk({
icon: 'warning',
title: 'Peringatan',
message: 'Format email tidak valid.',
});
setConfirmLoading(false);
return;
}
try {
const contactData = {
contact_name: formData.name,
contact_phone: formData.phone.replace(/[\s\-\(\)]/g, ''), // Clean phone number
email: formData.email?.trim(),
is_active: formData.is_active,
};
@@ -165,7 +134,6 @@ const DetailContact = memo(function DetailContact(props) {
setFormData({
name: props.selectedData.contact_name || props.selectedData.name,
phone: props.selectedData.contact_phone || props.selectedData.phone,
email: props.selectedData.contact_email || props.selectedData.email,
is_active:
props.selectedData.is_active || props.selectedData.status === 'active',
});
@@ -173,7 +141,6 @@ const DetailContact = memo(function DetailContact(props) {
setFormData({
name: '',
phone: '',
email: '',
is_active: true,
});
}
@@ -282,19 +249,6 @@ const DetailContact = memo(function DetailContact(props) {
style={{ color: formData.is_active ? '#000000' : '#ff4d4f' }}
/>
</div>
<div style={{ marginBottom: 12 }}>
<Text strong>Email</Text>
{/* <Text style={{ color: 'red' }}> *</Text> */}
<Input
name="email"
value={formData.email}
onChange={handleInputChange}
placeholder="Enter Email Number"
readOnly={props.readOnly}
maxLength={64}
style={{ color: formData.is_active ? '#000000' : '#ff4d4f' }}
/>
</div>
{/* Contact Type */}
{/* <div style={{ marginBottom: 12 }}>
<Text strong>Contact Type</Text>

View File

@@ -13,18 +13,13 @@ import {
Space,
ConfigProvider,
} from 'antd';
import { EditOutlined, DeleteOutlined } from '@ant-design/icons';
import {
EditOutlined,
DeleteOutlined
} from '@ant-design/icons';
import { NotifAlert, NotifOk, NotifConfirmDialog } from '../../../components/Global/ToastNotif';
import { useBreadcrumb } from '../../../layout/LayoutBreadcrumb';
import {
getBrandById,
createBrand,
createErrorCode,
getErrorCodesByBrandId,
updateErrorCode,
deleteErrorCode,
deleteBrand,
} from '../../../api/master-brand';
import { getBrandById, createBrand, createErrorCode, getErrorCodesByBrandId, updateErrorCode, deleteErrorCode, deleteBrand } from '../../../api/master-brand';
import BrandForm from './component/BrandForm';
import ErrorCodeForm from './component/ErrorCodeForm';
import SolutionForm from './component/SolutionForm';
@@ -47,9 +42,7 @@ const AddBrandDevice = () => {
const [selectedSparepartIds, setSelectedSparepartIds] = useState([]);
const [loading, setLoading] = useState(false);
const tab = searchParams.get('tab');
const [currentStep, setCurrentStep] = useState(
tab === 'error-codes' ? 1 : location.state?.phase || 0
);
const [currentStep, setCurrentStep] = useState(tab === 'error-codes' ? 1 : (location.state?.phase || 0));
const [editingErrorCodeKey, setEditingErrorCodeKey] = useState(null);
const [isErrorCodeFormReadOnly, setIsErrorCodeFormReadOnly] = useState(false);
const [searchText, setSearchText] = useState('');
@@ -75,7 +68,7 @@ const AddBrandDevice = () => {
const values = solutionForm.getFieldsValue(true);
const solutions = [];
solutionFields.forEach((fieldKey) => {
solutionFields.forEach(fieldKey => {
let solution = null;
if (values.solution_items && values.solution_items[fieldKey]) {
@@ -92,16 +85,9 @@ const AddBrandDevice = () => {
if (solutionType === 'text') {
isValid = solution.text && solution.text.trim() !== '';
} else if (solutionType === 'file') {
const hasPathSolution =
solution.path_solution && solution.path_solution.trim() !== '';
const hasFileUpload =
solution.fileUpload &&
typeof solution.fileUpload === 'object' &&
Object.keys(solution.fileUpload).length > 0;
const hasFile =
solution.file &&
typeof solution.file === 'object' &&
Object.keys(solution.file).length > 0;
const hasPathSolution = solution.path_solution && solution.path_solution.trim() !== '';
const hasFileUpload = (solution.fileUpload && typeof solution.fileUpload === 'object' && Object.keys(solution.fileUpload).length > 0);
const hasFile = (solution.file && typeof solution.file === 'object' && Object.keys(solution.file).length > 0);
isValid = hasPathSolution || hasFileUpload || hasFile;
}
@@ -132,9 +118,9 @@ const AddBrandDevice = () => {
text: '',
status: true,
file: null,
fileUpload: null,
},
},
fileUpload: null
}
}
});
}, 100);
}
@@ -142,6 +128,7 @@ const AddBrandDevice = () => {
};
const setSolutionsForExistingRecord = (solutions, targetForm) => {
if (!targetForm || !solutions || solutions.length === 0) {
return;
}
@@ -166,14 +153,11 @@ const AddBrandDevice = () => {
fileObject = {
uploadPath: solution.path_solution || solution.path_document,
path_solution: solution.path_solution || solution.path_document,
name:
solution.file_upload_name ||
(solution.path_solution || solution.path_document).split('/').pop() ||
'File',
name: solution.file_upload_name || (solution.path_solution || solution.path_document).split('/').pop() || 'File',
type_solution: solution.type_solution,
isExisting: true,
size: 0,
url: solution.path_solution || solution.path_document,
url: solution.path_solution || solution.path_document
};
}
@@ -186,7 +170,7 @@ const AddBrandDevice = () => {
file: fileObject,
fileUpload: fileObject,
path_solution: solution.path_solution || solution.path_document || null,
fileName: solution.file_upload_name || null,
fileName: solution.file_upload_name || null
};
});
@@ -196,35 +180,28 @@ const AddBrandDevice = () => {
setSolutionStatuses(newSolutionStatuses);
targetForm.resetFields();
setTimeout(() => {
targetForm.setFieldsValue({
solution_items: solutionItems,
solution_items: solutionItems
});
setTimeout(() => {
Object.keys(solutionItems).forEach((key) => {
Object.keys(solutionItems).forEach(key => {
const solution = solutionItems[key];
targetForm.setFieldValue(['solution_items', key, 'name'], solution.name);
targetForm.setFieldValue(['solution_items', key, 'type'], solution.type);
targetForm.setFieldValue(['solution_items', key, 'text'], solution.text);
targetForm.setFieldValue(['solution_items', key, 'file'], solution.file);
targetForm.setFieldValue(
['solution_items', key, 'fileUpload'],
solution.fileUpload
);
targetForm.setFieldValue(['solution_items', key, 'fileUpload'], solution.fileUpload);
targetForm.setFieldValue(['solution_items', key, 'status'], solution.status);
targetForm.setFieldValue(
['solution_items', key, 'path_solution'],
solution.path_solution
);
targetForm.setFieldValue(
['solution_items', key, 'fileName'],
solution.fileName
);
targetForm.setFieldValue(['solution_items', key, 'path_solution'], solution.path_solution);
targetForm.setFieldValue(['solution_items', key, 'fileName'], solution.fileName);
});
const finalValues = targetForm.getFieldsValue();
}, 100);
}, 100);
@@ -232,14 +209,14 @@ const AddBrandDevice = () => {
const handleAddSolutionField = () => {
const newKey = Math.max(...solutionFields, 0) + 1;
setSolutionFields((prev) => [...prev, newKey]);
setSolutionTypes((prev) => ({ ...prev, [newKey]: 'text' }));
setSolutionStatuses((prev) => ({ ...prev, [newKey]: true }));
setSolutionFields(prev => [...prev, newKey]);
setSolutionTypes(prev => ({ ...prev, [newKey]: 'text' }));
setSolutionStatuses(prev => ({ ...prev, [newKey]: true }));
};
const handleRemoveSolutionField = (fieldKey) => {
if (solutionFields.length > 1) {
setSolutionFields((prev) => prev.filter((key) => key !== fieldKey));
setSolutionFields(prev => prev.filter(key => key !== fieldKey));
const newTypes = { ...solutionTypes };
const newStatuses = { ...solutionStatuses };
delete newTypes[fieldKey];
@@ -256,7 +233,7 @@ const AddBrandDevice = () => {
};
const handleSolutionTypeChange = (fieldKey, type) => {
setSolutionTypes((prev) => ({ ...prev, [fieldKey]: type }));
setSolutionTypes(prev => ({ ...prev, [fieldKey]: type }));
if (type === 'file') {
solutionForm.setFieldValue(['solution_items', fieldKey, 'text'], '');
@@ -269,7 +246,7 @@ const AddBrandDevice = () => {
};
const handleSolutionStatusChange = (fieldKey, status) => {
setSolutionStatuses((prev) => ({ ...prev, [fieldKey]: status }));
setSolutionStatuses(prev => ({ ...prev, [fieldKey]: status }));
};
const handleNextStep = async () => {
@@ -282,7 +259,7 @@ const AddBrandDevice = () => {
brand_type: brandValues.brand_type || '',
brand_manufacture: brandValues.brand_manufacture || '',
brand_model: brandValues.brand_model || '',
is_active: brandValues.is_active !== undefined ? brandValues.is_active : true,
is_active: brandValues.is_active !== undefined ? brandValues.is_active : true
};
const response = await createBrand(brandApiData);
@@ -291,7 +268,7 @@ const AddBrandDevice = () => {
const newBrandInfo = {
...brandValues,
brand_id: response.data.brand_id,
brand_code: response.data.brand_code,
brand_code: response.data.brand_code
};
setBrandInfo(newBrandInfo);
setTemporaryBrandId(response.data.brand_id);
@@ -330,7 +307,8 @@ const AddBrandDevice = () => {
if (isTemporaryBrand && temporaryBrandId) {
try {
await deleteBrand(temporaryBrandId);
} catch (error) {}
} catch (error) {
}
}
navigate('/master/brand-device');
};
@@ -382,6 +360,8 @@ const AddBrandDevice = () => {
setTrigerFilter((prev) => !prev);
};
const resetErrorCodeForm = () => {
errorCodeForm.resetFields();
errorCodeForm.setFieldsValue({
@@ -411,16 +391,16 @@ const AddBrandDevice = () => {
return;
}
// if (!solutionData || solutionData.length === 0) {
// NotifAlert({
// icon: 'warning',
// title: 'Perhatian',
// message: 'Setiap error code harus memiliki minimal 1 solution!',
// });
// return;
// }
if (!solutionData || solutionData.length === 0) {
NotifAlert({
icon: 'warning',
title: 'Perhatian',
message: 'Setiap error code harus memiliki minimal 1 solution!',
});
return;
}
const formattedSolutions = solutionData.map((solution) => {
const formattedSolutions = solutionData.map(solution => {
const solutionType = solution.type || 'text';
let typeSolution = solutionType === 'text' ? 'text' : 'image';
@@ -442,11 +422,7 @@ const AddBrandDevice = () => {
} else {
formattedSolution.text_solution = '';
formattedSolution.path_solution =
solution.path_solution ||
solution.file?.uploadPath ||
solution.fileUpload?.uploadPath ||
'';
formattedSolution.path_solution = solution.path_solution || solution.file?.uploadPath || solution.fileUpload?.uploadPath || '';
}
if (formattedSolution.brand_code_solution_id) {
@@ -464,7 +440,7 @@ const AddBrandDevice = () => {
path_icon: errorCodeIcon?.uploadPath || '',
is_active: errorCodeValues.status === undefined ? true : errorCodeValues.status,
solution: formattedSolutions,
spareparts: selectedSparepartIds || [],
spareparts: selectedSparepartIds || []
};
let response;
@@ -480,13 +456,11 @@ const AddBrandDevice = () => {
NotifOk({
icon: 'success',
title: 'Berhasil',
message: editingErrorCodeKey
? 'Error code berhasil diupdate!'
: 'Error code berhasil ditambahkan!',
message: editingErrorCodeKey ? 'Error code berhasil diupdate!' : 'Error code berhasil ditambahkan!',
});
resetErrorCodeForm();
setTrigerFilter((prev) => !prev);
setTrigerFilter(prev => !prev);
} else {
NotifAlert({
icon: 'error',
@@ -505,10 +479,12 @@ const AddBrandDevice = () => {
}
};
const handleErrorCodeIconRemove = () => {
setErrorCodeIcon(null);
};
const handleFinish = async () => {
setConfirmLoading(true);
try {
@@ -530,10 +506,10 @@ const AddBrandDevice = () => {
const response = await getErrorCodesByBrandId(brandInfo.brand_id, queryParams);
if (response && response.statusCode === 200 && response.data) {
const freshErrorCodes = response.data.map((ec) => ({
const freshErrorCodes = response.data.map(ec => ({
...ec,
tempId: `existing_${ec.error_code_id}`,
status: 'existing',
status: 'existing'
}));
setApiErrorCodes(freshErrorCodes);
@@ -541,8 +517,7 @@ const AddBrandDevice = () => {
NotifAlert({
icon: 'warning',
title: 'Perhatian',
message:
'Harap tambahkan minimal 1 error code sebelum menyelesaikan.',
message: 'Harap tambahkan minimal 1 error code sebelum menyelesaikan.',
});
return;
}
@@ -551,8 +526,7 @@ const AddBrandDevice = () => {
NotifAlert({
icon: 'warning',
title: 'Perhatian',
message:
'Harap tambahkan minimal 1 error code sebelum menyelesaikan.',
message: 'Harap tambahkan minimal 1 error code sebelum menyelesaikan.',
});
return;
}
@@ -617,7 +591,11 @@ const AddBrandDevice = () => {
<Spin size="large" />
</div>
)}
<BrandForm form={brandForm} isEdit={false} brandInfo={brandInfo} />
<BrandForm
form={brandForm}
isEdit={false}
brandInfo={brandInfo}
/>
</div>
);
}
@@ -657,39 +635,31 @@ const AddBrandDevice = () => {
</Col>
<Col xs={24} md={16} lg={16}>
<div
style={{
paddingLeft: '12px',
}}
>
<div style={{
paddingLeft: '12px'
}}>
<Card
title={
<div
style={{
<div style={{
display: 'flex',
alignItems: 'center',
justifyContent: 'space-between',
width: '100%'
}}>
<span style={{
fontSize: '16px',
fontWeight: '600',
color: '#262626',
display: 'flex',
alignItems: 'center',
justifyContent: 'space-between',
width: '100%',
}}
>
<span
style={{
fontSize: '16px',
fontWeight: '600',
color: '#262626',
display: 'flex',
alignItems: 'center',
gap: '8px',
}}
>
<span
style={{
width: '4px',
height: '20px',
backgroundColor: '#23A55A',
borderRadius: '2px',
}}
></span>
gap: '8px'
}}>
<span style={{
width: '4px',
height: '20px',
backgroundColor: '#23A55A',
borderRadius: '2px'
}}></span>
Error Code Form
</span>
<Button
@@ -705,51 +675,43 @@ const AddBrandDevice = () => {
padding: '0 24px',
fontWeight: '500',
boxShadow: '0 2px 4px rgba(35, 165, 90, 0.2)',
transition: 'all 0.3s ease',
transition: 'all 0.3s ease'
}}
onMouseEnter={(e) => {
e.target.style.boxShadow =
'0 4px 8px rgba(35, 165, 90, 0.3)';
e.target.style.boxShadow = '0 4px 8px rgba(35, 165, 90, 0.3)';
}}
onMouseLeave={(e) => {
e.target.style.boxShadow =
'0 2px 4px rgba(35, 165, 90, 0.2)';
e.target.style.boxShadow = '0 2px 4px rgba(35, 165, 90, 0.2)';
}}
>
{editingErrorCodeKey
? 'Update Error Code'
: 'Save Error Code'}
{editingErrorCodeKey ? 'Update Error Code' : 'Save Error Code'}
</Button>
</div>
}
style={{
width: '100%',
boxShadow: '0 2px 8px rgba(0,0,0,0.06)',
borderRadius: '12px',
borderRadius: '12px'
}}
styles={{
body: { padding: '16px 24px 12px 24px' },
header: {
padding: '16px 24px',
borderBottom: '1px solid #f0f0f0',
backgroundColor: '#fafafa',
},
backgroundColor: '#fafafa'
}
}}
>
<div
style={{ display: 'flex', flexDirection: 'column', gap: '8px' }}
>
<div
style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
marginBottom: '0',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)',
}}
>
<div style={{ display: 'flex', flexDirection: 'column', gap: '8px' }}>
<div style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
marginBottom: '0',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)'
}}>
<ErrorCodeForm
errorCodeForm={errorCodeForm}
isErrorCodeFormReadOnly={isErrorCodeFormReadOnly}
@@ -762,42 +724,29 @@ const AddBrandDevice = () => {
<Row gutter={[20, 0]} style={{ marginTop: '0' }}>
<Col xs={24} md={12} lg={12}>
<div
style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)',
}}
>
<div
style={{
display: 'flex',
alignItems: 'center',
gap: '8px',
marginBottom: '12px',
paddingBottom: '8px',
borderBottom: '1px solid #f5f5f5',
}}
>
<div
style={{
width: '3px',
height: '16px',
backgroundColor: '#1890ff',
borderRadius: '2px',
}}
></div>
<h4
style={{
margin: 0,
color: '#262626',
fontSize: '14px',
fontWeight: '600',
}}
>
<div style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)'
}}>
<div style={{
display: 'flex',
alignItems: 'center',
gap: '8px',
marginBottom: '12px',
paddingBottom: '8px',
borderBottom: '1px solid #f5f5f5'
}}>
<div style={{
width: '3px',
height: '16px',
backgroundColor: '#1890ff',
borderRadius: '2px'
}}></div>
<h4 style={{ margin: 0, color: '#262626', fontSize: '14px', fontWeight: '600' }}>
Solution
</h4>
</div>
@@ -807,23 +756,14 @@ const AddBrandDevice = () => {
solutionTypes={solutionTypes}
solutionStatuses={solutionStatuses}
onAddSolutionField={handleAddSolutionField}
onRemoveSolutionField={
handleRemoveSolutionField
}
onRemoveSolutionField={handleRemoveSolutionField}
onSolutionTypeChange={handleSolutionTypeChange}
onSolutionStatusChange={
handleSolutionStatusChange
}
onSolutionFileUpload={(fileData) => {}}
onSolutionStatusChange={handleSolutionStatusChange}
onSolutionFileUpload={(fileData) => {
}}
onFileView={(fileData) => {
if (
fileData &&
(fileData.url || fileData.uploadPath)
) {
window.open(
fileData.url || fileData.uploadPath,
'_blank'
);
if (fileData && (fileData.url || fileData.uploadPath)) {
window.open(fileData.url || fileData.uploadPath, '_blank');
}
}}
isReadOnly={false}
@@ -832,55 +772,40 @@ const AddBrandDevice = () => {
</div>
</Col>
<Col xs={24} md={12} lg={12}>
<div
style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)',
}}
>
<div
style={{
display: 'flex',
alignItems: 'center',
gap: '8px',
marginBottom: '12px',
paddingBottom: '8px',
borderBottom: '1px solid #f5f5f5',
}}
>
<div
style={{
width: '3px',
height: '16px',
backgroundColor: '#faad14',
borderRadius: '2px',
}}
></div>
<h4
style={{
margin: 0,
color: '#262626',
fontSize: '14px',
fontWeight: '600',
}}
>
<div style={{
padding: '16px',
border: '1px solid #f0f0f0',
borderRadius: '10px',
backgroundColor: '#ffffff',
transition: 'all 0.3s ease',
boxShadow: '0 1px 3px rgba(0,0,0,0.04)'
}}>
<div style={{
display: 'flex',
alignItems: 'center',
gap: '8px',
marginBottom: '12px',
paddingBottom: '8px',
borderBottom: '1px solid #f5f5f5'
}}>
<div style={{
width: '3px',
height: '16px',
backgroundColor: '#faad14',
borderRadius: '2px'
}}></div>
<h4 style={{ margin: 0, color: '#262626', fontSize: '14px', fontWeight: '600' }}>
Sparepart Selection
</h4>
</div>
<div
style={{
maxHeight: '45vh',
overflow: 'auto',
border: '1px solid #e8e8e8',
borderRadius: '8px',
padding: '12px',
backgroundColor: '#fafafa',
}}
>
<div style={{
maxHeight: '45vh',
overflow: 'auto',
border: '1px solid #e8e8e8',
borderRadius: '8px',
padding: '12px',
backgroundColor: '#fafafa'
}}>
<SparepartSelect
selectedSparepartIds={selectedSparepartIds}
onSparepartChange={setSelectedSparepartIds}
@@ -891,16 +816,15 @@ const AddBrandDevice = () => {
</Col>
</Row>
<div
style={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
padding: '16px 0 0 0',
borderTop: '1px solid #f0f0f0',
marginTop: '12px',
}}
>
<div style={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
padding: '16px 0 0 0',
borderTop: '1px solid #f0f0f0',
marginTop: '12px'
}}>
{editingErrorCodeKey && (
<Button
size="large"
@@ -913,7 +837,7 @@ const AddBrandDevice = () => {
height: '40px',
padding: '0 24px',
fontWeight: '500',
transition: 'all 0.3s ease',
transition: 'all 0.3s ease'
}}
onMouseEnter={(e) => {
e.target.style.borderColor = '#ff4d4f';
@@ -947,7 +871,7 @@ const AddBrandDevice = () => {
setBreadcrumbItems([
{
title: <span style={{ fontSize: '14px', fontWeight: 'bold' }}> Master</span>,
title: <span style={{ fontSize: '14px', fontWeight: 'bold' }}> Master</span>
},
{
title: (
@@ -971,11 +895,12 @@ const AddBrandDevice = () => {
if (location.state?.fromFileViewer && location.state.phase !== undefined) {
setCurrentStep(location.state.phase);
}
}, [setBreadcrumbItems, navigate, searchParams, location.state]);
useEffect(() => {
if (brandInfo.brand_id && currentStep === 1) {
setTrigerFilter((prev) => !prev);
setTrigerFilter(prev => !prev);
}
}, [brandInfo.brand_id, currentStep]);
@@ -988,7 +913,8 @@ const AddBrandDevice = () => {
const errorCodes = response.data || [];
setApiErrorCodes(errorCodes);
}
} catch (error) {}
} catch (error) {
}
}
};
fetchErrorCodes();
@@ -999,7 +925,8 @@ const AddBrandDevice = () => {
if (isTemporaryBrand && temporaryBrandId && currentStep === 0) {
try {
await deleteBrand(temporaryBrandId);
} catch (error) {}
} catch (error) {
}
}
};
@@ -1010,6 +937,7 @@ const AddBrandDevice = () => {
};
}, [isTemporaryBrand, temporaryBrandId, currentStep]);
return (
<ConfigProvider
theme={{
@@ -1060,9 +988,14 @@ const AddBrandDevice = () => {
<Divider />
<div style={{ display: 'flex', justifyContent: 'space-between' }}>
<div>
<Button onClick={handleCancel}>Cancel</Button>
<Button onClick={handleCancel}>
Cancel
</Button>
{currentStep === 1 && (
<Button onClick={handlePrevStep} style={{ marginLeft: 8 }}>
<Button
onClick={handlePrevStep}
style={{ marginLeft: 8 }}
>
Kembali ke Brand Info
</Button>
)}

View File

@@ -479,14 +479,14 @@ const EditBrandDevice = () => {
return;
}
// if (!solutionData || solutionData.length === 0) {
// NotifAlert({
// icon: 'warning',
// title: 'Perhatian',
// message: 'Setiap error code harus memiliki minimal 1 solution!',
// });
// return;
// }
if (!solutionData || solutionData.length === 0) {
NotifAlert({
icon: 'warning',
title: 'Perhatian',
message: 'Setiap error code harus memiliki minimal 1 solution!',
});
return;
}
const formattedSolutions = solutionData.map(solution => {
const solutionType = solution.type || 'text';

View File

@@ -1,12 +1,6 @@
import React, { useState, useEffect, useMemo } from 'react';
import { Card, Input, Button, Row, Col, Empty } from 'antd';
import {
PlusOutlined,
SearchOutlined,
DeleteOutlined,
LeftOutlined,
RightOutlined,
} from '@ant-design/icons';
import { PlusOutlined, SearchOutlined, DeleteOutlined, LeftOutlined, RightOutlined } from '@ant-design/icons';
import { getErrorCodesByBrandId, deleteErrorCode } from '../../../../api/master-brand';
import { NotifAlert, NotifOk, NotifConfirmDialog } from '../../../../components/Global/ToastNotif';
@@ -22,7 +16,7 @@ const ListErrorCode = ({
onSearch,
onSearchClear,
isReadOnly = false,
errorCodes: propErrorCodes = null,
errorCodes: propErrorCodes = null
}) => {
const [errorCodes, setErrorCodes] = useState([]);
const [loading, setLoading] = useState(false);
@@ -58,12 +52,12 @@ const ListErrorCode = ({
if (response && response.statusCode === 200) {
const apiErrorData = response.data || [];
const allErrorCodes = [
...apiErrorData.map((ec) => ({
...apiErrorData.map(ec => ({
...ec,
tempId: `existing_${ec.error_code_id}`,
status: 'existing',
status: 'existing'
})),
...tempErrorCodes.filter((ec) => ec.status !== 'deleted'),
...tempErrorCodes.filter(ec => ec.status !== 'deleted')
];
setErrorCodes(allErrorCodes);
@@ -88,9 +82,11 @@ const ListErrorCode = ({
useEffect(() => {
if (isReadOnly && propErrorCodes) {
setErrorCodes(propErrorCodes);
setLoading(false);
} else {
fetchErrorCodes();
}
}, [brandId, queryParams, tempErrorCodes, trigerFilter, isReadOnly, propErrorCodes]);
@@ -130,19 +126,20 @@ const ListErrorCode = ({
title: 'Hapus Error Code',
message: `Apakah Anda yakin ingin menghapus error code ${item.error_code}?`,
onConfirm: () => performDelete(item),
onCancel: () => {},
confirmButtonText: 'Hapus',
onCancel: () => { },
confirmButtonText: 'Hapus'
});
}
};
const performDelete = async (item) => {
try {
if (!item.error_code_id || item.error_code_id === 'undefined') {
NotifAlert({
icon: 'error',
title: 'Error',
message: 'Error code ID tidak valid',
message: 'Error code ID tidak valid'
});
return;
}
@@ -151,7 +148,7 @@ const ListErrorCode = ({
NotifAlert({
icon: 'error',
title: 'Error',
message: 'Brand ID tidak valid',
message: 'Brand ID tidak valid'
});
return;
}
@@ -162,21 +159,21 @@ const ListErrorCode = ({
NotifOk({
icon: 'success',
title: 'Berhasil',
message: 'Error code berhasil dihapus',
message: 'Error code berhasil dihapus'
});
fetchErrorCodes();
} else {
NotifAlert({
icon: 'error',
title: 'Gagal',
message: 'Gagal menghapus error code',
message: 'Gagal menghapus error code'
});
}
} catch (error) {
NotifAlert({
icon: 'error',
title: 'Error',
message: 'Terjadi kesalahan saat menghapus error code',
message: 'Terjadi kesalahan saat menghapus error code'
});
}
};
@@ -184,8 +181,8 @@ const ListErrorCode = ({
return (
<Card
title="Daftar Error Code"
style={{ width: '100%', minWidth: '300px' }}
bodyStyle={{ padding: '12px' }}
style={{ width: '100%', minWidth: '472px' }}
styles={{ body: { padding: '12px' } }}
>
<Input.Search
placeholder="Cari error code..."
@@ -206,7 +203,7 @@ const ListErrorCode = ({
style={{
backgroundColor: '#23A55A',
borderColor: '#23A55A',
height: '32px',
height: '32px'
}}
>
Search
@@ -220,18 +217,19 @@ const ListErrorCode = ({
}}
/>
<div
style={{
height: '90vh',
border: '1px solid #d9d9d9',
borderRadius: '6px',
overflow: 'auto',
marginBottom: 12,
backgroundColor: '#fafafa',
}}
>
<div style={{
height: '90vh',
border: '1px solid #d9d9d9',
borderRadius: '6px',
overflow: 'auto',
marginBottom: 12,
backgroundColor: '#fafafa'
}}>
{errorCodes.length === 0 ? (
<Empty description="Belum ada error code" style={{ marginTop: 50 }} />
<Empty
description="Belum ada error code"
style={{ marginTop: 50 }}
/>
) : (
<div style={{ padding: '8px' }}>
{errorCodes.map((item) => (
@@ -242,25 +240,13 @@ const ListErrorCode = ({
padding: '8px 12px',
borderRadius: '6px',
marginBottom: '4px',
border:
selectedErrorCode?.tempId === item.tempId
? '2px solid #23A55A'
: '1px solid #d9d9d9',
backgroundColor:
selectedErrorCode?.tempId === item.tempId
? '#f6ffed'
: '#fff',
transition: 'all 0.2s ease',
border: selectedErrorCode?.tempId === item.tempId ? '2px solid #23A55A' : '1px solid #d9d9d9',
backgroundColor: selectedErrorCode?.tempId === item.tempId ? '#f6ffed' : '#fff',
transition: 'all 0.2s ease'
}}
onClick={() => onErrorCodeSelect(item)}
>
<div
style={{
display: 'flex',
justifyContent: 'space-between',
alignItems: 'center',
}}
>
<div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center' }}>
<div style={{ flex: 1 }}>
<div style={{ fontWeight: 'bold', fontSize: '12px' }}>
{item.error_code}
@@ -280,7 +266,7 @@ const ListErrorCode = ({
padding: '2px 6px',
height: '24px',
fontSize: '11px',
border: '1px solid #ff4d4f',
border: '1px solid #ff4d4f'
}}
/>
)}
@@ -306,15 +292,9 @@ const ListErrorCode = ({
onClick={handlePrevious}
disabled={pagination.current_page <= 1}
size="small"
></Button>
<span
style={{
fontSize: '12px',
color: '#666',
minWidth: '60px',
textAlign: 'center',
}}
>
</Button>
<span style={{ fontSize: '12px', color: '#666', minWidth: '60px', textAlign: 'center' }}>
{pagination.current_page} / {pagination.total_page}
</span>
<Button
@@ -322,7 +302,8 @@ const ListErrorCode = ({
onClick={handleNext}
disabled={pagination.current_page >= pagination.total_page}
size="small"
></Button>
>
</Button>
</div>
</Col>
</Row>

View File

@@ -1,22 +1,9 @@
import React, { useEffect, useState } from 'react';
import {
Modal,
Input,
Divider,
Typography,
Switch,
Button,
ConfigProvider,
Select,
DatePicker,
} from 'antd';
import { NotifAlert, NotifOk, NotifSmall } from '../../../../components/Global/ToastNotif';
import { Modal, Input, Divider, Typography, Switch, Button, ConfigProvider, Select } from 'antd';
import { NotifAlert, NotifOk } from '../../../../components/Global/ToastNotif';
import { createDevice, updateDevice } from '../../../../api/master-device';
import { reminderMonthly, reminderCustom } from '../../../../api/notification';
import { getAllBrands } from '../../../../api/master-brand';
import { validateRun } from '../../../../Utils/validate';
import { toApiDateFormatter } from '../../../../components/Global/Formatter';
import dayjs from 'dayjs';
const { Text } = Typography;
const { TextArea } = Input;
@@ -36,12 +23,7 @@ const DetailDevice = (props) => {
device_location: '',
device_description: '',
ip_address: '',
listen_channel: null,
reminder_at: null,
reminder_at_monthly: null,
start_date: null,
end_date: null,
period: null,
listen_channel: '',
};
const [formData, setFormData] = useState(defaultData);
@@ -85,26 +67,12 @@ const DetailDevice = (props) => {
ip_address: formData.ip_address,
brand_id: formData.brand_id,
listen_channel: formData.listen_channel,
listen_channel_reminder: formData.listen_channel_reminder,
reminder_at: formData.reminder_at,
reminder_at_monthly: formData.period !== 'custom' ? formData.reminder_at_monthly : null,
start_date: formData.start_date,
end_date: formData.end_date,
};
console.log(payload);
const response = formData.device_id
? await updateDevice(formData.device_id, payload)
: await createDevice(payload);
const response2 = formData.period !== 'custom'
? await updateDevice(formData.device_id, { reminder_at_monthly: formData.reminder_at_monthly,})
: await updateDevice(formData.device_id, {
start_date: formData.start_date,
end_date: formData.end_date,
});
// Check if response is successful
if (response && (response.statusCode === 200 || response.statusCode === 201)) {
const deviceName = response.data?.device_name || formData.device_name;
@@ -125,25 +93,6 @@ const DetailDevice = (props) => {
message: response?.message || 'Terjadi kesalahan saat menyimpan data.',
});
}
// Check if response Reminder At(Monthly) or Period are successful
const tipe = formData.period !== 'custom' ? 'Reminder At(Monthly)' : 'Period';
if (response2 && (response2.statusCode === 200 || response2.statusCode === 201)) {
NotifSmall({
icon: 'success',
title: 'Berhasil',
message: `${tipe} berhasil disimpan`,
});
} else {
NotifSmall({
icon: 'error',
title: 'Gagal',
message:
response?.message ||
`Terjadi kesalahan saat menyimpan ${tipe}`,
});
}
} catch (error) {
console.error('Save Device Error:', error);
NotifAlert({
@@ -179,13 +128,6 @@ const DetailDevice = (props) => {
});
};
const handleDateChange = (field, value) => {
setFormData({
...formData,
[field]: value,
});
};
// Fungsi untuk mengambil daftar brand
const fetchBrands = async () => {
setLoadingBrands(true);
@@ -206,56 +148,6 @@ const DetailDevice = (props) => {
}
};
useEffect(() => {
if (formData.start_date && formData.end_date) {
const start = dayjs(formData.start_date);
const end = dayjs(formData.end_date);
let periodValue = 'custom';
if (end.isSame(start.add(1, 'month').subtract(1, 'day'), 'day')) {
periodValue = '1';
} else if (end.isSame(start.add(3, 'month').subtract(1, 'day'), 'day')) {
periodValue = '3';
} else if (end.isSame(start.add(6, 'month').subtract(1, 'day'), 'day')) {
periodValue = '6';
}
setFormData((prev) => ({
...prev,
period: periodValue,
}));
}
}, [formData.start_date, formData.end_date]);
const handleMonthly = (field, value) => {
setFormData((prev) => {
const data = {
...prev,
[field]: value,
};
if (value !== 'custom') {
const months = Number(value);
const startDate = dayjs().startOf('day');
const endDate = startDate
.add(months, 'month')
.subtract(1, 'day')
.endOf('day');
data.start_date = startDate.toISOString();
data.end_date = endDate.toISOString();
data.reminder_at_monthly = null;
} else {
data.start_date = null;
data.end_date = null;
}
return data;
});
};
useEffect(() => {
if (props.showModal && (props.actionMode === 'add' || props.actionMode === 'edit')) {
fetchBrands();
@@ -277,8 +169,8 @@ const DetailDevice = (props) => {
props.actionMode === 'add'
? 'Tambah'
: props.actionMode === 'preview'
? 'Preview'
: 'Edit'
? 'Preview'
: 'Edit'
} Device`}
open={props.showModal}
// open={true}
@@ -326,10 +218,9 @@ const DetailDevice = (props) => {
</React.Fragment>,
]}
>
<Divider />
{formData && (
<div>
<div style={{ marginBottom: 12 }}>
<div>
<div>
<Text strong>Device Status</Text>
</div>
@@ -356,7 +247,7 @@ const DetailDevice = (props) => {
</div>
</div>
</div>
{/* <Divider style={{ margin: '12px 0' }} /> */}
<Divider style={{ margin: '12px 0' }} />
<div hidden>
<Text strong>Device ID</Text>
<Input
@@ -439,149 +330,15 @@ const DetailDevice = (props) => {
readOnly={props.readOnly}
/>
</div>
<div style={{ marginBottom: 12 }}></div>
<div style={{ marginBottom: 12 }}></div>
<div style={{ display: 'flex', gap: 16 }}>
<div style={{ flex: 1 }}>
{' '}
<Text strong>Channel Error</Text>
<Input
name="listen_channel"
value={formData.listen_channel}
onChange={handleInputChange}
placeholder="Enter Listen Channel"
readOnly={props.readOnly}
/>
</div>
<div style={{ flex: 1 }}>
<Text strong>Channel Reminder</Text>
<Input
name="listen_channel_reminder"
value={formData.listen_channel_reminder}
onChange={handleInputChange}
placeholder="Enter Listen Channel Reminder"
readOnly={props.readOnly}
/>
</div>
</div>
<div style={{ marginBottom: 12 }}>
<Text strong>Reminder At(Yearly)</Text>
<div style={{ display: 'flex', gap: 8, alignItems: 'center' }}>
<DatePicker
value={
formData.reminder_at
? dayjs(formData.reminder_at) // ✅ langsung parse ISO
: null
}
onChange={(date) =>
handleDateChange(
'reminder_at',
date ? date.toISOString() : null
)
}
format="DD-MM-YYYY HH:mm"
showTime={{ format: 'HH:mm' }}
style={{ flex: 1 }}
/>
<Button
danger
onClick={() =>
setFormData((prev) => ({
...prev,
reminder_at: null,
}))
}
>
Clear
</Button>
</div>
</div>
<div style={{ marginBottom: 12 }}>
<Text strong>Period</Text>
<Text style={{ color: 'red' }}> *</Text>
<Select
value={formData.period}
onChange={(value) => handleMonthly('period', value)}
placeholder="Select Period"
style={{ width: '100%' }}
>
<Select.Option value="1">1 Monthly</Select.Option>
<Select.Option value="3">3 Monthly</Select.Option>
<Select.Option value="6">6 Monthly</Select.Option>
<Select.Option value="custom">Custom</Select.Option>
</Select>
</div>
{formData.period === 'custom' && (
<div style={{ display: 'flex', gap: 8, marginBottom: 12 }}>
<DatePicker
placeholder="Start Date"
value={formData.start_date ? dayjs(formData.start_date) : null}
onChange={(date) =>
handleDateChange('start_date', date ? date.toISOString() : null)
}
disabledDate={(current) =>
formData.end_date &&
current &&
current.isAfter(dayjs(formData.end_date), 'day')
}
format="DD-MM-YYYY HH:mm"
showTime={{ format: 'HH:mm' }}
style={{ flex: 1 }}
/>
<DatePicker
placeholder="End Date"
value={formData.end_date ? dayjs(formData.end_date) : null}
onChange={(date) =>
handleDateChange('end_date', date ? date.toISOString() : null)
}
disabledDate={(current) =>
formData.start_date &&
current &&
current.isBefore(dayjs(formData.start_date), 'day')
}
format="DD-MM-YYYY HH:mm"
showTime={{ format: 'HH:mm' }}
style={{ flex: 1 }}
/>
</div>
)}
<div style={{ marginBottom: 12 }}>
<Text strong>Reminder At(Monthly)</Text>
<div style={{ display: 'flex', gap: 8, alignItems: 'center' }}>
<DatePicker
disabled={formData.period === 'custom'}
value={
formData.reminder_at_monthly
? dayjs(formData.reminder_at_monthly) // ✅ langsung parse ISO
: null
}
onChange={(date) =>
handleDateChange(
'reminder_at_monthly',
date ? date.toISOString() : null
)
}
format="DD-MM-YYYY HH:mm"
showTime={{ format: 'HH:mm' }}
style={{ flex: 1 }}
/>
<Button
disabled={formData.period === 'custom'}
danger
onClick={() =>
setFormData((prev) => ({
...prev,
reminder_at_monthly: null,
}))
}
>
Clear
</Button>
</div>
<Text strong>Listen Channel</Text>
<Input
name="listen_channel"
value={formData.listen_channel}
onChange={handleInputChange}
placeholder="Enter Listen Channel"
readOnly={props.readOnly}
/>
</div>
<div style={{ marginBottom: 12 }}>
<Text strong>Device Description</Text>

View File

@@ -11,7 +11,6 @@ import {
Row,
Col,
Image,
Checkbox,
} from 'antd';
import { PlusOutlined, EyeOutlined, DeleteOutlined } from '@ant-design/icons';
import { NotifAlert, NotifOk } from '../../../../components/Global/ToastNotif';
@@ -38,68 +37,9 @@ const DetailSparepart = (props) => {
const [previewTitle, setPreviewTitle] = useState('');
const [isHovering, setIsHovering] = useState(false);
const optionsMonthly = [
{
key: 1,
value: 1,
text: '1 Month',
},
{
key: 3,
value: 3,
text: '3 Month',
},
{
key: 6,
value: 6,
text: '6 Month',
},
];
const optionsYearly = [
{
key: 1,
value: 1,
text: '1 Year',
},
{
key: 2,
value: 2,
text: '2 Year',
},
{
key: 3,
value: 3,
text: '3 Year',
},
{
key: 4,
value: 4,
text: '4 Year',
},
{
key: 5,
value: 5,
text: '5 Year',
},
{
key: 6,
value: 6,
text: '6 Year',
},
];
const [checkedListM, setCheckedListM] = useState([]);
const [checkAllM, setCheckAllM] = useState(false);
const [indeterminateM, setIndeterminateM] = useState(false);
const [checkedList, setCheckedList] = useState([]);
const [checkAll, setCheckAll] = useState(false);
const [indeterminate, setIndeterminate] = useState(false);
const defaultData = {
sparepart_id: '',
sparepart_name: '',
sparepart_number: '',
sparepart_description: '',
sparepart_model: '',
sparepart_item_type: null,
@@ -296,10 +236,6 @@ const DetailSparepart = (props) => {
payload.sparepart_foto = imageUrl;
}
payload.sparepart_number = formData.sparepart_number;
payload.sparepart_yearly = checkedList;
payload.sparepart_monthly = checkedListM;
// console.log('Sending payload:', payload);
const response = formData.sparepart_id
@@ -346,36 +282,6 @@ const DetailSparepart = (props) => {
setFormData({ ...formData, [name]: value });
};
const onChangeCheckboxM = (list) => {
setCheckedListM(list);
setIndeterminateM(!!list.length && list.length < optionsMonthly.length);
setCheckAllM(list.length === optionsMonthly.length);
};
const onCheckAllChangeM = (e) => {
const checked = e.target.checked;
setCheckedListM(checked ? optionsMonthly.map((item) => item.value) : []);
setIndeterminateM(false);
setCheckAllM(checked);
};
const onChangeCheckbox = (list) => {
setCheckedList(list);
setIndeterminate(!!list.length && list.length < optionsYearly.length);
setCheckAll(list.length === optionsYearly.length);
};
const onCheckAllChange = (e) => {
const checked = e.target.checked;
setCheckedList(checked ? optionsYearly.map((item) => item.value) : []);
setIndeterminate(false);
setCheckAll(checked);
};
useEffect(() => {
if (props.selectedData) {
setFormData(props.selectedData);
@@ -412,19 +318,9 @@ const DetailSparepart = (props) => {
} else {
setFileList([]);
}
setCheckedListM(JSON.parse(props.selectedData.sparepart_monthly));
setCheckedList(JSON.parse(props.selectedData.sparepart_yearly));
} else {
setFormData(defaultData);
setFileList([]);
setIndeterminateM(false);
setCheckedListM([]);
setCheckAllM(false);
setIndeterminate(false);
setCheckedList([]);
setCheckAll(false);
}
}, [props.showModal, props.selectedData, props.actionMode]);
@@ -437,13 +333,12 @@ const DetailSparepart = (props) => {
return (
<Modal
width="40rem"
title={`${
props.actionMode === 'add'
? 'Tambah'
: props.actionMode === 'preview'
? 'Preview'
: 'Edit'
? 'Preview'
: 'Edit'
} Sparepart`}
open={props.showModal}
onCancel={handleCancel}
@@ -568,7 +463,7 @@ const DetailSparepart = (props) => {
<div
style={{
width: '180px', // Fixed width for square
height: '240px',
height: '180px',
border: '1px dashed #d9d9d9',
borderRadius: '8px',
display: 'flex',
@@ -590,17 +485,6 @@ const DetailSparepart = (props) => {
{/* Kolom untuk field lainnya */}
<Col span={14}>
<Row gutter={[16, 16]}>
<Col span={24}>
<Text strong>Part Number</Text>
<Text style={{ color: 'red' }}> *</Text>
<Input
name="sparepart_number"
value={formData.sparepart_number}
onChange={handleInputChange}
placeholder="Enter Sparepart Number"
readOnly={props.readOnly}
/>
</Col>
<Col span={24}>
<Text strong>Sparepart Name</Text>
<Text style={{ color: 'red' }}> *</Text>
@@ -676,78 +560,7 @@ const DetailSparepart = (props) => {
/>
</Col>
</Row>
<ConfigProvider
theme={{
token: {
colorPrimary: '#23A55A',
},
}}
>
{/* Yearly */}
<Row style={{ marginTop: 16 }}>
<Col>
<Checkbox
indeterminate={indeterminate}
onChange={onCheckAllChange}
checked={checkAll}
>
{checkAll ? 'Unselect All Years' : 'Select All Years'}
</Checkbox>
</Col>
</Row>
<Row style={{ marginTop: 10 }}>
<Col span={24}>
<Checkbox.Group
value={checkedList}
onChange={onChangeCheckbox}
style={{
width: '100%',
display: 'flex',
justifyContent: 'space-between',
}}
>
{optionsYearly.map((item) => (
<Checkbox key={item.key} value={item.value}>
{item.text}
</Checkbox>
))}
</Checkbox.Group>
</Col>
</Row>
{/* Monthly */}
<Row style={{ marginTop: 16 }}>
<Col>
<Checkbox
indeterminate={indeterminateM}
onChange={onCheckAllChangeM}
checked={checkAllM}
>
{checkAllM ? 'Unselect All Months' : 'Select All Months'}
</Checkbox>
</Col>
</Row>
<Row style={{ marginTop: 10 }}>
<Col span={24}>
<Checkbox.Group
value={checkedListM}
onChange={onChangeCheckboxM}
style={{
width: '100%',
display: 'flex',
justifyContent: 'space-between',
}}
>
{optionsMonthly.map((item) => (
<Checkbox key={item.key} value={item.value}>
{item.text}
</Checkbox>
))}
</Checkbox.Group>
</Col>
</Row>
</ConfigProvider>
<Row gutter={[16, 16]} style={{ marginTop: 16 }}>
<Col span={24}>
<Text strong>Description</Text>

View File

@@ -36,12 +36,6 @@ const columns = (showPreviewModal, showEditModal, showDeleteDialog) => [
key: 'sparepart_name',
width: '20%',
},
{
title: 'Sparepart Number',
dataIndex: 'sparepart_number',
key: 'sparepart_number',
width: '20%',
},
{
title: 'Description',
dataIndex: 'sparepart_description',
@@ -283,8 +277,8 @@ const ListSparepart = memo(function ListSparepart(props) {
onStockUpdate={doFilter}
onGetData={(data) => {
if(data && data.length > 0) {
// console.log('Sample sparepart data from API:', data[0]);
// console.log('Available fields:', Object.keys(data[0] || {}));
console.log('Sample sparepart data from API:', data[0]);
console.log('Available fields:', Object.keys(data[0] || {}));
}
}} // Log untuk debugging field-field yang tersedia
/>

View File

@@ -44,29 +44,16 @@ import {
getNotificationDetail,
resendChatByUser,
resendChatAllUser,
searchData,
} from '../../../api/notification';
import { onNotifUpdate } from '../../../components/Global/MqttConnection';
const { Text, Paragraph, Link: AntdLink } = Typography;
const OpenMail = ({ size = 22, color = 'black' }) => (
<svg
xmlns="http://www.w3.org/2000/svg"
viewBox="0 0 640 640"
width={size}
height={size}
fill={color}
>
<path d="M576 480C576 515.3 547.5 544 512.1 544L128 544C92.6 544 64 515.3 64 480L64 228C64.1 212.5 71.8 198 84.5 189.2L270 61.3C300.1 40.6 339.8 40.6 369.9 61.3L555.5 189.2C568.3 198 575.9 212.5 576 228L576 480zM128 496L512.1 496C520.9 496 528 488.9 528 480L528 288.3L373.2 405.7C341.8 429.6 298.3 429.6 266.8 405.7L112 288.3L112 480C112 488.9 119.2 496 128 496zM527.6 228.4L342.7 100.8C329 91.4 311 91.4 297.3 100.8L112.4 228.4L295.8 367.5C310.1 378.3 329.9 378.3 344.2 367.5L527.6 228.4z" />
</svg>
);
// Transform API response to component format
const transformNotificationData = (apiData) => {
return apiData.map((item, index) => ({
id: `notification-${item.notification_error_id}-${index}`, // Unique key prefix with array index
type: item.is_read ? 'resolved' : item.is_delivered ? 'warning' : 'critical',
title: item.error_code_name || 'Unknown Error',
color: item.error_code_color || 'Black',
issue: item.error_code || item.error_code_name || 'Unknown Error',
description: `${item.error_code} - ${item.error_code_name || ''}`,
timestamp: item.created_at
@@ -102,7 +89,6 @@ const ListNotification = memo(function ListNotification(props) {
const [activeTab, setActiveTab] = useState('all');
const [searchTerm, setSearchTerm] = useState('');
const [searchValue, setSearchValue] = useState('');
const [notifTrigger, setNotifTrigger] = useState(0);
const [loading, setLoading] = useState(false);
const [modalContent, setModalContent] = useState(null); // 'user', 'log', 'details', or null
const [isAddingLog, setIsAddingLog] = useState(false);
@@ -180,12 +166,6 @@ const ListNotification = memo(function ListNotification(props) {
fetchNotifications(page, pageSize, isReadFilter);
};
useEffect(() => {
onNotifUpdate(() => {
setNotifTrigger((prev) => prev + 1);
});
}, []);
useEffect(() => {
const token = localStorage.getItem('token');
if (!token) {
@@ -196,18 +176,18 @@ const ListNotification = memo(function ListNotification(props) {
// Fetch notifications on component mount and when tab changes
const isReadFilter = activeTab === 'read' ? 1 : activeTab === 'unread' ? 0 : null;
fetchNotifications(pagination.current_page, pagination.current_limit, isReadFilter);
}, [activeTab, notifTrigger]);
}, [activeTab]);
const getIconAndColor = (type) => {
switch (type) {
case 'critical':
return { IconComponent: MailOutlined, color: '#faad14', bgColor: '#fff1f0' };
return { IconComponent: CloseCircleFilled, color: '#ff4d4f', bgColor: '#fff1f0' };
case 'warning':
return { IconComponent: MailOutlined, color: '#1890ff', bgColor: '#fffbe6' };
return { IconComponent: WarningFilled, color: '#faad14', bgColor: '#fffbe6' };
case 'resolved':
return { IconComponent: MailOutlined, color: '#52c41a', bgColor: '#f6ffed' };
return { IconComponent: CheckCircleFilled, color: '#52c41a', bgColor: '#f6ffed' };
default:
return { IconComponent: MailOutlined, color: '#1890ff', bgColor: '#e6f7ff' };
return { IconComponent: InfoCircleFilled, color: '#1890ff', bgColor: '#e6f7ff' };
}
};
@@ -239,49 +219,13 @@ const ListNotification = memo(function ListNotification(props) {
);
};
const fetchSearch = async (data) => {
setLoading(true);
try {
const response = await searchData(data);
if (response && response.data) {
const transformedData = transformNotificationData(response.data);
setNotifications(transformedData);
// Update pagination with API response or calculate from data
if (response.paging) {
setPagination({
current_page: response.paging.current_page || page,
current_limit: response.paging.current_limit || limit,
total_limit: response.paging.total_limit || transformedData.length,
total_page:
response.paging.total_page || Math.ceil(transformedData.length / limit),
});
} else {
// Fallback: calculate pagination from data
const totalItems = transformedData.length;
setPagination((prev) => ({
...prev,
current_page: page,
current_limit: limit,
total_limit: totalItems,
total_page: Math.ceil(totalItems / limit),
}));
}
}
} catch (error) {
console.error(error);
} finally {
setLoading(false);
}
};
const handleSearch = () => {
fetchSearch(searchValue);
setSearchTerm(searchValue);
};
const handleSearchClear = () => {
setSearchValue('');
fetchSearch('');
setSearchTerm('');
};
const getUnreadCount = () => notifications.filter((n) => !n.isRead).length;
@@ -424,11 +368,7 @@ const ListNotification = memo(function ListNotification(props) {
flexShrink: 0,
}}
>
{notification.type === 'resolved' ? (
<OpenMail size={28.5} color={color} />
) : (
<IconComponent style={{ fontSize: '22px' }} />
)}
<IconComponent style={{ fontSize: '22px' }} />
</div>
<div style={{ flex: 1 }}>
<Row align="top">
@@ -443,12 +383,8 @@ const ListNotification = memo(function ListNotification(props) {
<div>
<Text strong>{notification.title}</Text>
<div style={{ marginTop: '4px' }}>
<Text
style={{
color: notification.color,
}}
>
Error Code {notification.issue}
<Text style={{ color }}>
{notification.issue}
</Text>
</div>
</div>
@@ -761,8 +697,8 @@ const ListNotification = memo(function ListNotification(props) {
{/* Kolom Kanan: Card */}
<Col flex="auto">
<Card size="small" style={{ borderColor: '#91d5ff' }}>
<Row gutter={[16, 8]} align="top">
<Col xs={24} md={10}>
<Row gutter={[16, 8]} align="middle">
<Col xs={24} md={12}>
<Space direction="vertical" size={4}>
<Space>
<ClockCircleOutlined />
@@ -773,14 +709,13 @@ const ListNotification = memo(function ListNotification(props) {
Added at {log.timestamp}
</Text>
</Space>
<div>
<Text strong>{log.addedBy.name}</Text>
</div>
<div>
<Text strong>
Added by: {log.addedBy.name}
</Text>
<span
style={{
marginLeft: '8px',
border: '1px solid #52c41a',
color: '#52c41a',
padding: '2px 6px',
@@ -793,8 +728,7 @@ const ListNotification = memo(function ListNotification(props) {
</div>
</Space>
</Col>
<Col xs={24} md={14}>
<Text strong>Description:</Text>
<Col xs={24} md={12}>
<Paragraph
style={{
color: '#595959',

File diff suppressed because it is too large Load Diff

View File

@@ -1,85 +0,0 @@
import React, { useState, useEffect, memo } from 'react';
import { useNavigate } from 'react-router-dom';
import { Button, Typography } from 'antd';
import { resetWA } from '../../api/whatsapp-control';
import { useBreadcrumb } from '../../layout/LayoutBreadcrumb';
import { ReloadOutlined } from '@ant-design/icons';
const { Text } = Typography;
const IndexWhatsAppControl = memo(function IndexWhatsAppControl() {
const navigate = useNavigate();
const { setBreadcrumbItems } = useBreadcrumb();
const [isPlaying, setIsPlaying] = useState(true);
const url = import.meta.env.VITE_WHATSAPP_URL;
const handleReset = async () => {
setIsPlaying(false);
await resetWA();
setIsPlaying(true);
};
useEffect(() => {
const token = localStorage.getItem('token');
if (token) {
setBreadcrumbItems([
{
title: (
<Text strong style={{ fontSize: '14px' }}>
WhatsApp Control Panel
</Text>
),
},
]);
} else {
navigate('/signin');
}
}, []);
return (
<div style={{ padding: '20px' }}>
<div style={{ marginBottom: 20 }}>
<Button type="primary" onClick={handleReset} style={{ marginRight: 10 }}>
<ReloadOutlined /> Restart WhatsApp
</Button>
</div>
<div
style={{
border: '1px solid #ddd',
height: '700px',
background: '#fafafa',
}}
>
{isPlaying ? (
<iframe
src={url}
title="WhatsApp Preview"
style={{
width: '100%',
height: '100%',
border: 'none',
}}
/>
) : (
<div
style={{
display: 'flex',
justifyContent: 'center',
alignItems: 'center',
height: '100%',
color: '#888',
}}
>
Memuat Halaman WhatsApp QR Code
</div>
)}
</div>
</div>
);
});
export default IndexWhatsAppControl;

View File

@@ -1,172 +0,0 @@
import React, { useState, useEffect, useRef, memo } from 'react';
import { useNavigate } from 'react-router-dom';
import { Button, Typography, message } from 'antd';
import { resetWA } from '../../api/web-control';
import { useBreadcrumb } from '../../layout/LayoutBreadcrumb';
import { ReloadOutlined } from '@ant-design/icons';
const { Text } = Typography;
const IndexWebControl = memo(function IndexWebControl() {
const navigate = useNavigate();
const { setBreadcrumbItems } = useBreadcrumb();
const [isPlaying, setIsPlaying] = useState(true);
const [currentUrl, setCurrentUrl] = useState('http://localhost:9531');
const iframeRef = useRef(null);
const handleReset = async () => {
setIsPlaying(false);
await resetWA();
setIsPlaying(true);
// Kembali ke halaman login setelah reset
setCurrentUrl('https://localhost:9531');
message.success('WhatsApp berhasil di-restart');
};
// Fungsi untuk redirect ke QR View
const redirectToQRView = () => {
setCurrentUrl('https://localhost:9531/qrview');
message.info('Redirecting to QR View...');
};
// Fungsi untuk kembali ke login
const backToLogin = () => {
setCurrentUrl('https://localhost:9531');
message.info('Back to login page');
};
useEffect(() => {
const token = localStorage.getItem('token');
if (token) {
setBreadcrumbItems([
{
title: (
<Text strong style={{ fontSize: '14px' }}>
Web Control Panel
</Text>
),
},
]);
} else {
navigate('/signin');
}
}, [navigate, setBreadcrumbItems]);
// Mendengarkan pesan dari iframe
useEffect(() => {
const handleMessage = (event) => {
// Terima pesan dari domain manapun untuk testing
console.log('Message received from:', event.origin);
console.log('Message data:', event.data);
// Cek apakah ini pesan login success
if (event.data) {
// Jika pesan adalah string
if (typeof event.data === 'string') {
const lowerData = event.data.toLowerCase();
if (
lowerData.includes('login') ||
lowerData.includes('success') ||
lowerData.includes('authenticated') ||
lowerData.includes('qrview')
) {
console.log('Login detected via string message');
redirectToQRView();
}
}
// Jika pesan adalah object
if (typeof event.data === 'object') {
if (
event.data.type === 'LOGIN_SUCCESS' ||
event.data.status === 'success' ||
event.data.logged_in === true ||
event.data.redirect === true
) {
console.log('Login detected via object message');
redirectToQRView();
}
}
}
};
window.addEventListener('message', handleMessage);
return () => {
window.removeEventListener('message', handleMessage);
};
}, []);
// Alternative: Coba dengan timer (jika postMessage tidak berfungsi)
useEffect(() => {
// Jika tidak ada pesan dari iframe, coba redirect otomatis setelah 10 detik
// Asumsi: login biasanya selesai dalam 10 detik
const timer = setTimeout(() => {
if (currentUrl === 'https://localhost:9531') {
console.log('Auto redirect after 10 seconds (fallback)');
redirectToQRView();
}
}, 10000);
return () => clearTimeout(timer);
}, [currentUrl]);
return (
<div style={{ padding: '20px' }}>
<div style={{ marginBottom: 20, display: 'flex', gap: '10px', flexWrap: 'wrap' }}>
<Button type="primary" onClick={handleReset}>
<ReloadOutlined /> Restart WhatsApp
</Button>
{/* <Button onClick={redirectToQRView} type="default">
Redirect ke QR View
</Button>
<Button onClick={backToLogin} type="default">
Kembali ke Login
</Button> */}
</div>
<div
style={{
border: '1px solid #ddd',
height: '700px',
background: '#fafafa',
position: 'relative',
}}
>
{isPlaying ? (
<iframe
key={currentUrl} // Force re-render saat URL berubah
ref={iframeRef}
src={currentUrl}
title="Web Preview"
style={{
width: '100%',
height: '100%',
border: 'none',
}}
onLoad={() => {
console.log('Iframe loaded with URL:', currentUrl);
// Hanya log, tidak mencoba mengakses URL untuk menghindari error CORS
}}
onError={(e) => console.error('Iframe error:', e)}
/>
) : (
<div
style={{
display: 'flex',
justifyContent: 'center',
alignItems: 'center',
height: '100%',
color: '#888',
}}
>
Memuat Halaman WhatsApp QR Code
</div>
)}
</div>
</div>
);
});
export default IndexWebControl;