nortikin / sverchok

Sverchok
http://nortikin.github.io/sverchok/
GNU General Public License v3.0
2.23k stars 232 forks source link

interpolation node #191

Closed ly29 closed 10 years ago

ly29 commented 10 years ago

linear-interpol First and simple, linear interpolation.

enzyme69 commented 10 years ago

Very nice!!! Ok, I think I was doing something that need this, I can now proceed.

Smooth vertex/vertices or Average Vertices will complete this :)

ly29 commented 10 years ago

Needs some more work before I push... Spline will come a bit later I think.

zeffii commented 10 years ago

I think this is exactly what spline normalize does, in conjunction with this node script

ly29 commented 10 years ago

Was playing a bit with numpy and thought this was good application for it.

            for v,t_in in zip(verts,repeat_last(t_ins)):
                pts = np.array(v).T
                tmp = np.apply_along_axis(np.linalg.norm,0,pts[:,:-1]-pts[:,1:])
                t = tmp/tmp.sum()
                t = np.insert(t,0,0)
                t = t.cumsum()
                t_corr = [min(1, max(t, 0)) for t in t_in]
                # this should also be numpy
                out = [np.interp(t_corr, t, pts[i]) for i in range(3)]
                verts_out.append(list(zip(*out)))
ly29 commented 10 years ago

Hadn't looked at your code.

zeffii commented 10 years ago

i'm not ashamed to say I have no notion of what that code does without picking it apart line by line :D

ly29 commented 10 years ago

As a hint it makes a function f(t)=x,y,z with t= [0,1] based on the distance between input points. Then it evaluates f(t) for the t input values from the interval after making sure they are in the interval.

nortikin commented 10 years ago

yes, based on existing edges - that what we need

ly29 commented 10 years ago

Let us explain numpy code to share knowledge. inputs, v is sverchok list of vertices [v0,v1,v2], t_in is a list of points to evaluate in [0,1]

            for v,t_in in zip(verts,repeat_last(t_ins)):
                pts = np.array(v).T #make a np array
                # calc the distance between points
                tmp = np.apply_along_axis(np.linalg.norm,0,pts[:,:-1]-pts[:,1:])
                # resize by inserting 0 and get cumulative sum
                t = np.insert(tmp,0,0).cumsum()
                # normalize t by dividing all values with the sum, t[-1] 
                t = t/t[-1]
                # ensure that all t values to evaled are in [0,1]
                t_corr = [min(1, max(t, 0)) for t in t_in]
                # interpolate X,Y,Z using np.interp
                out = [np.interp(t_corr, t, pts[i]) for i in range(3)]
                verts_out.append(list(zip(*out)))
ly29 commented 10 years ago

spline-first-attempt Spline was tricker than I thought. First attempt has some problem to say the least.

zeffii commented 10 years ago

is that a separate spline segment between each vertex?

ly29 commented 10 years ago

it is natural cubic spline based on the points. It should be smooth and pass through each points. Double fail.

zeffii commented 10 years ago

headwrecking as that seems, it looks like an interesting problem to solve. note to self : poly bezier

ly29 commented 10 years ago

I taking code from code from numerical recipes in C, since the problem is around the points I suspect numerical error. If increase the number of points it works better, however splines are supposed to be stable even with small inputs. Hmm. 20 input points instead of 10. splin2

ly29 commented 10 years ago

But still error around the input points...

ly29 commented 10 years ago

It doesn't say that does it? If t is numpy array that we used cumsum() on then t[-1] is max of the orignal array. Then we normalize the values between 0,1 with that line.

>>> t=np.linspace(0,10,6)
>>> t
array([  0.,   2.,   4.,   6.,   8.,  10.])

>>> t=t.cumsum()
>>> t
array([  0.,   2.,   6.,  12.,  20.,  30.])

>>> t/t[-1]
array([ 0.        ,  0.06666667,  0.2       ,  0.4       ,  0.66666667,  1.        ])
ly29 commented 10 years ago

Okay I won't have time to finish this soon. Will push the linear code soon and leave spline for a bit later.

zeffii commented 10 years ago

I get this error on startup with now: I'll update My blender build to see if the error goes.

Sverchok_nodes: added to pythonpath :-)
Have a nice day with Sverchok
Traceback (most recent call last):
  File "C:\blender_trunk\2.70\scripts\modules\addon_utils.py", line 299, in enable
    mod = __import__(module_name)
  File "C:\blender_trunk\2.70\scripts\addons\sverchok-master\__init__.py", line 279, in <module>
    import node_Interpolation
  File "C:\blender_trunk\2.70\scripts\addons\sverchok-master\..\sverchok-master\node_Interpolation.py"
, line 4, in <module>
    import numpy as np
  File "C:\blender_trunk\2.70\python\lib\site-packages\numpy\__init__.py", line 153, in <module>
    from . import add_newdocs
  File "C:\blender_trunk\2.70\python\lib\site-packages\numpy\add_newdocs.py", line 13, in <module>
    from numpy.lib import add_newdoc
  File "C:\blender_trunk\2.70\python\lib\site-packages\numpy\lib\__init__.py", line 8, in <module>
    from .type_check import *
  File "C:\blender_trunk\2.70\python\lib\site-packages\numpy\lib\type_check.py", line 11, in <module>
    import numpy.core.numeric as _nx
  File "C:\blender_trunk\2.70\python\lib\site-packages\numpy\core\__init__.py", line 6, in <module>
    from . import multiarray
ImportError: Module use of python33.dll conflicts with this version of Python.

the python version is

PYTHON INTERACTIVE CONSOLE 3.4.0 (default, Apr 30 2014, 14:55:04) [MSC v.1500 32 bit (Intel)]```
ly29 commented 10 years ago

That sounds like blender issue numpy.

zeffii commented 10 years ago

it's about time I upgrade to 3.4 locally anyway - cool, local install of Py 3.4 and numpy for that version, then renamed the python folder in blender to _python so blender uses my local python install. Works now.

zeffii commented 10 years ago

Maybe a note to this effect should be added to the readme.md - new section TroubleShooting Installation issues

ly29 commented 10 years ago

What blender version does this happen with? Please file bug report if it is an official build. There isn't any reason that shouldn't work, if it is to widespread lets disable interpolation node for now.

ly29 commented 10 years ago

spline So got it working, now, made really stupid indexing mistake earlier. But sadly this code cannot be used with sverchok due to licensing issues. Removed it from github and starting over...

zeffii commented 10 years ago

The openNURBS sdk has a very liberal license

ly29 commented 10 years ago

Looptools has python implementation that is gpl I just saw, simpler to copy I imagine.

zeffii commented 10 years ago

going to be awesome. Thanks for this!

ly29 commented 10 years ago

spline-looptools The code is certainly less elegant now but that we can work on later. Also should have an option to ensure output point distribution, but then we need to calculate each spline segment length and map input to that.

ly29 commented 10 years ago

Todo:

And add spline code to curve utils.

nortikin commented 10 years ago

https://github.com/nortikin/sverchok/issues/204#issuecomment-44951998 just link for images. interpolation blend

nortikin commented 10 years ago

:-1: POLS 2 EDGS Updated Float Series.001 in:0.0002 Updated Objects_in in:0.0024 Updated Interpolation.001 in:0.0424 Updated List Flip Node in:0.0018 Updated Interpolation in:0.1822 Updated Line Connect in:0.0106 Updated Polygons 2 Edges in:2.1216 Updated Float in:0.0001 Updated Vector Normal in:0.0284 Updated Vectors Move in:0.0196 Updated Viewer Draw in:0.0122 Updated Viewer Draw.001 in:0.0183 Updated Float in:0.0001 Updated Vectors Move in:0.0166 Updated Viewer Draw.001 in:0.0129

enzyme69 commented 10 years ago

Why Polygons 2 Edges is gone?

nortikin commented 10 years ago

i just marked it, don't know how underline on github

ly29 commented 10 years ago

Hint for pols2edges: Create a set of edges for each object, test for membership in list is a slow operation. This line:

if this not in edgs and this not in object:
    def polstoedgs(self, pols):
        out = []
        for obj in pols:
            object = []
            for pols in obj:
                edgs = []
                for i, ind in enumerate(pols):
                    this = [ind, pols[i-1]]
                    this.sort()
                    if this not in edgs and this not in object: 
                        edgs.append(this)
                object.extend(edgs)
            out.append(object)
        return out
nortikin commented 10 years ago

is there case with collections librery... i will rethink this node.

ly29 commented 10 years ago

@nortikin test now I did this:

    def pols_edges(self,obj):
        out = []
        for faces in obj:
            out_edges = set()
            for face in faces:
                for edge in zip(face,face[1:]+[face[0]]):
                    out_edges.add(tuple(sorted(edge)))
            out.append(list(out_edges))
        return out
ly29 commented 10 years ago

Old: Updated Cylinder in:0.0177 Updated Polygons 2 Edges in:0.9626 Updated Viewer Draw in:0.0084 New: Updated Cylinder in:0.0174 Updated Polygons 2 Edges in:0.0308 Updated Viewer Draw in:0.0187

So 3% of original time, lets be nice and call a factor of 2 improvements, should also scale much better. Settings for cylinder: Verts: 32, subdivisions 53.

nortikin commented 10 years ago

wow!!! i just thought of set() and this collection functions. yes, this is solution.

nortikin commented 10 years ago

afraid to ask. am i did wrong that asked evaluate point on surface? by uv coordinates to exact point on surface? Because i asked interpolation of developer, and he agreed to make this feature for API. if it is not ok, than we should stop asking. Can we find points by UV coordinates on nurbs?

ly29 commented 10 years ago

as you saw we can make spline interpolated surfaces now, but this is an important feature and it should be part of api for nurbs if it isn't already.

nortikin commented 10 years ago

it isn't. yes, anyway it will become part. but we have ours needs.