ValveSoftware / openvr

OpenVR SDK
http://steamvr.com
BSD 3-Clause "New" or "Revised" License
6.14k stars 1.28k forks source link

openvr driver about overwriting vive hmd positioning and getting vive hmd gyroscope rotation data #1664

Open oneday1992 opened 2 years ago

oneday1992 commented 2 years ago

Hello,

I created an openvr driver and it works fine. I have tried adding a device in the driver: TrackedDeviceClass_GenericTracker, this tracker device receives 3rd party positioning data via UDP, and overlays the positioning data with the helmet positioning data by using trackingoverrides; I don't use a base station. The problem now is:

1.When I use trackingoverrides to override the HMD positioning, the window of the steamVR application immediately pops up a prompt box, prompting me to set the room, the error code is C200; and the VR view is not displayed on the PC.like the picture: https://user-images.githubusercontent.com/39475297/148365368-d15b0e84-e2ab-449b-abc5-f1b91b94cd1f.png I see there are some methods that say other chaperone json files can be used directly, but I don't know how to use it, can anyone tell me the details? How to unify the coordinate system in the openvr driver, and how to avoid the frequent pop-up of room settings in steamvr?

  1. I want to use the position data in the third-party positioning data in the driver (without its rotation), and then use the rotation data of the HTC VIVE helmet's own gyroscope, and combine the third-party position data with the rotation data of the HTC vive helmet's gyroscope. After fusion, I set the positioning and rotation of the helmet together, because I know its own gyro rotation data is very accurate. Is my method correct? And how to get the rotation data of HTC vive helmet gyroscope through openvr driver? Note that I do not use lighthouse base stations. I have tested a lot of examples, but all of them have the above problems, including the vive official git sample, OpenVR-driver-for-DIY, Simple-OpenVR-Driver-Tutorial and many more. Hope to get help, thanks. I asked the same question on the steam forum because I was really bothered by it for a long time, I hope to get help, thanks. Best , Looking forward to getting a reply
TheBricktop commented 2 years ago

This is very much interesting problem, im very much curious about this too.

BlueprintBen commented 2 years ago

I'll bump this by saying I'm also looking to access the HMD's original IMU data while overriding the final pose through my custom driver. I'm imagining there should be an interface within the Custom Driver API that allows one to query for other active drivers and get their raw pose information (unaffected by TrackingOverrides). Any thoughts on if this could eventually be implemented @JoeLudwig / @aaronleiby? The TrackingOverrides Wiki page has mentioned "Losing access to the original pose" as a problem since 2019.

TheDeveloperGuy commented 2 years ago

The current way to do this is via a hook driver. It's not recommended and has the potential to blow up SteamVR if not implemented correctly, but can be done, and does work. Hooking Windows DLL functions is non-trivial, so I'd recommend learning a lot more about that and SteamVR internals before attempting it. Also, it's very much discouraged by Valve devs due to its potential to cause big problems in SteamVR. I have however had it in a commercial SteamVR driver for years without issue. YMMV.

BlueprintBen commented 2 years ago

Thanks for the direction @TheDeveloperGuy! The risks seem acceptable to us - we're primarily using this in a controlled environment. Are you hooking into vrserver.exe or the overridden driver's DLL? I don't believe debug symbols are available so were you grabbing RVAs for functions to hook via something like x64dbg? Am trying to get acquainted with things here but seems like a deep rabbit hole for sure.

TheDeveloperGuy commented 2 years ago

It would be irresponsible of me to give too much information about this on a public forum.

For a starting point, look at MinHook. Your driver DLL (and the one you want to hook) is loaded by vrserver.exe. You know the signatures of the functions you're hooking from the OpenVR headers. You don't need debug symbols or to do any kind of reverse-engineering. You'd need to ensure your driver was loaded before the default driver that handles Vive etc.

BlueprintBen commented 2 years ago

I've used MinHook to intercept the one function exported from the target driver (HmdDriverFactory) as described, but the function I really want to intercept is IVRServerDriverHost::TrackedDevicePoseUpdated which, as a non-exported virtual member function that I don't even readily have a reference to the object that it's called on, seems much more out of reach.

I'm BlueprintBen#4055 on Discord or ben@blueprintreality.com via email - I'd be extremely grateful to continue the conversation elsewhere if you have any time to elaborate any further.

TheDeveloperGuy commented 2 years ago

@oneday1992 AFAIK there isn't a way to get any kind of tracking data from a Lighthouse-tracked device (Vive, Index, Vive tracker) without using Lighthouses (ie. they don't work at all, not just in 3DOF without Lighthouses). So, you'd have to provide your own rotation data. It seems SteamVR's ATW (reprojection) doesn't take overridden tracker data into account, so you'd have to turn that off. Room setups are per "tracking universe". You'd have to at least run Room Setup in "standing" mode to get "chaperone" data set up. You could figure out the data format of the JSON and set it manually, but AFAIK there isn't a programmatic way of doing that through OpenVR.

duguguang commented 8 months ago

Is there any new progress?