XNA Oświetlenie Kurs ITA-106 (Grafika i multimedia) – Moduł 3

Slides:



Advertisements
Podobne prezentacje
C++ wykład 2 ( ) Klasy i obiekty.
Advertisements

C++ wykład 4 ( ) Przeciążanie operatorów.
Modele oświetlenia Punktowe źródła światła Inne
Klasy i obiekty.
Wzorce.
Krzysztof Skabek, Przemysław Kowalski
Podstawy grafiki komputerowej
Generics w .NET 2.0 Łukasz Rzeszot.
Przekształcenia afiniczne
Grafika komputerowa Wykład 2 Wykorzystanie podstawowych usług bibliotecznych (API) w operacjach graficznych.
Grafika komputerowa Wykład 8 Wstęp do wizualizacji 3D
dotyczące plików graficznych
Wielodziedziczenie od środka Konrad Lipiński
Programowanie w środowiskach zintegrowanych wykład 1 PSZ Programowanie w Środowiskach Zintegrowanych > Systemy i środowiska zintegrowane > Środowisko zintegrowane.
Struktury.
C++ wykład 2 ( ) Klasy i obiekty.
Eliminacja powierzchni niewidocznych Wyznaczanie powierzchni widocznych Które powierzchnie, krawędzie i punkty są widoczne ze środka rzutowania (albo wzdłuż.
1 Podstawy apletów Co to jest aplet, cykl życia apletu, metody apletu, metoda paint(), czcionki, kolory, parametryzowanie apletu, układ współrzędnych ekranowych,
Geometria obrazu Wykład 11
Geometria obrazu Wykład 10
Geometria obrazu Wykład 11
Czytanie, pisanie i rysowanie – cd.. Jeszcze jeden strumyk PrintStream działa jak PrintWriter, ale: Używa domyślnego (systemowego) kodowania Nie wyrzuca.
1 Języki i techniki programowania prowadzący dr Grzegorz Filipczyk.
Przygotowanie materiału ilustracyjnego
Przegląd ważniejszych bibliotek używanych przy projekcie Quall.
C# Windows Forms Zastosowania Informatyki Wykład 3
Współrzędne jednorodne
Współrzędne jednorodne
Podstawowe pojęcia i problemy związane z przetwarzaniem plików graficznych.
Graniastosłupy proste i nie tylko
Symulacje komputerowe
Symulacje komputerowe
Symulacje komputerowe Detekcja kolizji brył sztywnych Fizyka w modelowaniu i symulacjach komputerowych Jacek Matulewski (
Grafika 3D w C++/DirectX Oraz kombinowane XNA
Kinematyka prosta.
Modelowanie elementów świata 3D przy użyciu biblioteki Managed Directx
Light pre-pass renderer
Zaawansowane techniki renderingu
ZASTOSOWANIE RENDERINGU W GRAFICE KOMPUTEROWEJ
Programowanie Windows na przykładzie C# część 1
Dane INFORMACYJNE Nazwa szkoły: Zespół Szkół Gastronomicznych
Odwzorowywanie tekstur
Java – coś na temat Klas Piotr Rosik
Programowanie obiektowe Wykład 6 dr Dariusz Wardowski, Katedra Analizy Nieliniowej, WMiI UŁ 1/14 Dariusz Wardowski.
Farseer Physics Engine. Farseer Physics Engine jest silnikiem fizycznym napisanym dla platformy.NET. Został on zainspirowany przez silnik Box2D znany.
Grafika komputerowa Jest to dziedzina rozwijająca się niezwykle dynamicznie, a jednocześnie wymagająca znacznej mocy obliczeniowej. Łatwo możemy to zaobserwować,
Wojciech Toman. Dotychczasowe podejście do oświetlenia Idea deferred shadingu Typowe problemy wraz z propozycjami rozwiązania Optymalizacja wydajności.
3dMatchGL Wykorzystanie biblioteki graficznej OpenGL przy tworzeniu gry 3DMatchGL.
Algorytm Z-Bufora (bufora głębokości)
Kolory w kodzie RGB i HEX
RUCH KULISTY I RUCH OGÓLNY BRYŁY
Grafika i komunikacja człowieka z komputerem
Przygotowanie do egzaminu gimnazjalnego
Informatyka +.
Grafika i komunikacja człowieka z komputerem
Technologie internetowe Wykład 5 Wprowadzenie do skrytpów serwerowych.
Teksturowanie oraz algorytmy cieniowania
BRYŁY.
Geometria obrazu Wykład 10
Geometria obrazu Wykład 6
Podsumowanie omówionych zagadnień
Grafika komputerowa – Grafika wektorowa i rastrowa
Draver/GRK/cw3_result.jpg. Grafika 3D Wprowadzenie.
Grafika 2d - Podstawy. Kontakt Daniel Sadowski FTP: draver/GRK - wyklady.
PODSTAWY STEREOMETRII
Grafika komputerowa Dr inż. Michał Kruk. Reakcja ś wiat ł a z materi ą : – Odbicie ś wiat ł a – Przenikanie ś wiat ł a Zale ż ne od w ł a ś ciwo ś ci.
Programowanie Obiektowe – Wykład 6
Programowanie Obiektowe – Wykład 2
Wiktoria Dobrowolska. Grafika komputerowa - dział informatyki zajmujący się wykorzystaniem komputerów do generowania obrazów oraz wizualizacją rzeczywistych.
Symulacje komputerowe
Zapis prezentacji:

XNA Oświetlenie Kurs ITA-106 (Grafika i multimedia) – Moduł 3 Jacek Matulewski (e-mail: jacek@fizyka.umk.pl) http://www.fizyka.umk.pl/~jacek/dydaktyka/3d/ XNA Oświetlenie Wersja: 7 listopada 2009

Plan Nowy typ werteksów VertexPositionColorNormal Prostopadłościan – wektory normalne Oświetlenie domyślne Typy światła (model Phonga), własności materiału Uśrednianie i interpolacja normalnych Mieszanie kolorów Antyaliasing Problemy z przezroczystością Mgła Metoda rzutowania cieni

Projekt startowy Projekt można pobrać z http://www.fizyka.umk.pl/~jacek/dydaktyka/3d/xna/ita106/ Plik zrodla/M03/3A1-0 Oswietlenie (teoria) - Start.zip Komponent Prostopadłościan Obroty macierzy świata w metodzie Game1.Update Macierz rzutowania: perspektywa Macierz widoku: kamera w (0,0,2.5) skierowana na początek układu współrzędnych Będziemy edytować wyłącznie metodę Game1.Initialize

1/7 Nowy typ werteksu Werteks – wierzchołek figury 2D lub 3D, element siatki rozpiętej w 3D, która jest bazą renderowanej sceny Werteks nie jest po prostu punktem w przestrzeni 3D Z werteksem mogą być wiązane własności, m.in: - pozycja i kolor (VertexPositionColor), - normalna i wsp. Tekstury (VertexPositionNormalTexture) - głębokość, styczna, wielkość punktu, mgła, itd. W bibliotece XNA są tylko cztery klasy opisujące werteksy (VPC, VPCT, VPNT, VPT; my dodamy VPCN i VPCNT)

Nowy typ werteksu VC#: menu Project, Add class 1/7 using System; using System.Collections.Generic; using System.Linq; using System.Text; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Graphics; namespace ITA106 { public struct VertexPositionColorNormal } Dodajemy przestrzenie nazw XNA Klasę werteksu będziemy używać w kolejnych projektach Dodajemy przestrzenie nazw XNA Nazwa klasy w konwencji typów werteksów XNA

Nowy typ werteksu 1/7 public struct VertexPositionColorNormal { public Vector3 Position; public Color Color; public Vector3 Normal; Pola przechowujące dane werteksu (własności) Tablica opisująca elementy werteksu (własności) Rozmiar werteksu public static int SizeInBytes = 6 * sizeof(float) + sizeof(uint); public static readonly VertexElement[] VertexElements = new VertexElement[]{ new VertexElement( 0, 0, VertexElementFormat.Vector3, VertexElementMethod.Default, VertexElementUsage.Position, 0), Numer strumienia (0 - domyślny) Pierwszy z trzech elementów werteksu Element Pozycja Typ XNA Interpretacja Position VertexElementFormat.Vector3 VertexElementUsage.Position Color 3 * sizeof(float) VertexElementFormat.Color VertexElementUsage.Color Normal 3 * sizeof(float) + sizeof(uint) VertexElementUsage.Normal Numer bajtu w „paczce” W XNA Position jest typu Vector3 Metoda teselatora Semantyka elementu (własności) werteksa Indeks semantyki (ma sens gdy zdefiniowane jest więcej semantyk)

Nowy typ werteksu 1/7 public struct VertexPositionColorNormal { public Vector3 Position; public Color Color; public Vector3 Normal; … Konstruktor public VertexPositionColorNormal(Vector3 position, Color color, Vector3 normal) { this.Position = position; this.Color = color; this.Normal = normal; this.TextureCoordinate = textureCoordinate; } }

1/7 Nowy typ werteksu Ćwiczenie: zdefiniować typ werteksu uwzględniający element współrzędnych teksturowania public struct VertexPositionColorNormalTexture { public Vector3 Position; public Color Color; public Vector3 Normal; public Vector2 TextureCoordinate; public static int SizeInBytes = 8 * sizeof(float) + sizeof(uint); public struct VertexPositionColorNormalTexture { public Vector3 Position; public Color Color; public Vector3 Normal; public ?????? TextureCoordinate; public static int SizeInBytes = ? * sizeof(float) + sizeof(uint); Element Pozycja Typ XNA Interpretacja Position VertexElementFormat.Vector3 VertexElementUsage.Position Color 3 * sizeof(float) VertexElementFormat.Color VertexElementUsage.Color Normal 3 * sizeof(float) + sizeof(uint) VertexElementUsage.Normal Texture Coordinate 6 * sizeof(float) + sizeof(uint) VertexElementFormat.Vector2 VertexElementUsage. TextureCoordinate

Normalne w prostopadłościanie 2/7 Normalne w prostopadłościanie W pliku Prostopadloscian.cs: Ctrl+H: zmiana VertexPositionColor (typ XNA) na VertexPositionColorNormal (nasz typ) np. VertexPositionColorNormal[] werteksy = new VertexPositionColorNormal[6*2*3]{ //przednia sciana new VertexPositionColorNormal(punkty[3], kolor1, Vector3.UnitZ), new VertexPositionColorNormal(punkty[2], kolor1, Vector3.UnitZ), … //gorna sciana new VertexPositionColorNormal(punkty[3], kolor2, Vector3.UnitY),

Kolor światła otoczenia (typ Vector3) 3/7 Oświetlenie domyślne Wracamy do klasy gry Game1 (plik Game1.cs). W metodzie Game1.Initialize włączamy oświetlenie domyślne: efekt.EnableDefaultLighting(); efekt.AmbientLightColor = new Vector3(0.5f, 0.5f, 0.5f); efekt.AmbientLightColor = Color.Gray.ToVector3(); Kolor światła otoczenia (typ Vector3)

Typy światła (model Phonga) 4/7 Typy światła (model Phonga) Fizyczny model oświetlenia – na efekt końcowy (tj. kolor piksela) wpływają „własności emisyjne” źródła światła, „własności absorpcyjne” materiału, który jest oświetlany i własności ewentualnych ciał półprzezroczystych + = Typy źródeł oświetlenia: Światło otoczenia (ambient) – światło słoneczne w białym pomieszczeniu Rozproszone (diffuse) – mleczna żarówka, świeca Rozbłysk (specular) – reflektor, odbicie od lustra Dla każdego typu parametry materiału ustalane są osobno Typy źródeł oświetlenia: Światło otoczenia (ambient) Rozproszone (diffuse) – posiada źródło, ale jest jednorodne we wszystkich kierunkach Generalnie: Jasność proporcjonalna do kosinusa kąta padania (normalna) Typy źródeł oświetlenia: Światło otoczenia (ambient) – bez źródła i kierunku – rozświetla jednorodnie całą scenę, także wewnątrz figur) – nie daje cieni na obiekcie (nie ma złudzenia 3D) Typy źródeł oświetlenia: Światło otoczenia (ambient) Rozproszone (diffuse) Rozbłysk (specular) – źródło i kierunek reflektor, efekt „zajączka” – rozbłysku na gładkich pow.

Model oświetlenia Phonga 4/7 Model oświetlenia Phonga + = Opracowany w 1975 przez Phong Bui-Tuonga Jest jedynie zgrubnym przybliżeniem praw optyki Zakłada trzy niezależne komponenty odbitego światła Światło rozproszone – model Lamberta (1760) Model cieniowania Phonga (coś innego niż model ośw.) = interpolacja normalnych (uśrednianie normalnych)

Model oświetlenia Phonga 4/7 Model oświetlenia Phonga + = W XNA i Direct3D model Phonga jest uzupełniony o światło emisji (emission) Imitacja źródła światła (jednak nie oświetla innych aktorów na scenie!) Realizowane podobnie jak światło otoczenia

4/7 Model Lamberta Model światła rozproszonego Jasność przedmiotu (natężenie światła) równa jest Ii. Jest ono jakąś funkcją natężenia światła padającego na powierzchnię i kąta odbicia b (= padania) Model zakłada, że natężenie światła odbitego Id jest proporcjonalne do „efektywnej powierzchni” widzianej przez obserwatora Acos(b ). N – wektor normalny, L – promień św. odbitego N L Id = Ii cos(b ) Obliczanie cos(b ) jest szybkie: cos(b ) = NxLx+NyLy+NzLz

4/7 Model Phonga Model światła specular („zajączek”) Wprowadzony przez Phonga – nie ma podstaw fizycznych N – wektor normalny L – promień św. odbitego V – kierunek do obserwatora N L V Is = Ii cos n (a ) Parametr n kontroluje „ostrość” zależności od kąta pod którym oglądamy fragment powierzchni n ~ B..Effect.SpecularPower n = 1, 5, 10, 20, 50, 100

Ciało doskonale czarne 4/7 Ciało doskonale czarne Promiennik zupełny Ustawiamy wszystkie parametry materiału na czerń W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Gray.ToVector3(); Włączone światło otoczenia efekt.DiffuseColor = Color.Black.ToVector3(); efekt.SpecularColor = Color.Black.ToVector3(); efekt.EmissiveColor = Color.Black.ToVector3(); Materiał pochłania wszystkie typy światła (także otoczenia) efekt.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Black.ToVector3(); Wyłączamy wszystkie trzy źródła światła (pozostaje tylko światło otoczenia)

Ciało białe matowe Ustawiamy wszystkie parametry materiału na czerń 4/7 Ciało białe matowe Ustawiamy wszystkie parametry materiału na czerń W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Gray.ToVector3(); Tylko światło otoczenia, więc przedmiot jest płaski efekt.DiffuseColor = Color.White.ToVector3(); efekt.SpecularColor = Color.Black.ToVector3(); efekt.EmissiveColor = Color.Black.ToVector3(); efekt.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight0.DiffuseColor = Color.White.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Black.ToVector3(); Włączamy komponent światła rozproszonego pierwszego źródła światła

Czarny monolit z połyskiem 4/7 Czarny monolit z połyskiem Czarne ciało reagujące na światło typu rozbłysk W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Gray.ToVector3(); Pochłaniamy światło rozproszone, a odbijamy rozbłysk (specular) efekt.DiffuseColor = Color.Black.ToVector3(); efekt.SpecularColor = Color.White.ToVector3(); efekt.EmissiveColor = Color.Black.ToVector3(); efekt.SpecularPower = 1; = 16; = 128; n = 1 – jak światło rozproszone n = 16 – typowa wartość n = 128 – błysk tylko „w osi” efekt.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Red.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Black.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Black.ToVector3(); Włączamy tylko komponent rozbłysku pierwszego źródła światła

Wiele kolorowych reflektorów 4/7 Wiele kolorowych reflektorów Czarne ciało reagujące na światło typu rozbłysk W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Gray.ToVector3(); efekt.DiffuseColor = Color.Black.ToVector3(); efekt.SpecularColor = Color.White.ToVector3(); efekt.EmissiveColor = Color.Black.ToVector3(); efekt.SpecularPower = 16; efekt.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Red.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Green.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Black.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Blue.ToVector3();

Wiele źródeł światła Matowe ciało oświetlone trzema żarówkami 4/7 Wiele źródeł światła Matowe ciało oświetlone trzema żarówkami W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Black.ToVector3(); efekt.DiffuseColor = Color.White.ToVector3(); efekt.SpecularColor = Color.Black.ToVector3(); efekt.EmissiveColor = Color.Black.ToVector3(); efekt.DirectionalLight0.DiffuseColor = Color.Red.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Red.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Green.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Green.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Blue.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Blue.ToVector3();

Światło emisji Sześcienna żarówka (nie oświetla innych obiektów) 4/7 Światło emisji Sześcienna żarówka (nie oświetla innych obiektów) W metodzie Game1.Initialize : efekt.EnableDefaultLighting(); efekt.AmbientLightColor = Color.Black.ToVector3(); efekt.DiffuseColor = Color.White.ToVector3(); efekt.SpecularColor = Color.Black.ToVector3(); efekt.EmissiveColor = Color.Yellow.ToVector3(); efekt.DirectionalLight0.DiffuseColor = Color.Red.ToVector3(); efekt.DirectionalLight0.SpecularColor = Color.Red.ToVector3(); efekt.DirectionalLight1.DiffuseColor = Color.Green.ToVector3(); efekt.DirectionalLight1.SpecularColor = Color.Green.ToVector3(); efekt.DirectionalLight2.DiffuseColor = Color.Blue.ToVector3(); efekt.DirectionalLight2.SpecularColor = Color.Blue.ToVector3();

Cieniowanie Phonga Uśrednianie i interpolacja normalnych 5/7 Uśrednianie normalnych Interpolacja normalnych

Cieniowanie Phonga (ta sama ilość werteksów) 5/7 Cieniowanie Phonga Uśrednianie i interpolacja normalnych Cieniowanie płaskie Cieniowanie Phonga (ta sama ilość werteksów)

6/7 Mieszanie kolorów Mieszanie kolorów (alpha blending), kanał alfa koloru Antyaliasing (realizowany sprzętowo) Przezroczystość Mgła

6/7 Projekt startowy Projekt można pobrać z http://www.fizyka.umk.pl/~jacek/dydaktyka/3d/xna/ita106/ Plik 3A3-0 Oswietlenie (teoria) - Mieszanie kolorow - Start.zip Dwa nieprzezroczyste trójkąty Czerwony rysowany jest przed białym Obroty wokół osi OY

Mieszanie kolorów Antyaliasing (u mnie nie działa!!!!!) 5/7 public Game1() { Window.Title = "Modul 3 - Oświetlenie - Mieszanie kolorów"; graphics = new GraphicsDeviceManager(this); Content.RootDirectory = "Content";   graphics.PreferMultiSampling = true; graphics.PreparingDeviceSettings += new EventHandler<PreparingDeviceSettingsEventArgs>(graphics_PreparingDeviceSettings); } void graphics_PreparingDeviceSettings(object sender, PreparingDeviceSettingsEventArgs e) e.GraphicsDeviceInformation.PresentationParameters.MultiSampleQuality = 0; e.GraphicsDeviceInformation.PresentationParameters.MultiSampleType = MultiSampleType.FourSamples;

5/7 Mieszanie kolorów Antyaliasing

Mieszanie kolorów Trójkąty nieprzezroczyste 6/7 Mieszanie kolorów Trójkąty nieprzezroczyste Kolejność rysowania trójkątów nie ma znaczenia

Mieszanie kolorów Włączanie blendingu 6/7 protected override void Draw(GameTime gameTime) { GraphicsDevice gd = graphics.GraphicsDevice; gd.Clear(Color.Black); gd.RenderState.CullMode = CullMode.None; gd.VertexDeclaration = new VertexDeclaration( gd, VertexPositionColor.VertexElements);   gd.RenderState.AlphaBlendEnable = true; gd.RenderState.SourceBlend = Blend.SourceAlpha; gd.RenderState.DestinationBlend = Blend.InverseSourceAlpha; gd.RenderState.BlendFunction = BlendFunction.Add; efekt.Begin(); … Funkcja mieszanie powinna być ustalona w metodzie Initialize

Mieszanie kolorów Wyłączanie blendingu 6/7 protected override void Draw(GameTime gameTime) { … pass.End(); } efekt.End();   gd.RenderState.AlphaBlendEnable = false; base.Draw(gameTime); Po wyłączeniu blendingu kolejne przedmioty będą nieprzezroczyste bez względu na wartość alfa ich kolorów

Mieszanie kolorów Zmiana kanału alfa kolorów trójkątu 6/7 static Color kolor1 = Color.Red; static Color kolor2 = Color.White; static Color kolor1 = new Color(Color.Red, 128); static Color kolor2 = new Color(Color.White, 128); private VertexPositionColor[] werteksy = new VertexPositionColor[6]{ //trojkat czerwony new VertexPositionColor(new Vector3(1, -1, -0.1f), kolor1), new VertexPositionColor(new Vector3(-1, -1, -0.1f), kolor1), new VertexPositionColor(new Vector3(0, 1, -0.1f), kolor1), //trojkat bialy new VertexPositionColor(new Vector3(1, -1, 0.1f), kolor2), new VertexPositionColor(new Vector3(-1, -1, 0.1f), kolor2), new VertexPositionColor(new Vector3(0, 1, 0.1f), kolor2)};

Mieszanie kolorów Trójkąty przezroczyste 6/7 Mieszanie kolorów Trójkąty przezroczyste Pierwszy rysowany jest trójkąt czerwony, po nim biały Gdy bliżej jest trójkąt biały: Kolor trójkąta czerwonego jest ciemniejszy ze względu na tło. Jego obraz przekazywany jest do bufora głębi Kolor trójkąta białego mieszany jest z czerwonym, co daje różowy Test głębi (odległość od kamery): biały < czerwony Rysowany jest biały (różowy) Gdy bliżej jest trójkąt czerwony: Kolor trójkąta czerwonego jest ciemniejszy ze względu na tło. Jego obraz przekazywany jest do bufora głębi Kolor trójkąta białego mieszany jest z czerwonym, co daje różowy Test głębi (odległość od kamery): czerwony < biały Rysowany jest czerwony (ciemny), który nie jest zmieszany z białym bo był renderowany wcześniej

Mieszanie kolorów Trójkąty przezroczyste w odwróconej kolejności 6/7 Mieszanie kolorów Trójkąty przezroczyste w odwróconej kolejności Zmiana kolejności nie rozwiązuje problemu:

Mieszanie kolorów Proste pseudo-rozwiązanie problemu 6/7 Mieszanie kolorów Proste pseudo-rozwiązanie problemu Wyłączenie bufora głębii i mieszanie sumujące: gd.RenderState.DepthBufferEnable = false; gd.RenderState.DestinationBlend = Blend.One;

Mieszanie kolorów Poprawne rozwiązanie problemu przezroczystości 6/7 Mieszanie kolorów Dygresja o kwaternionach Kwaterniony to czwórki liczb analogiczne do liczb zespolonych q = ix+jy+kz+w = (x, y, z, w) Dobrze nadają się do opisu obrotów Jeżeli q to kąt obrotu wokół osi (x, y, z), to kwaternion: q = (sx, sy, sz, c), gdzie s = sin(q/2), c = cos(q/2) Mając kwaternion możemy łatwo obliczyć kąt obrotu: q = 2 arccos(w) Poprawne rozwiązanie problemu przezroczystości Sortowanie obiektów przezroczystych Moglibyśmy zdefiniować pole klasy Game1, które przechowywałoby kąt obrotu aktualizowane w metodzie Game1.Update. Zamiast tego odczytamy w metodzie Game1.Draw bieżący kąt obrotu z macierzy świata efekt.World. Do rozebrania macierzy na części służy metoda Matrix.Decompose: public bool Decompose ( out Vector3 scale, out Quaternion rotation, out Vector3 translation ) Do rozebrania macierzy na części służy metoda Matrix.Decompose: Vector3 skalowanie, translacja; Quaternion obrot; efekt.World.Decompose(out skalowanie, out obrot, out translacja); double katObrotu = 2 * Math.Acos(obrot.W); Do rozebrania macierzy na części służy metoda Matrix.Decompose: public bool Decompose ( out Vector3 scale, out Quaternion rotation, out Vector3 translation ) Wstawić do metody Game1.Draw!

Mieszanie kolorów Poprawne rozwiązanie problemu przezroczystości 6/7 Mieszanie kolorów Poprawne rozwiązanie problemu przezroczystości W pętli rysowania w metodzie Game1.Draw: if (katObrotu > -MathHelper.PiOver2 && katObrotu < MathHelper.PiOver2) { //czerwony, bialy gd.DrawUserPrimitives<VertexPositionColor>(PrimitiveType.TriangleList, werteksy, 0, 1); gd.DrawUserPrimitives<VertexPositionColor>(PrimitiveType.TriangleList, werteksy, 3, 1); } else //bialy, czerwony

Mieszanie kolorów Poprawne rozwiązanie problemu przezroczystości 6/7 Mieszanie kolorów Poprawne rozwiązanie problemu przezroczystości Sortowanie obiektów przezroczystych

Mieszanie kolorów Mgła Do Game1.Initialize dodajmy: 6/7 Mieszanie kolorów Mgła Do Game1.Initialize dodajmy: efekt.FogStart = 0.2f; efekt.FogEnd = 20; efekt.FogColor = Color.White.ToVector3(); efekt.FogEnabled = true; Można manipulować położeniem kamery, aby zobaczyć efekt mgły (im dalej, tym bielszy). Efekt nie dotyczy przestrzeni (mgła zmienia tylko kolor brył)

Mieszanie kolorów Mgła 6/7 Mieszanie kolorów Mgła Korytarz zbudowany z sześcianu (odwrócony CullMode)

Rzutowanie cieni na płaszczyznę 7/7 Rzutowanie cieni Dlaczego w XNA, DirectX i OpenGL nie ma wbudowanego algorytmu generowania cieni? Popularne techniki generowania cieni: Cienie rzutowane na płaszczyznę (plane projected shadows) Odwzorowywanie cieni (shadow mapping) Cienie objętościowe (volumetric shadows) Rzutowanie cieni na płaszczyznę Shadow mapping Cienie objętościowe Szybkość Tak Nie Dokładność Zależy od jakości tekstury Cienie własne „Odbiorcy” cienia Miękkie cienie: http://graphics.cs.lth.se/research/shadows/

6/7 Projekt startowy Projekt można pobrać z http://www.fizyka.umk.pl/~jacek/dydaktyka/3d/xna/ita106/ Plik 3A5-0 Oswietlenie (teoria) - Rzutowanie cieni – Start.zip Obracający się sześcian i płaskie podłoże Oba obiekty zbudowane z komponentów Prostopadloscian Domyślne źródło światła (nr 0) w kierunku (1,1,1)

Rzutowanie cieni Źródło światła (efekt.DirectionalLight0) 7/7 Rzutowanie cieni Źródło światła (efekt.DirectionalLight0) Tu powinien znaleźć się cień sześcianu

Rzutowanie cieni Uproszczenie: źródło światła w nieskończoności 7/7 Rzutowanie cieni Uproszczenie: źródło światła w nieskończoności Tu powinien znaleźć się cień sześcianu

7/7 Rzutowanie cieni Metoda rzutowania cieni polega na ponownym narysowaniu obiektu rzutującego cień, ale spłaszczonego i w ciemnym kolorze. Macierz rzutowania punktu na płaszczyznę XNA oferuje tylko macierz rzutowania równoległego Matrix.CreateShadow Obiekt 3D, ale jego wszystkie werteksy w jednej płaszczyźnie

7/7 Rzutowanie cieni Zalety metody rzutowania cieni (plane projected shadows) prostota i szybkość (dwa przebiegi) można jej używać zarówno z modelami, jak i funkcjami rysującymi obiekty dokładność odwzorowania (każdy piksel) Zasadnicza wada: ograniczenie do płaskiego podłoża (np. wyścigi samochodowe)

W naszym projekcie nie można wyłączyć bufora głębi 7/7 Rzutowanie cieni 1. Deklarujemy referencję do instancji komponentu: private Prostopadloscian cienSzescianu; W naszym projekcie nie można wyłączyć bufora głębi 2. W metodzie Game1.Initialize tworzymy komponent, i rejestrujemy go: cienSzescianu = new Prostopadloscian(this,efekt,1,1,1,Color.Black); this.Components.Add(cienSzescianu); 3. W metodzie Game1.Update „spłaszczamy” go: efekt.World *= obroty szescian.World = efekt.World; cienSzescianu.World = efekt.World * Matrix.CreateShadow(new Vector3(1,1,1), new Plane(Vector3.Up,1.70f)); Trzeba wyłączyć cieniowanie cienia efekt.World *= obroty szescian.World = efekt.World; cienSzescianu.World = efekt.World * Matrix.CreateShadow(new Vector3(1,1,1), new Plane(Vector3.Up,1.6999f));

7/7 Rzutowanie cieni 4. Tworzymy nowy efekt dla cienia i wyłączamy światło: BasicEffect efektCienia = (BasicEffect)efekt.Clone(graphics.GraphicsDevice); efektCienia.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efektCienia.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); cienSzescianu = new Prostopadloscian(this,efektCienia,1,1,1,Color.Black); this.Components.Add(cienSzescianu); BasicEffect efektCienia = (BasicEffect)efekt.Clone(graphics.GraphicsDevice); efektCienia.DirectionalLight0.DiffuseColor = Color.Black.ToVector3(); efektCienia.DirectionalLight0.SpecularColor = Color.Black.ToVector3(); cienSzescianu = new Prostopadloscian(this,efektCienia,1,1,1,Color.DarkGreen); this.Components.Add(cienSzescianu);