CGTalk > Software > Autodesk 3ds max > 3dsMax SDK and MaxScript
Login register
Thread Closed share thread « Previous Thread | Next Thread »  
 
Thread Tools Search this Thread Display Modes
Old 09-21-2010, 10:08 AM   #1
JHN
maxscript/c# lover
 
JHN's Avatar
Johan Boekhoven
Technical Artist
nmtrix.com
Netherlands
 
Join Date: Apr 2002
Posts: 1,714
Lerp for matrix3 values

Is there an existing way to lerp between 2 matrix values or do I have to decompose the PRS values, (s)lerp them and rebuilt the matrix each step?

Thanks,
-Johan
__________________
Online: LinkedIn | blog | nmtrix.com
Code: mxs+.net | c# | mb-python | php | html+js | mysql | python
 
Old 09-21-2010, 11:36 AM   #2
JHN
maxscript/c# lover
 
JHN's Avatar
Johan Boekhoven
Technical Artist
nmtrix.com
Netherlands
 
Join Date: Apr 2002
Posts: 1,714
Found a thread about it : http://forums.cgsociety.org/showthr...p?f=98&t=859470

Thanks,
-Johan
__________________
Online: LinkedIn | blog | nmtrix.com
Code: mxs+.net | c# | mb-python | php | html+js | mysql | python
 
Old 09-21-2010, 11:59 AM   #3
MatanH
Character TD
 
MatanH's Avatar
portfolio
Matan Halberstadt
Head of Rigging dpt.
snowball studios
Tel-Aviv, Israel
 
Join Date: Oct 2002
Posts: 379
Just saw your 2nd post but I'll post my solution anyhow..
Code:
( fn lerp matArray weights = ( local resMat = matrix3 [0,0,0] [0,0,0] [0,0,0] [0,0,0] for i = 1 to matArray.count do ( local w = weights[i] local intMat = matrix3 [w,0,0] [0,w,0] [0,0,w] [w,w,w] resMat += matArray[i] * intMat ) resMat ) if selection.count == 3 then ( local a = $[1] local b = $[2] local c = $[3] local d = copy a d.transform = lerp #(a.transform, b.transform, c.transform) #(0.5, 0.5, 0.5) ) else messageBox "Please select 3 objects!" )
 
Old 09-21-2010, 12:02 PM   #4
denisT
MAX Doctor
 
denisT's Avatar
portfolio
Denis Trofimov
CA, USA
 
Join Date: Jul 2009
Posts: 9,334
Send a message via ICQ to denisT
Quote:
Originally Posted by JHN
Is there an existing way to lerp between 2 matrix values or do I have to decompose the PRS values, (s)lerp them and rebuilt the matrix each step?

Thanks,
-Johan


there is no lerp for matrices. use lerp for rotation (in quaternions), and average for position and scale.
 
Old 09-21-2010, 12:22 PM   #5
JHN
maxscript/c# lover
 
JHN's Avatar
Johan Boekhoven
Technical Artist
nmtrix.com
Netherlands
 
Join Date: Apr 2002
Posts: 1,714
@ Matan : Thanks, I'm using something else since I just need to blend between 2 matrices (making a pose tool for CAT). Will test you code as it looks more compact.

@ Denis : I'm using a slightly modified variant on your code
Code:
fn blendMatrix m1: m2: weight:0.5 = ( fn dotQuat q q_prev = ( (q.w * q_prev.w + q.x * q_prev.x + q.y * q_prev.y + q.z * q_prev.z) < 0 ) r1 = m1.rotationpart r2 = m2.rotationpart if (dotQuat r1 r2) do r1 *=-1 r = slerp (normalize r1) (normalize r2) weight t = m1.translationpart + (m2.translationpart - m1.translationpart) * weight s = m1.scalepart + (m2.scalepart - m1.scalepart) * weight translate (rotate (scale (matrix3 1) s true) r) t -- ignores scale )

I added the scale averaging, and encapsulated the dotQuat fn.

Thanks!
-Johan
__________________
Online: LinkedIn | blog | nmtrix.com
Code: mxs+.net | c# | mb-python | php | html+js | mysql | python
 
Old 09-21-2010, 12:53 PM   #6
JHN
maxscript/c# lover
 
JHN's Avatar
Johan Boekhoven
Technical Artist
nmtrix.com
Netherlands
 
Join Date: Apr 2002
Posts: 1,714
@Matan, does it work between 2 transforms. I tried:
Code:
for i = 1 to 10 do point transform:(lerpM #($[1].transform, $[2].transform) #((i/10.), (1 - (i/10))))

Between 2 objects that are transformed differently, but the results are not good. How does your function work with 2 matrices?

Thanks,
-Johan
__________________
Online: LinkedIn | blog | nmtrix.com
Code: mxs+.net | c# | mb-python | php | html+js | mysql | python
 
Old 09-21-2010, 12:59 PM   #7
MatanH
Character TD
 
MatanH's Avatar
portfolio
Matan Halberstadt
Head of Rigging dpt.
snowball studios
Tel-Aviv, Israel
 
Join Date: Oct 2002
Posts: 379
it won't work correct if the weights don't sum up to exactly 1.0
here is an example of what you tried to do:
Code:
local a = $[1] local b = $[2] local n = 10 for i = 1 to n - 1 do ( local c = copy a local w = 1.0 * i / n c.transform = lerp #(a.transform, b.transform) #(w, 1.0 - w) )


EDIT:
just playing around with it, here is another nice test:
Code:
( fn lerp matArray weights = ( local resMat = matrix3 [0,0,0] [0,0,0] [0,0,0] [0,0,0] for i = 1 to matArray.count do ( local w = weights[i] local intMat = matrix3 [w,0,0] [0,w,0] [0,0,w] [w,w,w] resMat += matArray[i] * intMat ) resMat ) local a = teapot transform:(matrix3 [0.543478,1.19095,-0.738627] [-1.22502,0.788501,0.370005] [1.21654,0.836836,2.24443] [204.994,154.378,224.798]) wirecolor:red local b = teapot transform:(matrix3 [1,0,0] [0,1,0] [0,0,1] [122.507,3.13654,0]) wirecolor:green local c = teapot transform:(matrix3 [1.06301,0.5229,0.250736] [-0.301877,-0.31541,1.93761] [0.425891,-0.832628,-0.0691843] [288.803,-141.283,52.8861]) wirecolor:blue local n = 10 for j = 0 to n do ( local w1 = 1.0 * j / n for i = 0 to n do ( local d = copy a local w2 = (1.0 - w1) * i / n local w3 = 1.0 - w1 - w2 d.transform = lerp #(a.transform, b.transform, c.transform) #(w1, w2, w3) d.wireColor = a.wireColor * w1 + b.wireColor * w2 + c.wireColor * w3 ) ) )

Last edited by MatanH : 09-21-2010 at 01:18 PM.
 
Old 09-21-2010, 01:31 PM   #8
JHN
maxscript/c# lover
 
JHN's Avatar
Johan Boekhoven
Technical Artist
nmtrix.com
Netherlands
 
Join Date: Apr 2002
Posts: 1,714
I went wrong because my code produced an integer as weight instead of a float. But still your solution is not as good because the scale of the matrix is not avaraged, but get's distorted. So I'm sticking with my (Denis' actually) code. But there's some nice motion design effects to be made with your code!

Thanks,
-Johan
__________________
Online: LinkedIn | blog | nmtrix.com
Code: mxs+.net | c# | mb-python | php | html+js | mysql | python
 
Old 09-22-2010, 02:53 PM   #9
eek
Fixer
 
eek's Avatar
portfolio
Charles Looker
Snr Technical Artist
Electronic Arts
Vancouver, Canada
 
Join Date: Feb 2002
Posts: 4,221
Code:
local matrices = #((matrix3 1), ((eulerangles 0 45 32) as matrix3), (transMatrix [50,40,10])) local mc = for each in matrices collect each local tmp = #() local t = 0.5 while mc.count > 1 do ( for i = 1 to (mc.count-1) do ( append tmp ((slerp mc[i].rotation mc[i+1].rotation t) as matrix3 * transMatrix((1-t) * mc[i].row4 + mc[i+1].row4 * t)) ) mc = tmp tmp = #() ) mc[1]


This is a quadratic form of blending between multiple matrices roughly.
__________________
Disclaimer: My opinions are not those of my employer.


 
Old 09-22-2010, 02:53 PM   #10
CGTalk Moderation
Lord of the posts
CGTalk Forum Leader
 
Join Date: Sep 2003
Posts: 1,066,481
Thread automatically closed

This thread has been automatically closed as it remained inactive for 12 months. If you wish to continue the discussion, please create a new thread in the appropriate forum.
__________________
CGTalk Policy/Legalities
Note that as CGTalk Members, you agree to the terms and conditions of using this website.
 
Thread Closed share thread


Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off
CGSociety
Society of Digital Artists
www.cgsociety.org

Powered by vBulletin
Copyright 2000 - 2006,
Jelsoft Enterprises Ltd.
Minimize Ads
Forum Jump
Miscellaneous

All times are GMT. The time now is 05:52 PM.


Powered by vBulletin
Copyright ©2000 - 2016, Jelsoft Enterprises Ltd.