Skip to main content
Up and Coming
September 7, 2014

Head offset

G'day,

DK2 arrived and I have been mucking around with it and the latest UE4 binary build and have come across a little problem - the head offset.

At the moment, impossible to aim correctly while wearing a Rift. Its offsets the location of the camera after it has been adjusted in-game to line up with the weapon sights correctly.

In earlier versions of the Oculus Plugin, you could control the head offset via a config variable:
[Oculus.Settings]
HeadModel_v2=(X=0.0,Y=0,Z=0.0)


In the latest version, this is no longer the case.
Needless to say, this is very frustrating.

This has been mentioned before, but I'll say it too - I don't want anything to be done automatically for me.

Please give game developers the control needed to make the best possible experiences.

Thank you.
    This topic has been closed for replies.

    42 replies

    Up and Coming
    November 19, 2014
    It'll get there.

    On a related note, anyone been able to compile a GitHub source based version of the Oculus plugin that is compatible with the binary release?

    I tried a simply copy'n'paste job, but the binary build complains when it tries to load the one compiled from GitHub source. Different version and all that :(
    Rule#21: Be polite, be professional, but have a plan to kill everyone you meet.
    Up and Coming
    November 20, 2014
    First of all: I'd like to understand that 'aiming' issue.

    The head model offset you are referring to is not modifiable in the latest SDK. Moreover, the head model is not used at all as long as you have positional tracking. The only way to avoid positional offset could be to disable positional tracking at all, which is a bad idea in general.

    Seems to me, you should adjust your aiming by the current position of the HMD. You can use GetCurrentOrientationAndPosition function to get the CurrentPosition (which is a vector, offset from the "zero-position" (where the position was previously reset).

    As to remaining requests.... While I agree that more flexible controls are a must, we should carefully think it through. There are certain limitations (in UE and in Oculus SDK) we can't easily overcome without sacrificing quality of VR experience. It is very easy to make bad VR game with high latency, wrong head model, etc that will instantly make people sick.

    For example, if we do not update PlayerController orientation then objects will start disappearing, if you turn head left or right (since the engine thinks they are out of the player's view). If you don't want orientation and position to be applied 'automatically' - how are you updating it? There is a huge problem with letting devs updating orientation/position themselves: latency. The naive approach with updating camera on a game thread only will lead to latency around 50-60 ms, which is really bad. There are several tricks to keep latency low. One of them is updating orientation / position on a render thread, right before the actual rendering begins. The second - timewarp, that applies newest orientation right before Present. This brings positional latency down to ~35ms and orientational down to ~13 ms (for DK2). Unfortunately, this approach implies 'automagic'.

    What I would like to have is the detailed description of the use cases when you can't achieve your goal using current Oculus plugin (the repro cases as UE projects would be even better). This will give us an idea how to approach the issue / limitation w/o introducing too much handles to create bad VR.
    Up and Coming
    November 20, 2014
    "KrisRedbeard" wrote:
    It'll get there.

    On a related note, anyone been able to compile a GitHub source based version of the Oculus plugin that is compatible with the binary release?

    I tried a simply copy'n'paste job, but the binary build complains when it tries to load the one compiled from GitHub source. Different version and all that :(


    No, you can't just copy binary files simply because the plugin interface has changed. You need to re-build UE4 after getting Oculus integration.
    Up and Coming
    November 20, 2014
    "artyom17" wrote:

    You can use GetCurrentOrientationAndPosition function to get the CurrentPosition (which is a vector, offset from the "zero-position" (where the position was previously reset).


    Does that actually work now? The last time I took a look (I think this was back in 4.4) that function did not return meaningful values and I had to rewrite it.

    "artyom17" wrote:

    For example, if we do not update PlayerController orientation then objects will start disappearing, if you turn head left or right (since the engine thinks they are out of the player's view).


    This was easily fixed. I set the PlayerController orientation to that of the Camera instead of vice versa.

    "artyom17" wrote:

    There are several tricks to keep latency low. One of them is updating orientation / position on a render thread, right before the actual rendering begins. The second - timewarp, that applies newest orientation right before Present. This brings positional latency down to ~35ms and orientational down to ~13 ms (for DK2). Unfortunately, this approach implies 'automagic'.


    I understand how important latency is. Perhaps you could carry these updates out using camera space deltas and the existing rotation/position of the camera rather than trying to set it directly based on rift data? Maybe have a way of retrieving an initial rotation and position to be used for the frame before applying transforms? If it does need to be done automatically, we need a way to put in more information so that we can get desired results. Something like being able to specify that it should do things relative to the pelvis bone of the avatar rather than character or controller. Maybe a method such as SetRelative(Actor, Component, Bone, Socket);

    "artyom17" wrote:
    What I would like to have is the detailed description of the use cases when you can't achieve your goal using current Oculus plugin (the repro cases as UE projects would be even better). This will give us an idea how to approach the issue / limitation w/o introducing too much handles to create bad VR.


    The system I currently use welds the camera to a socket located at the eyes of the character model. No changes in rotation or location are ever applied directly to the camera. I use data from the rift as well as a series of conversions based on my own measurements(we need more measurements available in the user profiles) to drive animations on the character model such that the location of my eyes and the location of the character's camera match.

    I also plan to start work on some non-humanoid avatars (wolf, t-rex, etc.). Need lots of flexibility for those. I will probably have to do some weird conversions and non uniform scaling of data.

    I think these measurements would be very useful to have in the player profile.
    http://i.imgur.com/SQTpEiE.jpg

    These are possible setups I think people may settle on, similar things should apply to Prio VR and other alternatives to STEMs
    http://i.imgur.com/SQTpEiE.jpg
    I complain a lot. Just think of me as a squeaky wheel lol. Youtube channel -> https://www.youtube.com/user/xblBlackFang/videos
    Up and Coming
    November 20, 2014
    "BlackFang" wrote:
    "artyom17" wrote:

    You can use GetCurrentOrientationAndPosition function to get the CurrentPosition (which is a vector, offset from the "zero-position" (where the position was previously reset).


    Does that actually work now? The last time I took a look (I think this was back in 4.4) that function did not return meaningful values and I had to rewrite it.


    Well, it is hard for me to tell what exactly do you expect from that function and which values are meaningful for you. The GetCurrentOrientationAndPosition function returns current orientation and position offset from the zero point. It is used in, for example, CouchKnights demo (to change position of the body), so, it definitely works in this matter.
    How did you re-wrote it to make it work for you?

    "BlackFang" wrote:
    "artyom17" wrote:

    For example, if we do not update PlayerController orientation then objects will start disappearing, if you turn head left or right (since the engine thinks they are out of the player's view).


    This was easily fixed. I set the PlayerController orientation to that of the Camera instead of vice versa.


    And this is what happens when you set PlayerCameraManager.bFollowHmdOrientation to true.
    The positional change is not applied to the camera or PlayerController; instead, it is applied to ViewLocation at the calculation of stereo view offsets. I admit, you can't avoid this easily, need to think about this.

    "BlackFang" wrote:

    The system I currently use welds the camera to a socket located at the eyes of the character model. No changes in rotation or location are ever applied directly to the camera. I use data from the rift as well as a series of conversions based on my own measurements(we need more measurements available in the user profiles) to drive animations on the character model such that the location of my eyes and the location of the character's camera match.


    So, I think you are right and we should expose player's params, such as height, gender, etc (the ones available through OculusConfigTool). As to more measurements... Can't promise anything, but you always can have those params configurable through the game.
    As to your use case. If I understood correctly, you are driving your avatar by HMD (similar to CouchKnights?) and avatar's eyes-cameras are driven by the avatar? How does it work with timewarp and update-on-renderthread logic? Shouldn't it be opposite: your avatar follows the current orientation/position of the HMD?
    Up and Coming
    November 21, 2014
    I am having trouble getting accurate world space head tracking information. Going through the code, it appears that the head position tracking gets applied directly to the view matrix, rather than updating the camera position as in Unity.

    This makes it rather difficult to figure out where the eyes are, or tie behavior to head movement for things like raycasting, positioning of UI, etc. In my particular use case I want to be able to get and set the center-eye transform to snap the user's view to specific exact positions. Just moving the camera only puts the user's view somewhere near the point I specify, making for pretty sloppy control.
    Up and Coming
    November 21, 2014
    Last time I tried to use it, it had some comment lines and just returned 0,0,0 for the position. I haven't been coding for the last few months due to school, but it seems like it was fixed shortly after.

    "artyom17" wrote:

    And this is what happens when you set PlayerCameraManager.bFollowHmdOrientation to true.
    The positional change is not applied to the camera or PlayerController; instead, it is applied to ViewLocation at the calculation of stereo view offsets. I admit, you can't avoid this easily, need to think about this.


    "artyom17" wrote:

    So, I think you are right and we should expose player's params, such as height, gender, etc (the ones available through OculusConfigTool). As to more measurements... Can't promise anything, but you always can have those params configurable through the game.
    As to your use case. If I understood correctly, you are driving your avatar by HMD (similar to CouchKnights?) and avatar's eyes-cameras are driven by the avatar? How does it work with timewarp and update-on-renderthread logic? Shouldn't it be opposite: your avatar follows the current orientation/position of the HMD?


    The orientation of the avatar itself is completely independent of the HMD's rotation. The head and body can be oriented completely separately. (Razer Hydras control hands / arms)
    I initially tried to let Oculus drive the camera, and then drive the animations to match, but I could never get the camera to do what I wanted in that case. I couldn't get things to match up. My view orientation would act like it thought it was in world space instead of character space, or similar problems like the scale of the position data not being right. These were not exposed enough for me to adjust in the rift render updatey stuff, so I had to gut those functions completely.

    I think I'll download 4.6 and rewrite my project from scratch, see if I can come up with ideas for passing data into the render thread to ensure a match, rather than keeping the camera welded to a socket.
    I complain a lot. Just think of me as a squeaky wheel lol. Youtube channel -> https://www.youtube.com/user/xblBlackFang/videos
    Up and Coming
    November 22, 2014
    What is the intened use of ApplyHmdRotation?
    What is UpdatePlayerCameraRotation intended to do?

    Are both used, or is it one or the other?

    Are these intended to position the view correctly in world space?

    If I make modifications to the ApplyHMDRotation method, will timewarp and the render thread logic still work correctly?
    It calls GetCurrentPose, which has a comment that says it should only be called in the game thread.

    My plan is to have ApplyHMDRotation call a method in the PlayerController to do the math and position/rotate the camera correctly in world space. It can be overridden as needed by child classes. Will this work?
    I complain a lot. Just think of me as a squeaky wheel lol. Youtube channel -> https://www.youtube.com/user/xblBlackFang/videos
    Up and Coming
    November 23, 2014
    "artyom17" wrote:
    Seems to me, you should adjust your aiming by the current position of the HMD. You can use GetCurrentOrientationAndPosition function to get the CurrentPosition (which is a vector, offset from the "zero-position" (where the position was previously reset).


    I had attempted this the first time, but like Blackfang, was getting no useful positional data from GetCurrentOrientationAndPosition().

    After seeing this thread updated, I tried again using 4.6 and am happy to say, it now returns the positional data and I was able to remove it from camera location.

    That said, I wish I didn't have to.
    I'm fighting against the plugin rather than working with it :P
    Rule#21: Be polite, be professional, but have a plan to kill everyone you meet.
    Up and Coming
    November 23, 2014
    I got another question. Is the plugin trying to move the camera component, or is it altering the POV of the camera without changing the location of the camera component?
    I complain a lot. Just think of me as a squeaky wheel lol. Youtube channel -> https://www.youtube.com/user/xblBlackFang/videos