Search Unity

  1. Click here to see what's on sale for the "Best of Super Sale" on the Asset Store
    Dismiss Notice
  2. We are looking for feedback on the naming of a new user research platform that we are working on.
    Dismiss Notice
  3. Good news ✨ We have more Unite Now videos available for you to watch on-demand! Come check them out and ask our experts any questions!
    Dismiss Notice

Raycast from AnimationScriptPlayable Job

Discussion in 'Animation Previews' started by littlepolygon, Dec 3, 2019.

  1. littlepolygon

    littlepolygon

    Joined:
    Jul 7, 2013
    Posts:
    16
    I'm trying to write an animation job that performs foot-fixup against terrain as part of a PlayableGraph. However, both Physics.Raycast() and RaycastCommand.ScheduleBatch() complain about not being on the main thread.

    What's the correct way to raycast from the playable thread? If not, is there a way to synchronize with the main thread?

    For reference, here's the log produced by attempting to kick off a raycast batch through the job system, which I assumed with the idiomatic solution:

    Point of clarification: the foot location that we're querying-from is coming from the AnimationStream itself -- we're adjusting the incoming animation-pose with ik, so the position isn't known before the playable-graph kicks-off evaluation.
     
  2. AMNOD

    AMNOD

    Joined:
    Oct 19, 2014
    Posts:
    13
    Hey did you manage to make it work ?
     
  3. littlepolygon

    littlepolygon

    Joined:
    Jul 7, 2013
    Posts:
    16
    Not yet. I have some hacky workarounds (e.g. save/publish query position to main thread, perform raycast next-frame, apply previous-frames' result with some adjustments), but the results aren't ideal since there's a first-frame-pop and a frame-delay.

    Some folks on twitter pointed me at this megathread where people are discussing some of the more technical/experimental aspects of PlayableGraphs, alongside devs, so I x-posted there yesterday (fingers-crossed).
     
  4. DavidGeoffroy

    DavidGeoffroy

    Unity Technologies

    Joined:
    Sep 9, 2014
    Posts:
    332
    There is no way to do that, as you cannot schedule jobs from inside another job, access the main thread from a job, or access job data from another job.

    Here is a reasonable workaround, which is commonly used:
    Do your raycast before the job runs by approximating the foot position by using the previous frame position and velocity, along with the current frame deltaTime.

    As long as your animation is reasonably smooth (no pops), the result is pretty good. It's best when the foot is not moving much, which is where the player will have time to look at it anyway.

    In most cases, you should also be averaging or stabilizing your IK target position a bit, if you don't want your foot to repeatedly pop when it's right on the edge of a steep drop.

    Finally, you should store your raycast result position in character space (as opposed to world space), so that your foot doesn't point to a random spot in space if you ever teleport your character. (Well either that or disable IK for a frame when teleporting).
     
    florianhanke likes this.
  5. littlepolygon

    littlepolygon

    Joined:
    Jul 7, 2013
    Posts:
    16
    Yeah, as noted in my first reply, I've already implemented that workaround. The frame delay has mixed results. My next test is to precompute a "collision texture" of the ground-neighborhood that can be sampled during the animation job, which is looking promising, but still feels like extremely unnecessary and is a big liability both in terms of tuning, maintenance, and performance.

    Not scheduling jobs from other jobs is an impractical limitation. There's a whole class of useful cross-system integrations (animation/physics, animation/audiomix, etc) which we've implemented on Unreal at my dayjob which won't be portable to Unity. We don't need to access internal data, just results -- the idiom is akin to "goroutines": the parent job kicks off other jobs, suspend itself until they're finished, then gathers their results and resumes execution. Is there a venue for feature-requests where I could post this feedback?

    Sidebar: In practice only swimming animations are "reasonably smooth" (I would know, I wrote the animation controller for ABZU, lol) -- real animations are erratic by-design (animators want to emphasize key poses, not tweens).
     
  6. littlepolygon

    littlepolygon

    Joined:
    Jul 7, 2013
    Posts:
    16
    Alternatively, if a PlayableGraph is the level of abstraction to "compose jobs" then perhaps there can be a "RaycastPlayable" which could be interposed between, e.g., my AnimationMixerPlayable and my AnimationScriptPlayable?
     
unityunity