Search Unity

Official Unity Splines

Discussion in 'World Building' started by gabrielw_unity, Oct 5, 2022.

  1. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    2.0 and 2.1 are also compatible with 2021.3 as well, but you can't actually download them from the package manager in those versions.
     
    Aka_ToolBuddy likes this.
  2. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    @Rowlan "...having to find out everything by accident is terrible"

    Agreed heavily. For this, I keep pushing on the "Helper Bar" solution, which ought to land around 23.2. Would essentially be a dynamic bar (similar to Blender) with hints for mouse actions and modifiers. Would solve so many discovery issues :(

    Also, regarding a beta group for specific things like this - nothing official. Working on that too. It would be fantastic for us to have more and earlier testing and feedback.

    @jbooth "... the default is a line". Not if you change the Tool Option from "Linear on click" to "Auto-Smoothed on click" :)
     
    Rowlan likes this.
  3. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Speaking of feedback - if there are artists watching (sorry devs, not you :p ), we'd love to get your thoughts on the early components that were shipped in 2.x, also the new direct manipulation tools.

    Here's a fun thing I built in a few minutes with Splines and some hand-made props. Fun! spline-poly-fence-arrows.gif
     
  4. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
    Well as an artist, after less than 3 minutes of playing with it and pushing the buttons of its UI, it suddenly started spamming errors in the console, so not a great start.

    (edit: after playing around a bit more it seems it happens after you make the spline 3D, actually move a point up or down, then do a bunch of changes the type of the points)

    upload_2022-12-11_1-25-19.png
     
    Last edited: Dec 11, 2022
  5. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
    Auto behaviour is weird, the in-out tangent weights are of a fixed, really small length and that makes big splines look really sharp, I would have expected it to do something more advanced like take into account the distances of the next and previous point and adjust the weights accordingly or something?

    --

    Also there is a visual bug, if you rotate a point to something and then go back to auto, the spline line goes back to "normal" but the icon you have for the point stays rotated.

    --

    Trying to close a loop behaves weird. Here I haven't click yet, but I'm assuming the circle and the snapping indicates that if I click it will close the loop.

    upload_2022-12-11_1-36-7.png

    Instead I click and this happens

    upload_2022-12-11_1-36-36.png

    Maybe it wasn't indicating it would close the loop, but regardless, I don't know why it killed the first section of the spline, this can't be intended behaviour.

    --

    Spline Extrude threw errors, but it worked. I was expecting I could use two splines, one for the extrusion path and one for the profile (or a mesh for the profile?), but it seems the profile is always a circle? That really kills any usefulness the component might have.
     
    Last edited: Dec 11, 2022
  6. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
    Finally, this example here looks kinda cool, you look at the gif and imagine the possibilities, but there are no other possibilities, there isn't anything more to it.

    You could imagine having a variety of offset distributions (with math, or with a curve? So you can have stuff like most objects being towards the center and only a few going further away) nope, just a random range.

    You could imagine being able to add some of the offset data / parameters to the spline itself, so you can have certain points have more offset, or more items / density, or anything, nope, can't be done.

    You could imagine more intelligent placement that takes into account the bounding box size of the mesh (or it could be user input?) so that when placing a big item on the spline, there are no other items placed close to it to avoid meshes overlapping. No such thing exists. (notice on the gif every item needs roughly the same area, it would look like a mess with big differences in size)

    Then, I tried adding another spline with instantiated objects to be spline instantiated, in order to make something more complicated, and Unity crashed.

    All in all, my artist opinion for the whole package, if a tech artist came and presented this to me, I would say "cool proof of concept, please go ahead and make it an actual feature".
     
    Last edited: Dec 11, 2022
  7. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    It is on auto-smoothed, it still creates lines unless you click, hold for some amount of time, and drag out the tangent. The options are also only available in 2022, and the only options are "Linear and Auto Smooth". There is no option for "on click" that I can find.



    Further, when moving a spline knot (that doesn't jump to linear on touch, which seems to happen more on splines created in previous versions), it doesn't adjust the tangents to create a smooth curve.



    Note this was set to continuous, and that does not look like a continuous curve to me, rather the tangents are close to 0 in length and create a nearly linear interpolation. In the old system, when you dragged a spline point around, it kept a smooth continuous curve instead of basically turning into a linear interpolation with a tiny bevel on the edge.

    Also note how hard it is to see splines in real, textured art. All of your demo scenes are using low poly/flat shaded graphics which make it easy to see the splines. I shouldn't have to adjust my camera's clipping planes every time I want to adjust a spline.
     
  8. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    Yeah, realizing that Unity has a lot of 3d content in it and using it as such would suss a lot of problems out. The demo's are all too simple and on flat planes, etc. Here's what happens when you try to use spline instantiate in a real level:




    It's literally impossible to adjust the spline rotation to property align with anything but a perfectly flat plane with a perfectly flat spline (like in every demo). So it's really only useful for 2d games, where the spline gets no twist and the level doesn't change organically in shape. I was hoping to benefit from unity having written a lot of these tools, but I'm going to have to rewrite most of them anyway, the ones in examples as well as the ones in the actual spline package, because none of them are usable outside of a demo context.
     
  9. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Send bug reports please! :)

    Yeah, team is looking at this now. There's something incorrect or at least not ideal.

    Oh, that's very much a bug too. Well, sort of. This is a case where "expected result" could be multiple things:
    - I expect the point's tangents to become "Auto" ... and also discard the rotation of the point that I previously chose, setting the rotation back in line with the forward tangent
    - Or, I expect the points tangent to become "Auto" ... but keep the rotation that I chose, it was important!

    I'll take a further look at this, for sure.

    Sorry, I'm not totally following - can't tell how that result would happen. So probably a bug yes. Just in case, could you make a gif for me?

    1) Could you log the bug? Thanks!
    2) Yup, it only does a circular mesh. These components aren't intended for more than basic use, as Splines is designed as a foundation for others to build on.

    Yup, same as above on the circle-only extrude. I feel your pain wishing for more, but this simplicity is the intent, for now at least. Splines has a first goal of finally creating a common ground for everyone to build on. That itself is still in progress, as we take the feedback here and iterate.

    Ah, so "click, hold, drag" doesn't create auto-smoothed, it creates a "manually smoothed" bezier point. Dragging sets those tangents, and then you can manipulate them as needed. Is this what you'd like to appear on-click? What would you expect for tangent length and direction? Could certainly be made an option!

    Also, to clarify, the "on click" isn't part of the UI, I was just attempting to explain the linear vs auto smooth options, sorry for confusion :)

    Well, it's certainly very tedious and painstaking, yup. I think some sort of "project from the Spline I draw, onto X surface/layers/etc, and form the path there" might be necessary. That could be very game specific ... but, similar to the instantiate/animate/extrude components, it would be great if we could at least provide a basic version. Curious if you have solution ideas in mind?
     
  10. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
    Nah, I'm sorry, I have a policy of not submitting bugs for things that are not super critical to me.
    Sure.

    splines.gif

    Can't even tell what is the intended behaviour here. From the Unity Japan video I think it's supposed to close the spline loop, but not sure what it's doing here. It works more predictably in Linear mode.
    1. Nope, sorry see above.

    2. If Unity Splines is a foundation for tech artists / programmers to create something with it, then don't ask for feedback from artists.

    If the supplied features are actually "starter scripts" for tech artists and programmers to build upon, that's fine, but if it's supposed to be useful to artists as-is, then it is extremely limiting.

    And frankly, if I'm having a tech artist / programmer to make tools for me, he might as well write the spline code as well, so we can have complete control of the code and not have it break by Unity updates.

    (or just use something like this as a starting point? seems a lot more robust: https://github.com/vvrvvd/Unity-Spline-Editor )

    So if this is to be useful, it needs to do a lot more out of the box, so I can do a lot of the stuff I want easily, and then it would make sense to have a programmer extend it for more exotic functionality that I might want.

    As it is now, it is giving me way too little for the cost of depending on code I don't own.
     
    teutonicus likes this.
  11. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    I'd like a mode where it works like it worked in the 2.0 version, where you can click 5 points and get a curve instead of a bunch of lines. I don't want to fuss with the tangents on every click, because usually I haven't added the data to the spline yet that's going to make me know which tangents need to be adjusted (ie: it modifying the terrain, road lofting, whatever).

    Also, in the 2.0 version it would try to be smart and guess if I wanted a line or not based on the angle between the old bezier and the new- don't do that, it was always wrong, and I'd have to go back and make everything smooth again. If a tool can't get it right 95% of the time, it's usually wiser to make the tool dumb so it's predictable to the user.

    I'd add an option called "raycast for ground", which uses the batch raycast API to cast down from a user definable tolerance distance above the spline and finds the collision point below it and moves the object there. Add a layer filter while you're at it, as well as an align to normal option so things can be aligned to the terrain slope as well. This would make the whole system a ton more useful, and with the layer and tolerance options you can work around most issues you'd have in 3d.
     
    graskovi, JesOb and Lars-Steenhoff like this.
  12. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    Yeah, it feels like this decision wasn't really made on who the audience was. I've heard it both ways - the first version was for artists and that's why the API is not cleaned up, and now this is for extensibility and so the art tools are just example code. They can't both be correct unless neither of them is correct.

    If it's for artists, then everything needs to be a lot more robust and all the test cases should be designed on complex environments, not flat planes. It should come with components to do a lot of things, not a few that are 75% complete, and a bunch more that are 25% complete.

    If it's for coders and asset store publishers to extend, then the interface to extend it should be a lot more robust.

    Check out this example:



    Notice I have two width controls on the interface - Why? Well because Unity has the concept of width in it's loft example, but I can't use that externally, so I'm forced to have my own version of the width control. So now, in theory, I could have control points for the width of the road, but also control points for the width of the texture change I want around the spline.

    Maybe I want separate controls for these, but usually not. And the joy of having to line them up and keep them in sync is just delightful - that or keeping two separate splines in sync. This doesn't even get into all the issues with trying to make SplineData<T> robust, which is currently a mess of private classes we're not allowed to use and data breaking issues.
     
    AcidArrow likes this.
  13. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Hmm, sounds like the AutoSmooth is there, but not doing a good job. Sorry about that - I think I mentioned elsewhere, we're looking into that option in general, good timing, I'll add this to the list - thanks for the details!

    Hmm, I don't think we had any smarts for that. Maybe it just appeared to do so? Agreed that "dumb but predictable" is usually the best.

    Hmm, yeah, this is what I had in mind for Instantiate, but I was thinking more that perhaps this should be an option on the Spline itself. So any system using the Spline, would get a nice terrain/whatever aligned path. Anyway, definite yes on a layer filter and align to normal option. Thanks!
     
    hkalterkait, JesOb and Rowlan like this.
  14. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    Wouldn't this require creating a ton of knots though? You could end up with one per pixel on the terrain.

    In MicroVerse, the usual way things work is that the thing interpreting the spline either ignores the spline height and projects stuff downwards (texturing, spawning), or forces the terrain to conform to the spline (height modifications).

    This seems like a better way to approach it than adding hundreds of knots to the spline, since each thing interpreting the spline can decide what to do with the data. Otherwise you end up with an impossible to edit mess of hundred of closely clustered knots, which will need to be recreated from scratch every time anything changes with the underlying surface.. So yeah, placing things on the surface seems like a job for the Instantiate script, not the spline itself.
     
    gabrielw_unity likes this.
  15. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    Perhaps you mean in interpolation positions along a spline functions? That's interesting, but I don't think it would work out that well, since the spline would be lying about it's actual position, and you'd sometimes want access to the correct position, and you'd also be inserting raycasts into something which is already expensive without much context about how that data is used.

    BTW, I replaced the functions used for computing the positions of a spline in the .cginc file with some custom ones and saw a massive speedup. I do a simpler lookup to find the t value range I need, then do a fine pass to get a more acurate value, rather than brute forcing over a spline with 1000 iterations to get the closest point.

    (I convert most of the splines used in MV into SDF textures so I can sample 'distance from spline' and the spline's position in a single texture sample - makes it really easy to do things contextually vs. splines on the GPU).
     
    gabrielw_unity likes this.
  16. imaginaryhuman

    imaginaryhuman

    Joined:
    Mar 21, 2010
    Posts:
    5,834
    1) How is the 'split' supposed to work? Because all I see happening is that it seems like all the knots up to the selected knot, from the start, get split. I was assuming that I should select a knot and click split and that it would basically 'insert' a new knot in between the two, is that not what it's supposed to do? Because it doesn't seem to be doing it. Can you make it easier to split a spline like double-clicking on a spline between two points or something, or is there some modifier key or something which inserts knots in between existing knots?

    2) Could you add an option in terms of animation timing, whereby there is like a rate of 'knots per second', or relative time, so e.g. when knots are closer together the object moves slower, and when knots are further apart the object accelerates. Therefore a person could determine the movement speed on a per-knot basis by deciding how close together to place the knots.

    3) Would be useful to be able to visualize the position/rotation of an object in an animation clip, whereby the splines in the clip are tied into a visual spline in the scene view, so that you can do wisywig editing of the ACTUAL path instead of the split-out components of the path - which are very hard to visualize. Editing the spline in the scene view should instantly update the animation clip and vice versa. And somehow the object's rotation should be visualized as well. It's far easier to design actual paths in the scene than fiddling with separate x/y/z splines in the animation clip window.

    4) How are you supposed to draw new spline points which are very CLOSE to an existing point? Because it seems there is a radius that, when the mouse is close enough to the existing knot, it will not add a new knot - you are forced to have to be a certain distance away in order to place a new knot. I want to sometimes place knots that are very close together (related to #2), how can I do that, is there an adjustment for the closeness to the existing point or something - without having to zoom in a lot?

    5) How do you set the default knot type, e.g. to linear rather than auto, so that when you start drawing it is in the mode you want?

    6) When you create a spline using a method other than the 'drawing' tool, it was a bit confusing as to how to get TO the ability to draw or modify that spline. You explained it in your blog post better than in the documentation.

    7) I would like a mode where, as the mouse is moved, multiple spline knots are recorded e.g. at 60fps or 30fps perhaps, so that the movements of the mouse records a whole stream of knots as the mouse moves. Perhaps with a modifier key or something to do a rapid-fire automated mouse click sequence. This makes it very very fast for designing a rough-draft of a complex spline which otherwise takes a ton of mouse clicks. And also per #2 the closeness together of given knots and per #4 allowing knots very close together, allows the user to 'perform' a recording which captures the nuances of the hand motion and speed as part of the spline and its playback. Think of it like 'freehand' drawing, you can just draw a really complex spline very fast with a single click.
     
    Last edited: Dec 12, 2022
    gabrielw_unity likes this.
  17. Rowlan

    Rowlan

    Joined:
    Aug 4, 2016
    Posts:
    4,295
    Novack and gabrielw_unity like this.
  18. Rowlan

    Rowlan

    Joined:
    Aug 4, 2016
    Posts:
    4,295
    @gabrielw_unity Where can I add an official feature request? I still need access to the selection api. I need to select a start and end knot and subdivide or unsubdivide the selected segment. Or just jiggle the knots inbetween around. Or align the selected ones to the y position of a terrain and such. But the core is: Access to the selection api :)
     
    gabrielw_unity likes this.
  19. evyatron

    evyatron

    Joined:
    Jul 20, 2014
    Posts:
    132
    A bit of general feedback - although I very much appreciate finally having a native Spline solution in Unity, I think the shipped components need to be more extensive:
    1. Allow extruding of actual meshes along a spline
    2. The current Extrude should support more than a cylinder - at least a plane and a cube.
    3. Make creating a custom "generator" easier. A base class you can extend from, and you get a Generate method that tells your code to do redo whatever it does. I imagine the Extrude and Instantiate using it as well. That way extending it by coders will be much easier. (Just using the Spline Updated is not good enough, it doesn't fully track changing splines)
     
  20. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    You are correct, that seems much better! In that case I wonder if this ability would be best built into the component doing the spawning/painting/terrain height. We've built/seen examples in this way, does work well :)

    That sounds interesting, but over my head :p I'll drop it by the team!
     
  21. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Split will take the selected knot, and break it into two. I can see the reason for confusion though! We do have a ticket (backlog) for an action to "divide this segment into 2 equal segments" :)

    We could, but in all honesty probably won't (soon), sorry :( The components are only meant to be basic starters, to give an idea of what Splines can be used for. Plans upon plans for doing much more with them (and additional ones), but we've set our goals here for now. I do expect the Asset Store, etc will pick up very quickly though!

    YES, and actually I remember a co-worker even did something like this which was visible and editable in VR ... very cool stuff. Out of our scope for now though, unfortunately. (Our scope - ensure a consistent UX foundation for scene tooling ... quite a bit to do there still!)

    Hmm, sure ... that's an easy and useful modifier to add. I'll check on it. Something like "hold SHIFT and the only result will be adding points ... ".

    Via the Tool Settings Overlay, change the drop-down option from "Auto" to "Linear". One note though ... I think there is currently a bug where even tiny movement will result in bezier, vs it should really give more time/distance to stay as a "click".

    Good news is, we've already prototyped this, for a non-destructive painting tool! It's certainly doable and has really useful results. Bad news ... you guessed it ... it's not priority for now though I expect Environment work will bump that up, might the another team implementing it ( ... and you know I'll be pushing hard on them to make it generic, so everyone can benefit!).

    Worth noting here also ... I'm fairly certain most of these could be built or added on via Asset Store developers (or just raw custom). That's good and bad ... we really want to support the AS economy, but recognize this means artists need one more thing to buy. We're doing our best to tackle the crucial bits!
     
  22. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Hey, thanks for sharing, and glad you liked the gifs!! :)

    This has been in a few discussions, thanks to your (and others) poking at it! Thanks for that :) It's apparently not trivial within the constraints ... I'll check in again :)
     
  23. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Thanks, happy the overall native solution is appreciated!
    As a general answer, we took those components as far as time allowed (and actually a bit further, they were part of why we delayed a bit). It's unlikely we'll be adding more in the near future ... but always open to suggestions, thanks!!

    Extruding meshes - yes indeed, we all wanted this as well. Top contender when time allows!
    More than cylinder - we even have designs for this (I mean, all of a few lines in the inspector). Another top item. Simple enough that if lucky, it could drop in earlier.
    Generator - I'll need more info on this ... and then I'll pass it to the devs! Sorry, my technical knowledge drops off there :D

    Thanks again!
     
    Lars-Steenhoff likes this.
  24. Rowlan

    Rowlan

    Joined:
    Aug 4, 2016
    Posts:
    4,295
    It's really an important thing. The splines are really good, but you guys seem to have focused on the manual editing, what's missing is the procedural stuff. Like I did here:


    I prefer automatic level creation with fine adjustment on the manual part. Without API that's just too limited when there can easily come more from the community.
     
  25. gabrielw_unity

    gabrielw_unity

    Unity Technologies

    Joined:
    Feb 19, 2018
    Posts:
    963
    Hey @Rowlan ! :)
    So, yes devs confirmed - it's a very non-trivial thing. It's on the radar. Nothing I can confirm now though, sorry.
     
    Rowlan and Lars-Steenhoff like this.
  26. evyatron

    evyatron

    Joined:
    Jul 20, 2014
    Posts:
    132
    I won't write actual code here, but the idea is to give users an easy way to create new spline "generators" or spline "users". For example, if you want to write a Cinemachine Extension, you override from CinemachineExtension class and get:
    Code (CSharp):
    1. public class CinemachineExtensionExample : CinemachineExtension
    2. {
    3.     protected override void PostPipelineStageCallback( CinemachineVirtualCameraBase vcam, CinemachineCore.Stage stage, ref CameraState state, float deltaTime )
    4.     {
    5.      
    6.     }
    7. }
    A class which is ready to use, and gets called with the relevant information at the right time.

    I think having something similar for Splines would be super handy (in fact, whenever I use any spline solution I do just that - I even did it for Unity's splines!)
    Code (CSharp):
    1. public class SplineComponentExample : SplineComponent
    2. {
    3.     protected override void Generate( Spline spline )
    4.     {
    5.  
    6.     }
    7. }
    So in this example the base class SplineComponent will be provided by Unity. By having something like this, which guarantees that Generate gets called correctly (whenever the spline changes, or whenever the underlying spline of a spline container changes), as well as having access to any required utility functionality, you make it much easier for other people to extend functionality!
    (You currently use SplineComponent for a couple of your examples, but it doesn't really provide the needed functionality)
     
  27. Rowlan

    Rowlan

    Joined:
    Aug 4, 2016
    Posts:
    4,295
    It would already help to just get the currently selected knots on demand. No event handling or sth. I'd invoke my code on those. That certainly should be possible with a dedicated method and without conflicting anywhere.
     
  28. m_agostini

    m_agostini

    Joined:
    May 26, 2022
    Posts:
    1
    Hi, Is there any way for limit GetNearestPoint within a segments range? I'm using the version 1.0.1 and I see in the api that there are already some similar functions but are private...
    Thanks
     
  29. mgear

    mgear

    Joined:
    Aug 3, 2010
    Posts:
    9,440
    having invert extruded spline option would be nice! (to make tubes with inner surface) or 2 sided spline mesh also.
     
  30. alkaitagi

    alkaitagi

    Joined:
    Dec 8, 2016
    Posts:
    87
    Hi, thanks for the cool package. Been playing with it and I need help with the API.

    Is there a straightforward way to get all the links within a spline container? I see
    SplineContainer.KnotLinkCollection.GetKnotLinks
    , but with it I need to manually go through every knot and check it for links. That doesn't seem right.
     
  31. ManuelRauber

    ManuelRauber

    Joined:
    Apr 3, 2015
    Posts:
    122
    I'm also struggling a bit with the API, especially SplineSlice and SplinePath.

    My use case is the following:

    upload_2022-12-22_15-15-51.png

    I have a spawn point (bottom left) and an end point (top right). I have one SplineContainer with 2 Splines in it.
    The first spline is from start to end and the second spline is from crossing to crossing. The knots at the crossings are linked.
    I can also have multiple ways and crossings where splines are linked together.

    What I want to right know is to start at the start point and then build a path from start to end where the character randomly chooses a knot link to follow and maybe merge back into another spline. However, the character will always go "forward" in a spline.

    I hope that's somehow understandable. :)

    Using the current API, I've build a little algorithm to do that.

    The final piece boils down to this here:

    Code (CSharp):
    1. private void Awake()
    2. {
    3.     _splinePath = CreateRandomPath(Container);
    4.     _spline = new(_splinePath);
    5. }
    6.  
    7. private void Update()
    8. {
    9.     Progress += Time.deltaTime * Speed;
    10.  
    11.     var position = Container.EvaluatePosition(_spline, Progress);
    12.     transform.position = position;
    13.  
    14.     if (Progress > 1)
    15.     {
    16.         Destroy(gameObject);
    17.     }
    18. }
    My question is regarding Container (which is ISplineContainer) and the EvaluatePosition.

    First, take a look at the Awake. There is a method CreateRandomPath that walks through the spline container and stitches together some segments as described above.

    The following output is created:

    Screenshot 2022-12-22 at 17.09.38.png

    As I understand from the documentation, SplineSlice says the following:

    However, if you take a look Container.Evaluate, I get complete different visual results when I evaluate _spline vs _splinePath.

    From my understand and the docs, it should be the same, shouldn't it?

    Here is a video with the evaluation of the SplinePath (with the knots from above's images):


    And here is a video with the evaluation of a Spline constructed from the SplinePath as above:


    For the sake of completeness, here is the prototype algorithm for creation:

    Code (CSharp):
    1. // Prototype code, does not check for any lengths and stuff. :)
    2. // We assume that Spline[0] is the main spline that has the start and absolute end knot.
    3. private SplinePath CreateRandomPath(ISplineContainer container)
    4. {
    5.     var pathSlices = new List<SplineSlice<Spline>>();
    6.  
    7.     var endKnot = container.Splines[0].Last();
    8.  
    9.     var splineIndex = 0;
    10.     var knotIndex = 0;
    11.     BezierKnot endKnotInCurrentSlice;
    12.  
    13.     var maxIteration = 1000;
    14.     var currentIteration = 0;
    15.  
    16.     do
    17.     {
    18.         var traverseResult = TraverseToNextKnotLink(container, splineIndex, knotIndex);
    19.         pathSlices.Add(traverseResult.SplineSlice);
    20.         knotIndex = traverseResult.SplineSlice.Range.End + 1;
    21.  
    22.         if (traverseResult.LinkedKnots is { } linkedKnots)
    23.         {
    24.             // We have linkedKnots, so check for candidates that allow further traversal.
    25.             // The "+1" ensures we have at least one more knot to traverse
    26.             var candidates = linkedKnots
    27.                 .Where(linkedKnot => IsValidKnotIndex(Container.Splines[linkedKnot.Spline], linkedKnot.Knot + 1))
    28.                 .ToArray();
    29.  
    30.             if (candidates.Length != 0)
    31.             {
    32.                 var candidate = candidates[Random.Range(0, candidates.Length)];
    33.  
    34.                 splineIndex = candidate.Spline;
    35.                 knotIndex = candidate.Knot + 1;
    36.             }
    37.         }
    38.  
    39.         currentIteration++;
    40.         endKnotInCurrentSlice = traverseResult.SplineSlice.Spline[traverseResult.SplineSlice.Range.End];
    41.     } while (!endKnotInCurrentSlice.Equals(endKnot) && currentIteration < maxIteration);
    42.  
    43.     if (currentIteration >= maxIteration)
    44.     {
    45.         Debug.LogWarning("Something is wrong :)");
    46.     }
    47.  
    48.     return new(pathSlices);
    49. }
    50.  
    51. private bool IsValidKnotIndex(ISpline spline, int knotIndex) => knotIndex >= 0 && knotIndex < spline.Count;
    52.  
    53. private (SplineSlice<Spline> SplineSlice, IReadOnlyList<SplineKnotIndex> LinkedKnots) TraverseToNextKnotLink(
    54.     ISplineContainer container, int splineIndex, int startKnotIndex)
    55. {
    56.     var spline = container.Splines[splineIndex];
    57.     var links = container.KnotLinkCollection;
    58.  
    59.     var knotIndex = startKnotIndex;
    60.     IReadOnlyList<SplineKnotIndex> linkedKnots = null;
    61.  
    62.     while (knotIndex < spline.Count)
    63.     {
    64.         if (links.TryGetKnotLinks(new(splineIndex, knotIndex), out linkedKnots))
    65.         {
    66.             knotIndex++;
    67.             break;
    68.         }
    69.  
    70.         knotIndex++;
    71.     }
    72.  
    73.     return (
    74.         new(spline, new(startKnotIndex, knotIndex - startKnotIndex)),
    75.         linkedKnots
    76.     );
    77. }
     
  32. Zephus

    Zephus

    Joined:
    May 25, 2015
    Posts:
    356
    Is it just me or is there absolutely nothing on the actual scripting part in the manual? I just installed the package, made a curve and now I just want to move an object along the curve in script. How is it that I'm not able to find anything on that in the documentation? I was kind of under the impression that was the main purpose of the package.

    Maybe it's really simple, but the main point I'm making - the documentation only seems to describe how to create splines. But there's pretty much nothing on how to actually use them.
     
    JamesArndt and PutridEx like this.
  33. shikhrr

    shikhrr

    Joined:
    Nov 19, 2013
    Posts:
    68
    Yeah
     
  34. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
  35. Zephus

    Zephus

    Joined:
    May 25, 2015
    Posts:
    356
    I'm aware of the Scripting API, but I'm talking about a manual. I was hoping for some kind of tutorial on how to use these things. It's frankly kind of annoying to read through these dozens of different classes and still not know what the best way to use them is. I think packages like these just need better manuals or tutorial videos.
     
    tomkail_betterup likes this.
  36. ElSheriff

    ElSheriff

    Joined:
    Apr 12, 2014
    Posts:
    9
    Hello,
    I would like to provide an array of Vectror3 points and would like to generate a spline from there. As the position of the points are variable.

    Reading through the SplineContainer script a Spline takes a list of BezierKnot.
    Verified Here: https://docs.unity3d.com/Packages/com.unity.splines@2.1/api/UnityEngine.Splines.Spline.html

    For Scripting I am trying:

    Code (CSharp):
    1. using UnityEngine.Splines;
    2.  
    3. ...
    4. public class SplineTest : MonoBehaviour
    5. ...
    6. Vector3 pos = New Vector3(0,1,2);
    7. BezierKnot bezierKnot = BezierKnot(pos);
    8. Spline spline = Spline(bezierKnot );
    9.  
    10.  
    I get error of `Non-invocable member 'BezierKnot' cannot be used like a method.` Same with Spline

    My use case is the following:
    - Create a Spline Object from an array of points
    These points will change, resulting in a different spline drawn for each use case
     
  37. AcidArrow

    AcidArrow

    Joined:
    May 20, 2010
    Posts:
    11,791
    Ah, yeah, the scripting docs for packages are way too dry, yes.
     
  38. joshrs926

    joshrs926

    Joined:
    Jan 31, 2021
    Posts:
    115
    Bézier curves cannot represent a circle exactly. What you see in the pic is as close as they can get.
     
  39. wilgieseler

    wilgieseler

    Joined:
    Oct 17, 2013
    Posts:
    84
    Can someone explain the proper API to update a spline in an editor script? This does not seem to work and there is, as usual, no meaningful documentation and a confusing API.

    Here's what I've tried:

    Code (CSharp):
    1.     [MenuItem("Tools/Snap Spline Knots to Ground")]
    2.     public static void SnapSplineToGround() {
    3.         var container = Selection.activeGameObject.GetComponent<UnityEngine.Splines.SplineContainer>();
    4.         container.Splines = container.Splines.Select(spline => {
    5.             var knots = spline.ToArray();
    6.             for (var i = 0; i < knots.Length; i++) {
    7.                 var knot = knots[i];
    8.                 var transform = new UnscaledTransform(knot.Position, knot.Rotation);
    9.                 GroundedLevelObject.SnapToGround(transform, null, true);
    10.                 var newKnot = knot;
    11.                 newKnot.Position = transform.Position;
    12.                 newKnot.Rotation = transform.Rotation;
    13.                 spline.SetKnot(i, newKnot);
    14.             }
    15.             return spline;
    16.         }).ToList();
    17.     }
    18.  
    The specifics aren't important, just need to figure out how to get the spline to update. The code runs, but nothing happens.

    Also, the documentation indicates the spline subscript
    Code (CSharp):
    1. spline[i]
    is a setter, but it isn't actually a setter.

    Also, I cannot for the life of me figure out how to add a new knot to a spline in the UI. I've been using the stupid + button in the inspector. The documentation does not explain this.
     
  40. Kubinna

    Kubinna

    Joined:
    Apr 19, 2015
    Posts:
    18
    @gabrielw_unity

    Hello,

    I am using Splines package in my 2D game. My goal is to create spline which is describing movement of player. Spline will be created runtime in game via code. Player movement is saved in list, which is containing float3 positions. For spline creation I am using SplineUtility.FitSplineToPoints function and SplineMesh.Extrude function for creating mesh.

    My problem is, that in some points is spline twisted and I don´t know why... Is there any possibility how to remove this twisted parts?

    My code is:
    Code (CSharp):
    1.  List<float3> line_data;      // player path
    2. SplineContainer spl = lineObject.GetComponent<SplineContainer>();       // reference to spline on object
    3. UnityEngine.Splines.Spline spline = new UnityEngine.Splines.Spline();       // variable to which will be created spline saved
    4.  
    5. bool error = SplineUtility.FitSplineToPoints(line_Data_float3, 0.01f, false, out spline);       // computing spline
    6. spl.Spline = spline;        // saving created spline to spline component
    7.        
    8. Mesh lineMesh = new Mesh();     // creating new mesh
    9. float length = spline.GetLength();
    10. int segments = (int)(200 * length);     // calculation from example
    11.  
    12. SplineMesh.Extrude(spline, lineMesh, 0.1f, 1, segments, true, new float2(0f, 1));       // creating mesh
    13. lineObject.GetComponent<MeshFilter>().sharedMesh = lineMesh;        // saving mesh
    Problem looks like this:
    In shadded and wireframe mode:
    twisted.png

    Points in spline:

    twisted2.png

    Selected point info:

    twisted3.png

    Thank you very much for help!! :)
     
  41. kaarrrllll

    kaarrrllll

    Unity Technologies

    Joined:
    Aug 24, 2017
    Posts:
    552
    @wilgieseler this code works for me. Make sure you're using a 2.0+ version of the Splines package.

    Code (CSharp):
    1. using System.Linq;
    2. using UnityEditor;
    3. using UnityEngine.Splines;
    4.  
    5. class SnapSpline
    6. {
    7.     [MenuItem("Tools/Snap Spline Knots to Ground")]
    8.     public static void SnapSplineToGround()
    9.     {
    10.         var container = Selection.activeGameObject.GetComponent<SplineContainer>();
    11.         container.Splines = container.Splines.Select(spline =>
    12.         {
    13.             for (int i = 0, c = spline.Count; i < c; i++)
    14.             {
    15.                 var knot = spline[i];
    16.                 knot.Position.y = 0f;
    17.                 spline[i] = knot;
    18.             }
    19.  
    20.             return spline;
    21.         }).ToList();
    22.     }
    23. }
     
  42. kaarrrllll

    kaarrrllll

    Unity Technologies

    Joined:
    Aug 24, 2017
    Posts:
    552
    @Kubinna it looks like this was fixed in 2.1.0:
    • [STO-2680] Fixed a bug where `SplineMesh.Extrude` would create twisted mesh geometry.

     
  43. kaarrrllll

    kaarrrllll

    Unity Technologies

    Joined:
    Aug 24, 2017
    Posts:
    552
    Most of this will be in the scripting API, or Samples code. A good quick-start can be found in Spline Samples/Runtime/SplineCommonAPI.cs
     
  44. Kubinna

    Kubinna

    Joined:
    Apr 19, 2015
    Posts:
    18
    Hello,

    first off all thank you for your reply. I forgot to mention, that I am using version 2.1.0. I tested this problem and found that the problem occurs already when spline is created. If the move spline tool is active and I move it on created spline, the blue wheel rotates. This can be seen in the attached gif.

    problem.gif
     
  45. tomkail_betterup

    tomkail_betterup

    Joined:
    Nov 17, 2021
    Posts:
    106
    Hi! Finally checking this tool out. It's wonderful - we're really impressed.

    The API appears to be really well thought out, and easy to use.
    The editor, too, appears to be simple and powerful.

    As has been mentioned by another poster, the X key conflicts with another default editor shortcut.

    I realise I don't really understand how Unity operates internally, but really hope you continue to actively support this after V2.1. I've seen far too many promising Unity tools fail to get the dev support they need and end up becoming either too limited, unfinished or broken. It seems reasonably feature complete, but I really hope this doesn't get left out in the cold.

    Relatedly, please make time to build quality tutorials before you move on! I know it takes a lot of time for you but it costs the developer community so much more when it's left out. I'd always rather a google search takes me to a well built official page than a bunch of youtube and blog links.

    And finally, a question on extendability: lets say we wanted to build a spline where each knot contained additional info - perhaps "speed", "width" or "color". How would we go about this? Ideally we'd have an extended version of BezierKnot but that's not possible (AFAIK). I see there's a Spline.Changed event - would we have a separate list of structs that mirrors the spline?
     
    gabrielw_unity and Shizola like this.
  46. kaarrrllll

    kaarrrllll

    Unity Technologies

    Joined:
    Aug 24, 2017
    Posts:
    552
    That looks like a probable bug to me, but it's difficult to say without the full context. If you would like, please file a bug report with a reproduce-able case and I will investigate further.

    @tomkail_betterup regarding tutorials, are there any topics in particular you'd like to see explored? We have a good selection of Sample scenes and code in the package available for install in the Package Manager, but I agree that a good tutorial is a great way to get started from scratch. Would you be more interested in working with Splines in the Editor, or code?

    This was fixed on the editor side recently, we allowed for more specific shortcut contexts to override global shortcuts. However it does need to be addressed in earlier versions of Unity, thanks for pointing this out.

    Our splines do not embed data in knots through inheritance, but instead use the SplineData<T> collection type to associate generic data with splines. Check out https://docs.unity3d.com/Packages/com.unity.splines@2.1/api/UnityEngine.Splines.SplineData-1.html for more information.
     
  47. filod

    filod

    Joined:
    Oct 3, 2015
    Posts:
    224
    Any plans to support DOTS/Subscene Workflow ?
     
    Deleted User likes this.
  48. metaphysician

    metaphysician

    Joined:
    May 29, 2012
    Posts:
    190
    i just ran into this exact situation and i'm on 2021.3.11 LTS. is there any way to download those version without using Package Manager? from Github maybe?
     
  49. jbooth

    jbooth

    Joined:
    Jan 6, 2014
    Posts:
    5,461
    You can actually download them via the PM, they just don't show up in the menu. Open the PM and click the plus on the top left and select "install by name" and put "com.unity.splines" into the dialog.
     
  50. bfoddy

    bfoddy

    Joined:
    Mar 27, 2012
    Posts:
    85
    It'd be really cool if the documentation gave the tiniest clue how you can get a position or tangent at a given position along a spline.

    The manual just doesn't reference this at all, it just tells you how to edit the splines in editor.

    Meanwhile the API doc just doesn't provide any clues at all about how to achieve that most basic of workflows. So it's either a case of 'read every class and method in alphabetical order' or else trawling through the sample code and trying to crossreference. It shouldn't be this way!
     
    Last edited: Jan 17, 2023