Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Enables a tracker to forward log messages to the server, and the server to send the log messages to the UI. #1234

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
54 changes: 54 additions & 0 deletions gui/src/components/tracker/DeviceLogs.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import { useEffect, useRef, memo, Fragment } from 'react';

type LogProps = {
messages: string[]
};

function Log({ messages } : LogProps) {
const preRef = useRef(null);
const lastScrollTopRef = useRef(0);

useEffect(() => {
const pre = preRef.current;
const lastScrollTop = lastScrollTopRef.current;
// Scroll to the latest message if either:
// - We were looking at the latest message previously; or
// - The scroll height shrunk, e.g. when logs are cleared due to device reconnecting
if (pre && (pre.scrollTop >= lastScrollTop || lastScrollTop >= pre.scrollHeight)) {
pre.scrollTop = pre.scrollHeight;
lastScrollTopRef.current = pre.scrollTop;
}
}, [messages]);

return (
<pre ref={preRef}
style={{
overflowX: 'auto',
maxHeight: '300px',
userSelect: 'text'
}}
>
{messages.length === 0 && (
<>[No log messages]</>
)}
{messages.length > 0 &&
messages.map((msg, index) => (
<Fragment key={index}>
{msg}
<br />
</Fragment>
))}
</pre>
)
}

// Only render if the log messages have actually changed
const LogMemo = memo(Log, (a, b) => {
return (
a.messages.length === b.messages.length &&
a.messages.every((e, i) => b.messages[i] === e));
});

export {
LogMemo as DeviceLog
};
7 changes: 7 additions & 0 deletions gui/src/components/tracker/TrackerSettings.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ import { TrackerCard } from './TrackerCard';
import { Quaternion } from 'three';
import { useAppContext } from '@/hooks/app';
import { MagnetometerToggleSetting } from '@/components/settings/pages/MagnetometerToggleSetting';
import { DeviceLog } from './DeviceLogs';

const rotationsLabels: [Quaternion, string][] = [
[rotationToQuatMap.BACK, 'tracker-rotation-back'],
Expand Down Expand Up @@ -469,6 +470,12 @@ export function TrackerSettingsPage() {
</Button>
</div>
)}
<div className="flex flex-col gap-2 w-full mt-3">
<Typography variant="section-title">
Device Logs
</Typography>
<DeviceLog messages={tracker?.device?.logMessages || []} />
</div>
</div>
</div>
</form>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -259,6 +259,21 @@ public static int createTrackersData(
return fbb.endVector();
}

public static int createLogMessagesData(
FlatBufferBuilder fbb,
Device device
) {
List<String> messages = device.getLogMessages();

int numMessages = messages.size();
int[] messageOffsets = new int[numMessages];
for (int i = 0; i < numMessages; ++i) {
messageOffsets[i] = fbb.createString(messages.get(i));
}

return DeviceData.createLogMessagesVector(fbb, messageOffsets);
}

public static int createDeviceData(
FlatBufferBuilder fbb,
int id,
Expand Down Expand Up @@ -306,12 +321,15 @@ public static int createDeviceData(
? fbb.createString(device.getName())
: 0;

int logMessagesOffset = DataFeedBuilder.createLogMessagesData(fbb, device);

DeviceData.startDeviceData(fbb);
DeviceData.addCustomName(fbb, nameOffset);
DeviceData.addId(fbb, DeviceId.createDeviceId(fbb, id));
DeviceData.addHardwareStatus(fbb, hardwareDataOffset);
DeviceData.addHardwareInfo(fbb, hardwareInfoOffset);
DeviceData.addTrackers(fbb, trackersOffset);
DeviceData.addLogMessages(fbb, logMessagesOffset);

return DeviceData.endDeviceData(fbb);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ open class Device(val magSupport: Boolean = false) {

open val hardwareIdentifier: String = "Unknown"

open var logMessages: MutableList<String> = mutableListOf()

val isOpenVrDevice: Boolean
get() = manufacturer == "OpenVR"

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,9 @@ enum class ServerFeatureFlags {
- `PACKET_ROTATION_AND_ACCELERATION` = 23 (0x17). */
PROTOCOL_BUNDLE_COMPACT_SUPPORT,

/** Server can receive log messages: `PACKET_LOG` = 102 (0x66). */
PROTOCOL_LOG_SUPPORT,

// Add new flags here

BITS_TOTAL, ;
Expand All @@ -60,6 +63,7 @@ enum class ServerFeatureFlags {
val flagsEnabled: Set<ServerFeatureFlags> = setOf(
PROTOCOL_BUNDLE_SUPPORT,
PROTOCOL_BUNDLE_COMPACT_SUPPORT,
PROTOCOL_LOG_SUPPORT,

// Add enabled flags here
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,7 @@ class TrackersUDPServer(private val port: Int, name: String, private val tracker
connection
}
connection.firmwareFeatures = FirmwareFeatures()
connection.logMessages.clear()
bb.limit(bb.capacity())
bb.rewind()
parser.writeHandshakeResponse(bb, connection)
Expand Down Expand Up @@ -561,6 +562,11 @@ class TrackersUDPServer(private val port: Int, name: String, private val tracker
LogManager.info("[TrackerServer] Acknowledged config change on ${connection.descriptiveName} (${trackers.map { it.trackerNum }.joinToString()}). Config changed on ${packet.configType}")
}

is UDPPacket26Log -> {
if (connection == null) return
connection.logMessages.add(packet.message)
}

is UDPPacket200ProtocolChange -> {}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -378,6 +378,13 @@ data class UDPPacket25SetConfigFlag(
}
}

data class UDPPacket26Log(var message: String = "") : UDPPacket(26) {
override fun readData(buf: ByteBuffer) {
val length = buf.get().toUByte().toInt()
message = readASCIIString(buf, length)
}
}

data class UDPPacket200ProtocolChange(
var targetProtocol: Int = 0,
var targetProtocolVersion: Int = 0,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,7 @@ class UDPProtocolParser {
PACKET_USER_ACTION -> UDPPacket21UserAction()
PACKET_FEATURE_FLAGS -> UDPPacket22FeatureFlags()
PACKET_ACK_CONFIG_CHANGE -> UDPPacket24AckConfigChange()
PACKET_LOG -> UDPPacket26Log()
PACKET_PROTOCOL_CHANGE -> UDPPacket200ProtocolChange()
else -> null
}
Expand Down Expand Up @@ -150,6 +151,7 @@ class UDPProtocolParser {
const val PACKET_ROTATION_AND_ACCELERATION = 23
const val PACKET_ACK_CONFIG_CHANGE = 24
const val PACKET_SET_CONFIG_FLAG = 25
const val PACKET_LOG = 26
const val PACKET_BUNDLE = 100
const val PACKET_BUNDLE_COMPACT = 101
const val PACKET_PROTOCOL_CHANGE = 200
Expand Down
Loading