Animacja - przechowywanie zmiennych - 2006-10-26
Przy zapisywaniu wartości do pliku nie zapomnij wstawić na końcu przecinka
wiecej >>

Szukaj: 
Logowanie
Login
Hasło   
Pamiętaj mnie na tej stronie
 Zarejestruj się...




Najnowsza grafika
maxmoon
2012-04-24


Najnowsza tapeta
Nunas
2011-09-15
Matematyka - Piramida Kulek

Co znajdziesz w tym tutorialu
  • Deklarowanie obiektów
  • Trochę wzorów

    Krok 1: Założenia podstawowe.

    Powiem szczerze, że przez lata uczenia się matematyki zadawałem sobie pytanie, po co?! Po co mi wiedzieć jak obliczyć wysokość jakiegoś ostrosłupa, po co mi wiedza, jak obliczyć pole powierzchni jakiejś tam bryły. W sumie, poza tym, iż sama nauka takich rzeczy niesie pewne korzyści, to jest to nie użyteczne.

    W tym tutorialu postaram się pokazać jednak, że taka wiedza się przydaje i można ją wykorzystać do czegoś poza szkolnymi sprawdzianami.


    Wczoraj pojawiła mi się pewna wizja "piramida kulek", wydobyłem z przepaści szufladowych garść kulek. Pośpiesznie ułożyłem 4 kulki w piramidę. Fajnie, zobaczyłem "na żywca" jak taka piramida wygląda, czyli trzy kulki w pierwszej warstwie stykają się bokami, a czwarta kulka leży na pozostałych trzech. Po takiej wizualizacji przystąpiłem do pracy z POVRay'em. Pierwsze dwie kulki ułożyć było dość prosto dopiero później zaczęły się schody. No ale od początku.

    Na samym początku przygotowałem sobie scenę, w której te kulki będą umieszczone, a że chciałem aby owe kulki były jak najbardziej realistyczne (przynajmniej takie było moje pierwsze założenie) postanowiłem użyć do tego gotowego szablonu "Proton Scene"

    Czyli:
    Uruchamiamy POVRAY

    Menu File->New File

    Następnie

    Menu Insert -> Scene Templates -> Photons Scene

    Teraz trochę porządkujemy gotowy plik aby uzyskać coś takiego
      
      #version 3.5;
      #include "colors.inc"
      #declare Photons=on;
      global_settings {
        //assumed_gamma 1.0
        max_trace_level 15
        #if (Photons)          // global photon block
          photons {
            spacing 0.02 
          }
        #end
      }
      // ----------------------------------------
      camera {
        location  <0,10,-15>
        look_at   <0,1,0>
        angle 30
      }
      light_source {
        <-500,300,250>       // light's position
        color rgb <1,1,1>       // light's color
        photons {           // photon block for a light source
          refraction on
          reflection on
        }
      }
      sky_sphere {
        pigment {
          gradient y
          color_map {
            [0.0 rgb <0.6,0.7,1.0>]
            [0.7 rgb <0.0,0.1,0.8>]
          }
        }
      }
      plane {
        y, 0
        texture {
          pigment { color Gray }
        }
      }
      #declare M_Glass=    // Glass material
      material {
        texture {
          pigment {rgbt 1}
          finish {
            ambient 0.0
            diffuse 0.05
            specular 0.6
            roughness 0.005
            reflection {
              0.1, 1.0
              fresnel on
            }
            conserve_energy
          }
        }
        interior {
          ior 1.5
          fade_power 1001
          fade_distance 0.9
          fade_color <0.5,0.8,0.6>
        }
      }
      
    
    Tak przygotowana scena po zrenderowaniu powinna wyglądać tak:



    Nic nadzwyczajnego, można powiedzieć że w HTML coś takiego można wyrenderować. Jednak przejdźmy dalej. Jak już wspomniałem a jak nie wspomniałem to mówię teraz, moja piramida będzie składała się z jednorodnych kulek czyli takich samych (wielkość, materiał) tak więc deklarujemy taką kulkę. Taka deklaracja powinna wyglądać tak.

      
        1. #declare k1=sphere
        2. {
        3.  <0,0,0>,r
        4.  material { M_Glass }
        5.  photons { 
        6.   target 1.0
        7.    refraction on
        8.   reflection on
        9. }
      10.}
      
    

    Trochę objaśnień
    W pierwszej linijce słowo #declare określa, że rozpoczynamy deklarację obiektu, po słowie declare jest nazwa obiektu, następnie =, a później właściwa deklaracja. To była taka teoria a teraz po co i jak tego użyć. Wyobraźmy sobie naszą scenę, tylko z taką różnicą że piramida którą będziemy budować będzie się składała z 10 kulek i nagle zmieniamy zadanie i nasze kulki nie mają już być ze szkła tylko z metalu, ale co więcej nie mają już być o promieniu 1 tylko o promieniu .5. W momencie kiedy byśmy w scenia za każdym razem ręcznie pisali sphere {} to musielibyśmy zmieniać te sphere 10 razy. A przy zastosowaniu deklaracji zmieniamy tylko w jednym miejscu. Jeśli chodzi o to jak tego użyć to nic prostszego zwyczajnie piszemy:
      
      object { k1 }
      
    

    W trzeciej linijce jest zwykła deklaracja kulki <0,0,0> punkt w przestrzeni gdzie ta kulka ma się znaleźć, r - a to jest promień kulki, oczywiście teraz gdybyśmy próbowali wyrenderować scenę nakrzyczało by na nas ponieważ r nie jest zdeklarowane. Tak więc przed deklaracją kulki k1 deklarujemy promień tej kulki r.
      
      #declare r=1;
      
    
    W linijce 4 określamy z jakiego materiału jest ta kulka, wykorzystujemy materiał jaki był zdeklarowany w tej scenie szablonowej. Natomiast w linijkach 5,6,7,8,9 jest deklaracja właściwości obiektu przy użyciu fotonów. Nie będę się rozpisywał co to oznacza, bo nie jest to miejsce na tego typu rozmowy i po prostu nie mam bladego pojęcia, wiem natomiast, że jest to wymagane aby fotony zadziałały.

    Dobrze teraz mamy już zdefiniowaną naszą kulkę to ją wsadźmy do naszej sceny:
      
      object { k1 translate <0,r,0> }
      
    
    translate jest to słowo kluczowe, określa nam nowe położenie obiektu, dla uproszczenia możemy przyjąć, że w nawiasach ostrych <> podajemy nowe współrzędne danego obiektu. Oczywiście obiekt umiejscowiony jest w przestrzeni dlatego też, podajemy trzy wartości. (dokładny opis świata POVRay'owego można znaleźć w tutorialu pt. "praca z programem POVRAY". W skrócie przypomnę, że te współrzędne podajemy w kolejności x,y,z. W tym przypadku napisałem translate <0,r,0> pytanie dlaczego przesuwam naszą kulkę w góre (czyli po y) o wartość promienia? Ponieważ nasza "ziemia" czyli plane jest na poziomie y=0; i jeżeli byśmy kulki nie przesunęli o wartość promienia r to nasza kulka była by wbita do połowy w ziemię.

    A po zrenderowanu kulka powinna wyglądać tak:



    Tak jak wspomniałem na początku dwie pierwsze kulki umieścić to nie problem. Druga kulka będzie na tym samym poziomie z czyli z=0, na tym samym poziomie y=r. A wartość x=2*r. Pytanie dlaczego 2*r a nie o r. Ponieważ gdybyśmy przesunęli kulkę o r to nasz rysunek wyglądałby tak:



    Po matematycznemu: Promień kulki równa się r (promień czyli odległość środka od dowolnego punktu na jej powierzchni), a że kulki mają się stykać w jednym punkcie, to środek drugiej kulki ma być oddalony o r pierwszej kulki i o r swojej czyli 2*r przyjmijmy że a=2*r
      
      #declare a=2*r;
      
    

    Tak wyglądają dobrze ustawione kulki:



    Tyle pisania a to przecież podobno drugą kulkę ustawić to nie problem. No ale dobra zajmijmy się kulką trzecią. Docelowo chciałem, aby była ona umieszczona tak:



    Nie było to takie proste określić współrzędną tej trzeciej kulki, kilka razy "na oko" próbowałem i prawie mi się udało, jednak nie powiem, żeby to był inteligentny sposób. Tak więc powróćmy do matematyki. Schematycznie narysowana nasza scena od góry wygląda tak:



    Łącząc środki naszych kulek powstaje nam trójkąt równoboczny o boku a=2*r. Współrzędna x naszej trzeciej kulki jest równa r, ponieważ wiemy z matematyki, że wysokość trójkąta równobocznego przecina przeciwległy bok dokładnie w połowie. (Ale to można było wywnioskować) Teraz współrzędna z jest to wysokość naszego trójkąta, a jak to policzyć? No cóż profesor Romanowski zwykł mawiać "był sobie kiedyś takie stary mądry Grek Dziadzio Pitagoras" czyli: co po uproszczeniu daje nam .
    A tak wygląda zapis naszych rozważań w povrayu
      
      object { k1 translate <r,r,a*sqrt(3)/2> }
      
    


    Warto wspomnieć o funkcji sqrt(), która zwraca nam pierwiastek drugiego stopnia z liczby podanej jako argument (liczba podana w nawiasie)

    Dobra, to była ta prostsza część. Teraz przydałoby się umieścić kulkę czwartą, która opierałaby się na pozostałych trzech.

    Zastosowałem tą samą metodę a mianowicie połączyłem środki wszystkich czterech kulek co w rezultacie dało mi czworościan foremny. Okazało się, że środek czwartej kulki to nic innego jak wysokość takiego czworościanu. Można na piechotę obliczyć wzór tej wysokości albo można skorzystać z tablic matematycznych, albo jak się nie ma tablic można zajrzeć do WIKIPEDII :-) tak jak ja to uczyniłem i taki wzór otrzymałem



    To nasze obliczone h to nic innego jak współrzędna kulki y (oczywiście trzeba dodać jeszcze r). X jest taki sam jak w przypadku kulki trzeciej. Pozostało nam obliczyć z, bo z tą współrzędną jest trochę gorzej. Aby wyznaczyć środek ostatniej kulki trzeba przypomnieć sobie takie określenie jak środek ciężkości trójkąta. Dla przypomnienia podpowiem, że jest to punkt przecięcia się środkowych trójkąta, czyli prostych prowadzonych od wierzchołka do środka przeciwległej ściany. W trójkącie równobocznym środek ciężkości można określić jako 1/3 wysokości. Tzn., że środkowe dzielą się w stosunku 2:1. Jako, że nasza wysokość równa się a*sqrt(3)/2 po podzieleniu przez 3 otrzymamy a*sqrt(3)/6
      
      object { k1 translate <0,r,0> }
      object { k1 translate <a,r,0> }
      object { k1 translate <r,r,a*sqrt(3)/2> }
      object { k1 translate <r, r+a*sqrt(2/3), a*sqrt(3)/6>
      }
      
    


    A render naszego dzieła wygląda tak:



    Teraz trzeba dodać może jeszcze parę kulek tak, aby piramida miała trzy kulki w podstawie i już będzie jakoś wyglądało to nasze dzieło.

    Dodatkowo:
  • Plik z gotową sceną
  • Piramida kulek - macro - druga część tutoriala o kulkach. Tym razem tworzone jest makro.
  • © druidy.pl

    Korzystając z witryny bez zmiany ustawień przeglądarki wyrażasz zgodę na użycie plików cookies. W każdej chwili możesz swobodnie zmienić ustawienia przeglądarki decydujące o ich zapisywaniu.