diff --git a/EonaCat.HID.Console/EonaCat.HID.Console.csproj b/EonaCat.HID.Console/EonaCat.HID.Console.csproj
new file mode 100644
index 0000000..589f755
--- /dev/null
+++ b/EonaCat.HID.Console/EonaCat.HID.Console.csproj
@@ -0,0 +1,14 @@
+
+
+
+ Exe
+ net8.0
+ enable
+ enable
+
+
+
+
+
+
+
diff --git a/EonaCat.HID.Console/Program.cs b/EonaCat.HID.Console/Program.cs
new file mode 100644
index 0000000..2182867
--- /dev/null
+++ b/EonaCat.HID.Console/Program.cs
@@ -0,0 +1,113 @@
+using EonaCat.HID;
+using System.Globalization;
+
+namespace EonaCat.HID.Example
+{
+ public class Program
+ {
+ static IHidManager _deviceManager;
+ static IHid _device;
+ static IEnumerable _deviceList;
+
+ static async Task Main(string[] args)
+ {
+ try
+ {
+ _deviceManager = HidFactory.CreateDeviceManager();
+ if (_deviceManager == null)
+ {
+ Console.WriteLine("Failed to create HID manager.");
+ return;
+ }
+
+ _deviceManager.OnDeviceInserted += (s, e) =>
+ {
+ Console.WriteLine($"Inserted Device --> VID: {e.Device.VendorId:X4}, PID: {e.Device.ProductId:X4}");
+ };
+
+ _deviceManager.OnDeviceRemoved += (s, e) =>
+ {
+ Console.WriteLine($"Removed Device --> VID: {e.Device.VendorId:X4}, PID: {e.Device.ProductId:X4}");
+ };
+
+ RefreshDevices();
+
+ if (!_deviceList.Any())
+ {
+ Console.WriteLine("No HID found.");
+ return;
+ }
+
+ DisplayDevices();
+
+ Console.Write("Select a device index to connect: ");
+ int index = int.Parse(Console.ReadLine());
+ _device = _deviceList.ElementAt(index);
+
+ _device.OnDataReceived += (s, e) =>
+ {
+ Console.WriteLine($"Rx Data: {BitConverter.ToString(e.Data)}");
+ };
+
+ _device.OnError += (s, e) =>
+ {
+ Console.WriteLine($"Error: {e.Exception.Message}");
+ };
+
+ _device.Open();
+ Console.WriteLine($"Connected to {_device.ProductName}");
+
+ await _device.StartListeningAsync(default);
+
+ Console.WriteLine("Listening... Press [Enter] to send test output report.");
+ Console.ReadLine();
+
+ // Example: Send output report
+ var data = ByteHelper.HexStringToByteArray("01-02-03");
+ byte[] outputReport = new byte[data.Length + 1];
+ outputReport[0] = 0x00; // Report ID
+ Array.Copy(data, 0, outputReport, 1, data.Length);
+
+ await _device.WriteOutputReportAsync(outputReport);
+ Console.WriteLine($"Sent output report: {BitConverter.ToString(outputReport)}");
+
+ Console.WriteLine("Press [Enter] to exit...");
+ Console.ReadLine();
+ }
+ catch (Exception ex)
+ {
+ Console.WriteLine($"[EXCEPTION] {ex.Message}");
+ }
+ }
+
+ static void RefreshDevices(ushort? vendorId = null, ushort? productId = null)
+ {
+ _deviceList = _deviceManager.Enumerate(vendorId, productId);
+ }
+
+ static void DisplayDevices()
+ {
+ int i = 0;
+ foreach (var dev in _deviceList)
+ {
+ Console.WriteLine($"[{i++}] {dev.ProductName} | VID:PID = {dev.VendorId:X4}:{dev.ProductId:X4}");
+ }
+ }
+ }
+
+ public static class ByteHelper
+ {
+ public static byte[] HexStringToByteArray(string hex)
+ {
+ return hex
+ .Replace("-", "")
+ .Replace(" ", "")
+ .ToUpper()
+ .Where(c => Uri.IsHexDigit(c))
+ .Select((c, i) => new { c, i })
+ .GroupBy(x => x.i / 2)
+ .Select(g => byte.Parse($"{g.First().c}{g.Last().c}", NumberStyles.HexNumber))
+ .ToArray();
+ }
+ }
+}
\ No newline at end of file
diff --git a/EonaCat.HID.sln b/EonaCat.HID.sln
index 00d167c..a43121b 100644
--- a/EonaCat.HID.sln
+++ b/EonaCat.HID.sln
@@ -6,6 +6,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EonaCat.HID.Analyzer", "Ana
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EonaCat.HID", "EonaCat.HID\EonaCat.HID.csproj", "{00403BD6-7A26-4971-29D3-8A7849AAC770}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EonaCat.HID.Console", "EonaCat.HID.Console\EonaCat.HID.Console.csproj", "{E8FD1273-26F3-462B-8EDF-4DA044D10D59}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -50,6 +52,22 @@ Global
{00403BD6-7A26-4971-29D3-8A7849AAC770}.Release|x64.Build.0 = Release|Any CPU
{00403BD6-7A26-4971-29D3-8A7849AAC770}.Release|x86.ActiveCfg = Release|Any CPU
{00403BD6-7A26-4971-29D3-8A7849AAC770}.Release|x86.Build.0 = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|x64.Build.0 = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Debug|x86.Build.0 = Debug|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|Any CPU.Build.0 = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|Mixed Platforms.Build.0 = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|x64.ActiveCfg = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|x64.Build.0 = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|x86.ActiveCfg = Release|Any CPU
+ {E8FD1273-26F3-462B-8EDF-4DA044D10D59}.Release|x86.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE