@imperosoft/cris-webui-components 1.1.2-beta.1 → 1.1.2-beta.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -21,6 +21,8 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
21
21
  var index_exports = {};
22
22
  __export(index_exports, {
23
23
  CrisButton: () => CrisButton,
24
+ CrisCoDebug: () => CrisCoDebug,
25
+ CrisCoMatrixListsTie: () => CrisCoMatrixListsTie,
24
26
  CrisGauge: () => CrisGauge,
25
27
  CrisOfflinePage: () => CrisOfflinePage,
26
28
  CrisSlider: () => CrisSlider,
@@ -108,9 +110,12 @@ function CrisButton({
108
110
  iconNameActive,
109
111
  iconClassActive,
110
112
  iconStyleActive,
113
+ selected,
111
114
  showControlFeedback = true,
112
115
  showLocalFeedback = true,
113
116
  suppressKeyClicks = false,
117
+ visible,
118
+ enabled,
114
119
  smartId,
115
120
  className = "",
116
121
  classActive = "",
@@ -134,11 +139,11 @@ function CrisButton({
134
139
  const touchStartedHereRef = (0, import_react.useRef)(false);
135
140
  const feedbackJoin = joinFeedback ?? join;
136
141
  const feedback = (0, import_cris_webui_ch5_core.useDigital)(feedbackJoin ?? 0);
137
- const enabled = (0, import_cris_webui_ch5_core.useDigital)(joinEnable ?? 0);
138
- const visible = (0, import_cris_webui_ch5_core.useDigital)(joinVisible ?? 0);
142
+ const enabledJoin = (0, import_cris_webui_ch5_core.useDigital)(joinEnable ?? 0);
143
+ const visibleJoin = (0, import_cris_webui_ch5_core.useDigital)(joinVisible ?? 0);
139
144
  const dSet = (0, import_cris_webui_ch5_core.useJoinsStore)((state) => state.dSet);
140
- const isEnabled = joinEnable == null ? true : enabled;
141
- const isVisible = joinVisible == null ? true : visible;
145
+ const isEnabled = enabled ?? (joinEnable == null ? true : enabledJoin);
146
+ const isVisible = visible ?? (joinVisible == null ? true : visibleJoin);
142
147
  (0, import_react.useEffect)(() => {
143
148
  log("visibility effect", { isVisible, pressedRef: pressedRef.current });
144
149
  if (!isVisible && pressedRef.current) {
@@ -161,7 +166,7 @@ function CrisButton({
161
166
  }
162
167
  };
163
168
  }, [join, smartId, dSet, log]);
164
- const hasControlFeedback = showControlFeedback && feedbackJoin != null && feedback;
169
+ const hasControlFeedback = showControlFeedback && (feedbackJoin != null && feedback || selected === true);
165
170
  const hasPressedFeedback = showLocalFeedback && pressed && isEnabled;
166
171
  const isActive = hasControlFeedback || hasPressedFeedback;
167
172
  let currentText = text ?? "";
@@ -1138,9 +1143,470 @@ function CrisOfflinePage({
1138
1143
  ] })
1139
1144
  ] }) });
1140
1145
  }
1146
+
1147
+ // src/components/CrisCoDebug.tsx
1148
+ var import_cris_webui_ch5_core7 = require("@imperosoft/cris-webui-ch5-core");
1149
+ var import_jsx_runtime7 = require("react/jsx-runtime");
1150
+ var defaultStyles = {
1151
+ container: {
1152
+ display: "flex",
1153
+ flexDirection: "column",
1154
+ overflow: "auto",
1155
+ gap: 2
1156
+ },
1157
+ title: {
1158
+ fontSize: 14,
1159
+ fontWeight: 600,
1160
+ padding: "8px 12px",
1161
+ opacity: 0.7
1162
+ },
1163
+ item: {
1164
+ display: "flex",
1165
+ alignItems: "center",
1166
+ padding: "8px 12px",
1167
+ gap: 8,
1168
+ minHeight: 48
1169
+ },
1170
+ info: {
1171
+ flex: 1,
1172
+ minWidth: 0,
1173
+ overflow: "hidden"
1174
+ },
1175
+ moduleName: {
1176
+ fontSize: 14,
1177
+ fontWeight: 600,
1178
+ whiteSpace: "nowrap",
1179
+ overflow: "hidden",
1180
+ textOverflow: "ellipsis"
1181
+ },
1182
+ moduleType: {
1183
+ fontSize: 11,
1184
+ opacity: 0.5
1185
+ },
1186
+ icons: {
1187
+ display: "flex",
1188
+ gap: 4,
1189
+ alignItems: "center",
1190
+ minWidth: 56,
1191
+ justifyContent: "center"
1192
+ },
1193
+ buttons: {
1194
+ display: "flex",
1195
+ gap: 4,
1196
+ alignItems: "center"
1197
+ },
1198
+ iconBox: {
1199
+ width: 24,
1200
+ height: 24,
1201
+ display: "flex",
1202
+ alignItems: "center",
1203
+ justifyContent: "center",
1204
+ position: "relative"
1205
+ }
1206
+ };
1207
+ function ConnectionIcon({ on, type }) {
1208
+ const label = type === "eth" ? "ETH" : "RS";
1209
+ return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1210
+ "div",
1211
+ {
1212
+ style: {
1213
+ ...defaultStyles.iconBox,
1214
+ opacity: on ? 1 : 0.4
1215
+ },
1216
+ title: `${type === "eth" ? "Ethernet" : "RS232"}: ${on ? "Connected" : "Disconnected"}`,
1217
+ children: /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("svg", { width: "20", height: "20", viewBox: "0 0 20 20", children: [
1218
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("rect", { x: "1", y: "4", width: "18", height: "12", rx: "2", fill: "none", stroke: "currentColor", strokeWidth: "1.5" }),
1219
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("text", { x: "10", y: "12.5", textAnchor: "middle", fontSize: "7", fontWeight: "bold", fill: "currentColor", children: label }),
1220
+ on ? /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("circle", { cx: "16", cy: "5", r: "3.5", fill: "#4caf50", stroke: "none" }) : /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(import_jsx_runtime7.Fragment, { children: [
1221
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("circle", { cx: "16", cy: "5", r: "3.5", fill: "#f44336", stroke: "none" }),
1222
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("line", { x1: "14", y1: "3", x2: "18", y2: "7", stroke: "white", strokeWidth: "1.5" })
1223
+ ] })
1224
+ ] })
1225
+ }
1226
+ );
1227
+ }
1228
+ function DebugModuleItem({
1229
+ module: module2,
1230
+ onAction,
1231
+ itemClassName,
1232
+ itemStyle,
1233
+ buttonClassName,
1234
+ buttonActiveClassName,
1235
+ iconEthOn,
1236
+ iconEthOff,
1237
+ iconRs232On,
1238
+ iconRs232Off
1239
+ }) {
1240
+ const name = module2.lb ? `${module2.id} (${module2.lb})` : module2.id;
1241
+ return /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(
1242
+ "div",
1243
+ {
1244
+ className: itemClassName,
1245
+ style: itemClassName ? itemStyle : { ...defaultStyles.item, ...itemStyle },
1246
+ children: [
1247
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { style: defaultStyles.info, children: [
1248
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { style: defaultStyles.moduleName, children: name }),
1249
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { style: defaultStyles.moduleType, children: module2.tp })
1250
+ ] }),
1251
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { style: defaultStyles.icons, children: [
1252
+ module2.et.vs && (iconEthOn && iconEthOff ? module2.et.on ? iconEthOn : iconEthOff : /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(ConnectionIcon, { on: module2.et.on, type: "eth" })),
1253
+ module2.rs.vs && (iconRs232On && iconRs232Off ? module2.rs.on ? iconRs232On : iconRs232Off : /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(ConnectionIcon, { on: module2.rs.on, type: "rs232" }))
1254
+ ] }),
1255
+ /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)("div", { style: defaultStyles.buttons, children: [
1256
+ module2.md.vs && /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1257
+ CrisButton,
1258
+ {
1259
+ selected: module2.md.on,
1260
+ text: "Mod",
1261
+ className: buttonClassName,
1262
+ classActive: buttonActiveClassName,
1263
+ onPress: () => onAction("toggleMod", module2.id)
1264
+ }
1265
+ ),
1266
+ module2.cm.vs && /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1267
+ CrisButton,
1268
+ {
1269
+ selected: module2.cm.on,
1270
+ text: "Com",
1271
+ className: buttonClassName,
1272
+ classActive: buttonActiveClassName,
1273
+ onPress: () => onAction("toggleCom", module2.id)
1274
+ }
1275
+ )
1276
+ ] })
1277
+ ]
1278
+ }
1279
+ );
1280
+ }
1281
+ function CrisCoDebug({
1282
+ oid = "__DBG__",
1283
+ title,
1284
+ className,
1285
+ style,
1286
+ itemClassName,
1287
+ itemStyle,
1288
+ buttonClassName,
1289
+ buttonActiveClassName,
1290
+ iconEthOn,
1291
+ iconEthOff,
1292
+ iconRs232On,
1293
+ iconRs232Off
1294
+ }) {
1295
+ const modules = (0, import_cris_webui_ch5_core7.useCustomObject)(oid);
1296
+ const send = (0, import_cris_webui_ch5_core7.useCustomObjectSend)();
1297
+ const handleAction = (action, id) => {
1298
+ send(oid, { action, id });
1299
+ };
1300
+ if (!modules || modules.length === 0) {
1301
+ return null;
1302
+ }
1303
+ const visibleModules = modules.filter((m) => m.vs);
1304
+ return /* @__PURE__ */ (0, import_jsx_runtime7.jsxs)(
1305
+ "div",
1306
+ {
1307
+ className,
1308
+ style: className ? style : { ...defaultStyles.container, ...style },
1309
+ children: [
1310
+ title && /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { style: defaultStyles.title, children: title }),
1311
+ visibleModules.map((module2) => /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(
1312
+ DebugModuleItem,
1313
+ {
1314
+ module: module2,
1315
+ onAction: handleAction,
1316
+ itemClassName,
1317
+ itemStyle,
1318
+ buttonClassName,
1319
+ buttonActiveClassName,
1320
+ iconEthOn,
1321
+ iconEthOff,
1322
+ iconRs232On,
1323
+ iconRs232Off
1324
+ },
1325
+ module2.id
1326
+ ))
1327
+ ]
1328
+ }
1329
+ );
1330
+ }
1331
+
1332
+ // src/components/CrisCoMatrixListsTie.tsx
1333
+ var import_cris_webui_ch5_core8 = require("@imperosoft/cris-webui-ch5-core");
1334
+ var import_jsx_runtime8 = require("react/jsx-runtime");
1335
+ var defaults = {
1336
+ container: {
1337
+ display: "flex",
1338
+ flexDirection: "row",
1339
+ gap: 8,
1340
+ height: "100%"
1341
+ },
1342
+ list: {
1343
+ flex: 1,
1344
+ display: "flex",
1345
+ flexDirection: "column",
1346
+ overflow: "hidden",
1347
+ minHeight: 0
1348
+ },
1349
+ header: {
1350
+ fontSize: 13,
1351
+ fontWeight: 600,
1352
+ padding: "6px 10px",
1353
+ textTransform: "uppercase",
1354
+ opacity: 0.6,
1355
+ flexShrink: 0
1356
+ },
1357
+ scroll: {
1358
+ flex: 1,
1359
+ minHeight: 0,
1360
+ overflow: "auto",
1361
+ WebkitOverflowScrolling: "touch",
1362
+ display: "flex",
1363
+ flexDirection: "column",
1364
+ gap: 2
1365
+ },
1366
+ item: {
1367
+ display: "flex",
1368
+ alignItems: "center",
1369
+ gap: 6,
1370
+ padding: "6px 10px",
1371
+ minHeight: 40,
1372
+ cursor: "pointer",
1373
+ userSelect: "none"
1374
+ },
1375
+ itemLabel: {
1376
+ flex: 1,
1377
+ fontSize: 13,
1378
+ whiteSpace: "nowrap",
1379
+ overflow: "hidden",
1380
+ textOverflow: "ellipsis"
1381
+ },
1382
+ indicators: {
1383
+ display: "flex",
1384
+ gap: 4,
1385
+ alignItems: "center"
1386
+ },
1387
+ indicator: {
1388
+ width: 8,
1389
+ height: 8,
1390
+ borderRadius: "50%",
1391
+ flexShrink: 0
1392
+ }
1393
+ };
1394
+ function DefaultIoIndicator({ on }) {
1395
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1396
+ "div",
1397
+ {
1398
+ style: {
1399
+ ...defaults.indicator,
1400
+ backgroundColor: on ? "#4caf50" : "#f44336"
1401
+ },
1402
+ title: on ? "Online" : "Offline"
1403
+ }
1404
+ );
1405
+ }
1406
+ function DefaultSignalIndicator({ on }) {
1407
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1408
+ "div",
1409
+ {
1410
+ style: {
1411
+ ...defaults.indicator,
1412
+ backgroundColor: on ? "#2196f3" : "#666"
1413
+ },
1414
+ title: on ? "Signal detected" : "No signal"
1415
+ }
1416
+ );
1417
+ }
1418
+ function MatrixItemRow({
1419
+ item,
1420
+ type,
1421
+ active,
1422
+ showChannels,
1423
+ vmText,
1424
+ onSelect,
1425
+ onToggleVideoMute,
1426
+ itemClassName,
1427
+ itemStyle: itemStyleProp,
1428
+ itemActiveClassName,
1429
+ itemActiveStyle,
1430
+ itemDisabledClassName,
1431
+ vmButtonClassName,
1432
+ vmButtonActiveClassName,
1433
+ renderIoIndicator,
1434
+ renderSignalIndicator
1435
+ }) {
1436
+ const isActive = active;
1437
+ const isEnabled = item.sl.en;
1438
+ const classes = [
1439
+ "cris-co-matrix-item",
1440
+ itemClassName,
1441
+ isActive && (itemActiveClassName || "active"),
1442
+ !isEnabled && (itemDisabledClassName || "disabled")
1443
+ ].filter(Boolean).join(" ");
1444
+ const computedStyle = itemClassName ? { ...itemStyleProp } : {
1445
+ ...defaults.item,
1446
+ ...itemStyleProp,
1447
+ ...isActive ? itemActiveStyle : void 0,
1448
+ opacity: isEnabled ? 1 : 0.4
1449
+ };
1450
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("div", { className: classes, style: computedStyle, children: [
1451
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1452
+ CrisButton,
1453
+ {
1454
+ selected: isActive,
1455
+ enabled: isEnabled,
1456
+ onPress: onSelect,
1457
+ className: `cris-co-matrix-item-btn ${itemActiveClassName ?? ""}`,
1458
+ classActive: itemActiveClassName,
1459
+ children: /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("div", { style: { display: "flex", alignItems: "center", gap: 6, width: "100%" }, children: [
1460
+ showChannels && /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { className: "cris-co-matrix-ch", style: { flexShrink: 0, opacity: 0.6 }, children: item.id }),
1461
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("span", { style: defaults.itemLabel, children: item.lb || `${type === "input" ? "Input" : "Output"} ${item.id}` }),
1462
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)("div", { style: defaults.indicators, children: [
1463
+ item.io.vs && (renderIoIndicator ? renderIoIndicator(item.io.on) : /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(DefaultIoIndicator, { on: item.io.on })),
1464
+ item.sg.vs && (renderSignalIndicator ? renderSignalIndicator(item.sg.on) : /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(DefaultSignalIndicator, { on: item.sg.on }))
1465
+ ] })
1466
+ ] })
1467
+ }
1468
+ ),
1469
+ item.vm.vs && /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1470
+ CrisButton,
1471
+ {
1472
+ selected: item.vm.on,
1473
+ enabled: item.vm.en,
1474
+ text: vmText,
1475
+ onPress: onToggleVideoMute,
1476
+ className: vmButtonClassName,
1477
+ classActive: vmButtonActiveClassName
1478
+ }
1479
+ )
1480
+ ] });
1481
+ }
1482
+ function CrisCoMatrixListsTie({
1483
+ oid,
1484
+ inputTitle = "Inputs",
1485
+ outputTitle = "Outputs",
1486
+ showChannels = true,
1487
+ className,
1488
+ style,
1489
+ listClassName,
1490
+ listStyle,
1491
+ headerClassName,
1492
+ headerStyle,
1493
+ itemClassName,
1494
+ itemStyle,
1495
+ itemActiveClassName,
1496
+ itemActiveStyle,
1497
+ itemDisabledClassName,
1498
+ vmText = "Mute",
1499
+ vmButtonClassName,
1500
+ vmButtonActiveClassName,
1501
+ renderIoIndicator,
1502
+ renderSignalIndicator
1503
+ }) {
1504
+ const matrix = (0, import_cris_webui_ch5_core8.useCustomObject)(oid);
1505
+ const send = (0, import_cris_webui_ch5_core8.useCustomObjectSend)();
1506
+ if (!matrix) return null;
1507
+ const { si, ip: inputs, op: outputs } = matrix;
1508
+ const handleSelectInput = (id) => {
1509
+ send(oid, { action: "selectInput", id });
1510
+ };
1511
+ const handleTie = (id) => {
1512
+ send(oid, { action: "tie", id });
1513
+ };
1514
+ const handleToggleVideoMute = (type, id) => {
1515
+ send(oid, { action: "toggleVideoMute", type, id });
1516
+ };
1517
+ return /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(
1518
+ "div",
1519
+ {
1520
+ className,
1521
+ style: className ? style : { ...defaults.container, ...style },
1522
+ children: [
1523
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(
1524
+ "div",
1525
+ {
1526
+ className: listClassName,
1527
+ style: listClassName ? listStyle : { ...defaults.list, ...listStyle },
1528
+ children: [
1529
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1530
+ "div",
1531
+ {
1532
+ className: headerClassName,
1533
+ style: headerClassName ? headerStyle : { ...defaults.header, ...headerStyle },
1534
+ children: inputTitle
1535
+ }
1536
+ ),
1537
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("div", { style: defaults.scroll, children: inputs?.map((item) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1538
+ MatrixItemRow,
1539
+ {
1540
+ item,
1541
+ type: "input",
1542
+ active: si === item.id,
1543
+ showChannels,
1544
+ vmText,
1545
+ onSelect: () => handleSelectInput(item.id),
1546
+ onToggleVideoMute: () => handleToggleVideoMute("input", item.id),
1547
+ itemClassName,
1548
+ itemStyle,
1549
+ itemActiveClassName,
1550
+ itemActiveStyle,
1551
+ itemDisabledClassName,
1552
+ vmButtonClassName,
1553
+ vmButtonActiveClassName,
1554
+ renderIoIndicator,
1555
+ renderSignalIndicator
1556
+ },
1557
+ item.id
1558
+ )) })
1559
+ ]
1560
+ }
1561
+ ),
1562
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsxs)(
1563
+ "div",
1564
+ {
1565
+ className: listClassName,
1566
+ style: listClassName ? listStyle : { ...defaults.list, ...listStyle },
1567
+ children: [
1568
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1569
+ "div",
1570
+ {
1571
+ className: headerClassName,
1572
+ style: headerClassName ? headerStyle : { ...defaults.header, ...headerStyle },
1573
+ children: outputTitle
1574
+ }
1575
+ ),
1576
+ /* @__PURE__ */ (0, import_jsx_runtime8.jsx)("div", { style: defaults.scroll, children: outputs?.map((item) => /* @__PURE__ */ (0, import_jsx_runtime8.jsx)(
1577
+ MatrixItemRow,
1578
+ {
1579
+ item,
1580
+ type: "output",
1581
+ active: item.ti === si,
1582
+ showChannels,
1583
+ vmText,
1584
+ onSelect: () => handleTie(item.id),
1585
+ onToggleVideoMute: () => handleToggleVideoMute("output", item.id),
1586
+ itemClassName,
1587
+ itemStyle,
1588
+ itemActiveClassName,
1589
+ itemActiveStyle,
1590
+ itemDisabledClassName,
1591
+ vmButtonClassName,
1592
+ vmButtonActiveClassName,
1593
+ renderIoIndicator,
1594
+ renderSignalIndicator
1595
+ },
1596
+ item.id
1597
+ )) })
1598
+ ]
1599
+ }
1600
+ )
1601
+ ]
1602
+ }
1603
+ );
1604
+ }
1141
1605
  // Annotate the CommonJS export names for ESM import in node:
1142
1606
  0 && (module.exports = {
1143
1607
  CrisButton,
1608
+ CrisCoDebug,
1609
+ CrisCoMatrixListsTie,
1144
1610
  CrisGauge,
1145
1611
  CrisOfflinePage,
1146
1612
  CrisSlider,