Jump to content
70MadMax

Pivot Point Dinamico

Recommended Posts

Pivot point dinamico

Molte volte può capitare di dover far ruotare tutto il nostro personaggio intorno ad un punto, e, magari poi farlo ruotare di nuovo intorno ad un altro centro di rotazione, prendiamo l'esempio di un cilindro che si muove in questa maniera:

Image00.jpg

E quindi parta da qui(Il locator indica il punto di rotazione):

Image01.jpg

Ruoti...

Image02.jpg

arrivato qui il suo centro di rotazione si sposti

Image03.jpg

ruoti

Image04.jpg

cambio

Image05.jpg

rotazione

Image06.jpg

Naturalmente tutto questo all'interno di una animazione...come fare per modificare il pivot point di un oggetto dinamicamente?

Questa è la semplice costruzione della scena:

Un oggetto(il cilindro), un gruppo parent dell'oggetto, ed un locator(che può essere creato in qualsiasi momento ed in qualsiasi momento eliminato, non è importante che esista sempre, come non è importante che sia un locator, potrebbe essere anche un qualsiasi oggetto della scena).

Il gruppo rappresenta il nostro pivot point animabile, mentre il nostro cilindro avrà il suo pivot point fisso, dove serve a noi per la nostra scena ma sempre fisso.

Ora faremo il tutto in maniera manuale, per capire la tecnica...

Nascondiamo il nostro locator e selezioniamo il gruppo...la posizione del gizmo di rotazione rappresenta il nostro PP(Pivot Point).

Image07.jpg

ora ruotiamo

Image08.jpg

Benissimo...ora vogliamo spostare il nostro PP, quindi spostiamo il nostro gruppo, naturalmente spostandolo si muoverà anche il cilindro...allora, per avere un punto di riferimento preciso duplico il cilindro, gli applico un materiale trasparente e lo stacco dal gruppo.

Image09.jpg

Ora selezioniamo il cilindro e riportiamolo nella posizione che aveva prima

Image10.jpg

riselezioniamo il gruppo

Image11.jpg

e ruotiamo

Image12.jpg

Vi risparmio il seguito...è uguale...sposto il gruppo, rimetto a posto il cilindro, ruoto il gruppo...ecc....

Ho creato un piccolo e semplice script che fa tutto questo per me...devo solo selezionare il parent(cioè il gruppo che faccio ruotare), il o i figli(in questo caso il cilindro) e l'obiettivo(il locator)...

Lo script crea tutti locators che si snappano alle posizioni dei figli, poi muove il gruppo sull'obiettivo e riporta i figli nei punti indicati dai locators creati, cancellandoli subito dopo(i locators, non i figli... :) ).

La procedura di snap funziona in questo modo:

Abbiamo un parallelepipedo (A) e un cilindro ( B ), in posizioni diverse, vogliamo snappare A su B,

Image13.jpg

selezioniamo B (quello fisso) e shift+selezione A (quello che si deve muovere)

Image14.jpg

Eseguiamo un point constraint con il flag Mantain Offset DESELEZIONATO, ed ecco che il tutto avviene

Image15.jpg

Ora nell'outliner basterà selezionare e cancellare il point constraint appena creato

Image16.jpg

Un problema sorge quando il nostro oggetto che si deve spostare ha delle keyframes nei campi translate...una volta eliminato il point constraint lui ritorna nella posizione che aveva prima, rendendo inutile il procedimento...allora lo script cosa fa...una volta creato il point constraint, legge i valori nei campi di translate, elimina il point constraint e poi ce li rimette.

In questa maniera anche se l'oggetto è già stato animato e ha delle keyframes, rimane nella posizione che gli abbiamo assegnato.

Vediamo lo script:

/*

SELEZIONA PARENT, FIGLI, OBIETTIVO

MUOVE IL PARENT SULL ' OBIETTIVO

E TUTTI I FIGLI

IN MODO CHE LA LORO POSIZIONE RIMANGA LA STESSA

*/

prendiamo la selezione corrente, usiamo il flag -l (i nomi lunghi, perchè non so se nella scena ci sono oggetti con lo stesso nome e parent diversi

string $allobjs[] = `ls -sl -l`;

mettiamo in $sz il numero degli elementi selezionati

int $sz = size($allobjs);

string $children[];

il primo è il nostro oggetto che deve snapparsi

string $master = $allobjs[0];

l'ultimo è l'obiettivo

string $moveto = $allobjs[$sz - 1];

tutti gli altri li mettiamo nell'array $children

int $i;

for($i = 0; $i < ($sz - 2); $i++) {

$children[$i] = $allobjs[$i + 1];

}

creiamo un locator per ogni figlio, e snappiamolo, gli diamo il nome "dummyloc" + il nome del figlio

for($i = 0; $i < ($sz - 2); $i++) {

string $dummyloc = ("dummyloc_" + $i);

la procedura verrà spiegata in seguito

LocatorTo($dummyloc,$children[$i]);

}

ora snappiamo il nostro gruppo principale all'obiettivo(spiegazione della procedura in seguito)

PCandDelete($moveto,$master);

snappiamo tutti i figli che presumibilmente si saranno mossi ed eliminiamo uno ad uno tutti i locators creati

for($i = 0; $i < ($sz - 2); $i++) {

string $dummyloc = ("dummyloc_" + $i);

PCandDelete($dummyloc,$children[$i]);

delete $dummyloc;

}

questa procedura crea un locator, lo snappa al figlio e gli da' il nome

proc LocatorTo(string $locName,string $toObj) {

creo un locator all'origine degli assi

string $loc[] = `spaceLocator -p 0 0 0`;

lo snappo

PCandDelete($toObj,$loc[0]);

lo rinomino

rename $loc[0] $locName;

}

Questa è la procedura di snap:

proc PCandDelete(string $master,string $slave) {

creo un point constraint e mi segno il nome

string $pc[] = `pointConstraint -offset 0 0 0 -weight 1 $master $slave`;

metto in $px, $py e $pz i nuovi valori di translate presi dall'oggetto mosso

float $px = `getAttr ($slave + ".translateX")`;

float $py = `getAttr ($slave + ".translateY")`;

float $pz = `getAttr ($slave + ".translateZ")`;

elimino il point constraint

delete $pc;

rimetto nell'oggetto mosso i valori che avevo registrato prima, nel caso l'oggetto stesso abbia keyframes e quindi sia ritornato alla sua posizione precedente non appena eliminato il point constraint

setAttr ($slave + ".translateX") $px;

setAttr ($slave + ".translateY") $py;

setAttr ($slave + ".translateZ") $pz;

}

Lo stesso metodo si può utilizzare con l'orient constraint, e tutti e due insieme per un object snap sia della posizione che dell'orientamento, ad esempio quando un personaggio deve prendere un oggetto...cosa che spiegherò in un prossimo tutorial.

Ora un breve esempio di applicazione in una animazione...la stessa iniziale

Cilindro...gruppo...locator...

Image17.jpg

settiamo una keyframe a 1 per il gruppo e il cilindro(IMPORTANTE...tutti e due)

spostiamo la timeline su 6 e ruotiamo il gruppo di 90°

Image18.jpg

Ora portiamo il locator nella nuova posizione del nostro PP e selezioniamo in quest'ordine: GRUPPO + CILINDRO + LOCATOR

Image19.jpg

eseguiamo lo script...niente sembra essere successo, ma se selezioniamo il gruppo, vediamo che il suo PP si è spostato

Image20.jpg

settiamo un'altra keyframe a 6 per il gruppo e il cilindro(IMPORTANTE...tutti e due)

spostiamo la timeline su 12 e ruotiamo il gruppo di altri 90° (180°)

settiamo un'altra keyframe a 12 per il gruppo e il cilindro(IMPORTANTE...tutti e due).

Con ancora la selezione dei due oggetti attiva apriamo il graph editor e selezioniamo i valori di traslate poi premiamo il tasto A (che ci renderà visibili tutte le chiavi per quei valori)

Image21.jpg

selezioniamo tutto

Image22.jpg

e cambiamo le tangenti in 'stepped'

Image23.jpg

Image24.jpg

questo perchè i cambi di posizione del pivot point devono essere eseguiti in un frame, per rendere invisibile il procedimento

Premiamo play e divertiamoci.

post-59835-1250120750_thumb.jpg


Edited by nicolce

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.


  • Recently Browsing   0 members

    No registered users viewing this page.

×
×
  • Create New...