1
$\begingroup$

I generated a bunch of points using mathutils.geometry.interpolate_bezier() but noticed the points are not uniformly distributed on the curve. Please see attached screenshot.

I think it has to do with the interpolation function processing each segment individually which can be dense or sparse depending on how stretched the segment is.

Is there is a better way to interpolate bezier curve and obtain a list of uniformly distributed points?

Thanks! enter image description here

$\endgroup$
6
  • 1
    $\begingroup$ Related blender.stackexchange.com/questions/47359/… $\endgroup$ Oct 30, 2017 at 2:28
  • $\begingroup$ This may help : a primer on Bézier curves $\endgroup$
    – dr. Sybren
    Oct 30, 2017 at 13:48
  • 1
    $\begingroup$ @John, Bezier curves are evaluated on a non space based paramter (sometiems called 't'). You can think of it as time, and moving along the curve at different speeds. They way I work around this is that I evaluate the enture curve at small t steps, then re-evaluate/interpolate my points to space them evenly along the evaluated curve. $\endgroup$
    – patmo141
    Feb 25, 2018 at 16:10
  • $\begingroup$ github.com/patmo141/odc_public/blob/… $\endgroup$
    – patmo141
    Feb 25, 2018 at 16:11
  • $\begingroup$ @patmo141 Clever. But I end up converting to mesh and subdividing it to generate enough vertices. I thought that is what you did in your code too. Anyways Thanks $\endgroup$
    – John
    Mar 3, 2018 at 6:27

1 Answer 1

5
$\begingroup$

Use offset factor of follow path constraint.


Use the offset factor of follow curve constraint.

Test script, select the curve in object mode and run script.

import bpy
context = bpy.context
scene = context.scene
curve_obj = context.object
spline = curve_obj.data.splines[0]
bpy.ops.mesh.primitive_ico_sphere_add(size=0.05, location=(0, 0, 0))
sphere = context.object
fp = sphere.constraints.new(type='FOLLOW_PATH')
fp.target = curve_obj
fp.use_fixed_location = True

res = len(spline.bezier_points)

spheres = [sphere]
o = 0 if spline.use_cyclic_u else 1
r = spline.resolution_u + 1
pts = (res + o) * r
for i in range(1, pts + o):
    s = sphere.copy()
    sc = s.constraints[0]
    sc.offset_factor = i / pts
    scene.objects.link(s)
    spheres.append(s)

To remove the constraints, and keep their constraint location

# remove constraints
scene.update()
for s in spheres:
    sc = s.constraints[0]
    s.location = s.matrix_world.translation
    s.constraints.remove(sc)
$\endgroup$
1
  • $\begingroup$ Nice, can this be done with a custom count? $\endgroup$ Jan 20, 2021 at 5:35

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .