diff --git a/remote.html b/remote.html index 4765978..78f5a36 100644 --- a/remote.html +++ b/remote.html @@ -185,6 +185,25 @@ .refresh-btn:hover { background-color: #45a049; } + .filter-container { + display: flex; + align-items: center; + gap: 10px; + margin-bottom: 10px; + } + .filter-label { + color: #ccc; + font-size: 0.9em; + } + .filter-select { + flex: 1; + padding: 8px; + border-radius: 5px; + border: 1px solid #555; + background-color: #4a4c56; + color: white; + font-size: 0.9em; + } @@ -198,10 +217,22 @@
+
+ Group: + +
+
+ Group: + +
@@ -310,14 +341,24 @@ function renderItems() { const itemList = document.getElementById('itemList'); + const groupFilter = document.getElementById('itemGroupFilter').value; itemList.innerHTML = ''; - if (Object.keys(items).length === 0) { + // Update group filter options + updateItemGroupFilter(); + + // Filter items by group + let filteredItems = Object.values(items); + if (groupFilter) { + filteredItems = filteredItems.filter(item => item.GroupName === groupFilter); + } + + if (filteredItems.length === 0) { itemList.innerHTML = '
No items found
'; return; } - Object.values(items).forEach(item => { + filteredItems.forEach(item => { const itemCard = document.createElement('div'); itemCard.className = 'item-card'; @@ -348,12 +389,26 @@ case 2: // ITEM_VALUE_NO_VALUE controlHtml = '
No control
'; break; + case 3: // ITEM_VALUE_ENUM + const valueNames = item.ValueNames || []; + let optionsHtml = ''; + valueNames.forEach((name, index) => { + optionsHtml += ``; + }); + controlHtml = ` + + `; + break; } + const groupInfo = item.GroupName ? ` | Group: ${item.GroupName}` : ''; itemCard.innerHTML = `
${item.Name}
-
ItemId: ${item.ItemId} | Type: ${getTypeName(type)}
+
ItemId: ${item.ItemId} | Type: ${getTypeName(type)}${groupInfo}
${controlHtml} `; @@ -362,6 +417,28 @@ }); } + function updateItemGroupFilter() { + const select = document.getElementById('itemGroupFilter'); + const currentValue = select.value; + const groups = new Set(); + + Object.values(items).forEach(item => { + if (item.GroupName) { + groups.add(item.GroupName); + } + }); + + select.innerHTML = ''; + Array.from(groups).sort().forEach(group => { + const option = document.createElement('option'); + option.value = group; + option.textContent = group; + select.appendChild(option); + }); + + select.value = currentValue; + } + function toggleItem(itemId, newValue) { if (!socket || socket.readyState !== WebSocket.OPEN) { alert('Not connected to server'); @@ -401,11 +478,30 @@ socket.send(JSON.stringify(message)); } + function setEnumItem(itemId, value) { + if (!socket || socket.readyState !== WebSocket.OPEN) { + alert('Not connected to server'); + return; + } + + const message = { + MessageType: 'ItemUpdate', + Data: [{ + ItemId: itemId, + Value: parseInt(value) + }], + FullList: false + }; + + socket.send(JSON.stringify(message)); + } + function getTypeName(type) { switch (type) { case 0: return 'BOOL'; case 1: return 'UINT'; case 2: return 'NO_VALUE'; + case 3: return 'ENUM'; default: return 'UNKNOWN'; } } @@ -425,14 +521,24 @@ function renderSensors() { const sensorList = document.getElementById('sensorList'); + const groupFilter = document.getElementById('sensorGroupFilter').value; sensorList.innerHTML = ''; - if (Object.keys(sensors).length === 0) { + // Update group filter options + updateSensorGroupFilter(); + + // Filter sensors by group + let filteredSensors = Object.values(sensors); + if (groupFilter) { + filteredSensors = filteredSensors.filter(sensor => sensor.GroupName === groupFilter); + } + + if (filteredSensors.length === 0) { sensorList.innerHTML = '
No sensors found
'; return; } - Object.values(sensors).forEach(sensor => { + filteredSensors.forEach(sensor => { const sensorCard = document.createElement('div'); sensorCard.className = 'sensor-card'; @@ -456,11 +562,12 @@ // Truncate to 2 decimal places const fieldValue = Number(sensor.Field).toFixed(2); + const groupInfo = sensor.GroupName ? ` | Group: ${sensor.GroupName}` : ''; sensorCard.innerHTML = `
${sensor.Name}
-
Type: ${typeName} | ID: ${sensor.Id}
+
Type: ${typeName} | ID: ${sensor.Id}${groupInfo}
@@ -473,11 +580,34 @@ }); } + function updateSensorGroupFilter() { + const select = document.getElementById('sensorGroupFilter'); + const currentValue = select.value; + const groups = new Set(); + + Object.values(sensors).forEach(sensor => { + if (sensor.GroupName) { + groups.add(sensor.GroupName); + } + }); + + select.innerHTML = ''; + Array.from(groups).sort().forEach(group => { + const option = document.createElement('option'); + option.value = group; + option.textContent = group; + select.appendChild(option); + }); + + select.value = currentValue; + } + function getTypeName(type) { switch (type) { case 0: return 'BOOL'; case 1: return 'UINT'; case 2: return 'NO_VALUE'; + case 3: return 'ENUM'; default: return 'UNKNOWN'; } }