diff --git a/app/src/components/Sidebar/TopicPanel/TopicTypeButton.tsx b/app/src/components/Sidebar/TopicPanel/TopicTypeButton.tsx index d5e8095..3fcb439 100644 --- a/app/src/components/Sidebar/TopicPanel/TopicTypeButton.tsx +++ b/app/src/components/Sidebar/TopicPanel/TopicTypeButton.tsx @@ -9,7 +9,8 @@ import Popper from '@material-ui/core/Popper' import MenuItem from '@material-ui/core/MenuItem' import MenuList from '@material-ui/core/MenuList' -const options: q.TopicDataType[] = ['string', 'json', 'hex', 'integer', 'unsigned int', 'floating point']; +// const options: q.TopicDataType[] = ['json', 'string', 'hex', 'integer', 'unsigned int', 'floating point'] +const options: q.TopicDataType[] = ['json', 'string', 'hex', 'uint8', 'uint16', 'uint32', 'uint64', 'int8', 'int16', 'int32', 'int64', 'float', 'double'] export const TopicTypeButton = (props: { node?: q.TreeNode diff --git a/backend/src/Model/Base64Message.ts b/backend/src/Model/Base64Message.ts index 82ae52c..86bf00e 100644 --- a/backend/src/Model/Base64Message.ts +++ b/backend/src/Model/Base64Message.ts @@ -26,7 +26,7 @@ export class Base64Message { return new Base64Message(Base64.encode(str)) } - /* Raw message conversions (hex, uint, int, float) */ + /* Raw message conversions ('uint8' | 'uint16' | 'uint32' | 'uint64' | 'int8' | 'int16' | 'int32' | 'int64' | 'float' | 'double') */ public static format(message: Base64Message | null, type: TopicDataType = 'string'): [string, 'json' | undefined] { if (!message) { return ['', undefined] @@ -44,19 +44,54 @@ export class Base64Message { const hex = Base64Message.toHex(message) return [hex, undefined] } - case 'integer': + case 'uint8': { - const int = Base64Message.toInt(message) - return [int ? int : '', undefined] - } - case 'unsigned int': - { - const uint = Base64Message.toUInt(message) + const uint = Base64Message.toUInt(message, 1) return [uint ? uint : '', undefined] } - case 'floating point': + case 'uint16': { - const float = Base64Message.toFloat(message) + const uint = Base64Message.toUInt(message, 2) + return [uint ? uint : '', undefined] + } + case 'uint32': + { + const uint = Base64Message.toUInt(message, 4) + return [uint ? uint : '', undefined] + } + case 'uint64': + { + const uint = Base64Message.toUInt(message, 8) + return [uint ? uint : '', undefined] + } + case 'int8': + { + const int = Base64Message.toInt(message, 1) + return [int ? int : '', undefined] + } + case 'int16': + { + const int = Base64Message.toInt(message, 2) + return [int ? int : '', undefined] + } + case 'int32': + { + const int = Base64Message.toInt(message, 4) + return [int ? int : '', undefined] + } + case 'int64': + { + const int = Base64Message.toInt(message, 8) + return [int ? int : '', undefined] + } + case 'float': + { + const float = Base64Message.toFloat(message, 4) + return [float ? float : '', undefined] + } + case 'double': + { + const float = Base64Message.toFloat(message, 8) return [float ? float : '', undefined] } default: @@ -76,72 +111,93 @@ export class Base64Message { let str: string = ''; buf.forEach(element => { - str += `0x${element.toString(16)} ` + let hex = element.toString(16).toUpperCase(); + str += `0x${hex.length < 2 ? "0" + hex : hex} ` }) return str.trimRight() } - public static toUInt(message: Base64Message) { + public static toUInt(message: Base64Message, bytes: number) { const buf = Buffer.from(message.base64Message, 'base64') - let num: Number = 0; - switch (buf.length) { + let str: String[] = []; + switch (bytes) { case 1: - num = buf.readUInt8(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readUInt8(index).toString()) + } break case 2: - num = buf.readUInt16LE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readUInt16LE(index).toString()) + } break case 4: - num = buf.readUInt32LE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readUInt32LE(index).toString()) + } break case 8: - num = Number(buf.readBigUInt64LE(0)) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readBigUInt64LE(index).toString()) + } break default: return undefined } - return num.toString() + return str.join(', ') } - public static toInt(message: Base64Message) { + public static toInt(message: Base64Message, bytes: number) { const buf = Buffer.from(message.base64Message, 'base64') - let num: Number = 0; - switch (buf.length) { + let str: String[] = []; + switch (bytes) { case 1: - num = buf.readInt8(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readInt8(index).toString()) + } break case 2: - num = buf.readInt16LE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readInt16LE(index).toString()) + } break case 4: - num = buf.readInt32LE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readInt32LE(index).toString()) + } break case 8: - num = Number(buf.readBigInt64LE(0)) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readBigInt64LE(index).toString()) + } break default: return undefined } - return num.toString() + return str.join(', ') } - public static toFloat(message: Base64Message) { + public static toFloat(message: Base64Message, bytes: number) { const buf = Buffer.from(message.base64Message, 'base64') - let num: Number = 0; - switch (buf.length) { + let str: String[] = []; + switch (bytes) { case 4: - num = buf.readFloatLE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readFloatLE(index).toString()) + } break case 8: - num = buf.readDoubleLE(0) + for (let index = 0; index < buf.length; index += bytes) { + str.push(buf.readDoubleLE(index).toString()) + } break default: return undefined } - return num.toString() + return str.join(', ') } public static toDataUri(message: Base64Message, mimeType: string) { diff --git a/backend/src/Model/TreeNode.ts b/backend/src/Model/TreeNode.ts index d9ca465..7adcd98 100644 --- a/backend/src/Model/TreeNode.ts +++ b/backend/src/Model/TreeNode.ts @@ -2,7 +2,8 @@ import { Destroyable } from './Destroyable' import { Edge, Message, RingBuffer, MessageHistory } from './' import { EventDispatcher } from '../../../events' -export type TopicDataType = 'string' | 'json' | 'hex' | 'integer' | 'unsigned int' | 'floating point' +// export type TopicDataType = 'json' | 'string' | 'hex' | 'integer' | 'unsigned int' | 'floating point' +export type TopicDataType = 'json' | 'string' | 'hex' | 'uint8' | 'uint16' | 'uint32' | 'uint64' | 'int8' | 'int16' | 'int32' | 'int64' | 'float' | 'double' export class TreeNode { public sourceEdge?: Edge @@ -19,7 +20,7 @@ export class TreeNode { public onMessage = new EventDispatcher() public onDestroy = new EventDispatcher>() public isTree = false - public type: TopicDataType = 'string' + public type: TopicDataType = 'json' private cachedPath?: string private cachedChildTopics?: Array>