Lecture 3

advertisement
COM337 Bilgisayar Grafiği
OpenGL ile Grafik Programlama
Dr. Erkan Bostancı
İçerik
• Işık
• Resim ve Metin Görüntüleme
• Texture-mapping
Işık (1/3)
• OpenGL’de bir sahne 8 farklı ışık kaynağı kullanabilir.
• İlk ışık kaynağı için specular ve diffuse parametreleri öntanımlıdır.
• Işığın çalışması için glShadeModel ve
glEnable(GL_LIGHTING) çağrılarının yapılması gerekir.
• Işık kaynakları her yönde (omnidirectional) ışık saçar ama spot ışık
olarak da kullanılabilir.
• Renk değerlerindeki 4. parametre alpha ya da opaklık değeridir. Bu
sayede transparan veya ışığı geçiren materyaller oluşturulabilir.
• Örnek 9
Işık (2/3)
• RGBA modunda her pikselin bir opaklık
değeri vardır.
• Opaklık değerinin 0 olması o pikseli
transparan yapar.
• Opaklık anti-aliasing’de kullanılır. Kenar
(edge) içeren bir piksel’in bir kısmı
alpha değerinde tutulur.
Işık (3/3)
• Örnek 11
Pikseller, imgeler ve metin
• OpenGL’de bir pencerede bir imge göstermek için şu anki çizim
yapılacak konumu ilgili dörtgenin sol alt tarafına getirip pikselleri
çizeriz.
• Metin çizmek için, yine ilgili konuma gidip, tek tek karakterleri çizeriz.
• OpenGL hem bitmap fontları, hem de stroked fontları destekler.
• Stroke fontlar çizgilerden oluşur ve bunlara dönüşümler (scale, vs.) uygulanabilir.
• Metin çizerken, ışıkları kapatmak önemlidir, aksi takdirde OpenGL
metinlere de gölgelendirme vermeye çalışır.
• Bir nedenden dolayı 3B koordinat sisteminizi pencere koordinatlarıyla
eşleştirmek isterseniz, örnekteki reshape callback’i bunu yapar.
• Örnek 12
Görüntüleme pipeline’ını ters çevirmek
• Bazı uygulamalarda ekrandaki bir noktaya tıkladığınızda o noktanın 3B uzayda
karşılığını bulmak istersiniz.
• Bu aslında projeksiyondan dolayı eksik tanımlı (ill-defined) bir problemdir ve ters
projeksiyon net değildir.
• Fakat penceredeki (x,y) değerleriyle birlikte bir z değeri de belirtirsek, modelview
ve projection matrislerinin tersinin alınmasını sağlayabiliriz. Bu z değeri yakın ve
uzak kırpma düzlemleri arasında olmalıdır.
gluUnProject (winx, winy, winz // window position + z-value
modelmatrix, // 16-element modelview matrix
projmatrix, // 16-element projection matrix
objx, objy, objz) // pointers for object-space position
Texture-mapping (1/7)
• Bir nesneye yapılan doku ataması (texture-mapping) o nesneyi görsel
anlamda zenginleştirir.
• OpenGL 1, 2, 3 boyutlu texture’ları destekler. Texture-mapping
yalnızca RGBA modunda çalışır.
• Bu modda her pikselin bir opaklık değeri vardı.
• Örnek 13
Texture-mapping (2/7)
• OpenGL’de doku ataması yaparken 3 adım vardır:
1. Öncelikle texture olarak kullanılacak imgeyi belirlememiz gerekli. Örnekte,
init fonksiyonun içindeki 2 for döngüsü bir satranç tahtası texture’ını
oluşturuyor.
2. Ardından, OpenGL texture’ı nasıl uygulayacağını belirten parametreleri
tanımlıyoruz.
3. Son olarak da, noktalar için texture koordinatlarını tanımlıyoruz. Bu
poligonların oluşturulduğu display callback’i içinde yapılır ve texture
koordinatları poligon’un köşe koordinatları ile ilişkilendirilir.
Texture-mapping (3/7)
• Texture’ın kendisini oluşturmanın yanı sıra, bütün parametre
ayarlamaları init’in içinde yapılıyor.
• glGenTextures ve glBindTexture bir imge için texture
nesnesi oluşturur.
• Önemli olan çağrı
glTexImage2D (GL_TEXTURE_2D, 0, GL_RGBA, WIDTH,
HEIGHT, 0, GL_RGBA,GL_UNSIGNED_BYTE, image);
• İmgeyi texture map’a dönüştürür.
Texture-mapping (4/7)
• Fonksiyonun parametreleri:
1. GL_TEXTURE_2D: 2 boyutlu texture kullandığımızı belirtir.
2. 0: texture map’in derecesin en üst derece yapar. Bu mip-mapping’de
kullanılır.
3. GL_RGBA: imge verisi hem RGB kanallarını hem de alpha kanalını içerir.
4. WIDTH ve HEIGHT: imgedeki column ve row sayısı.
• 2’nin bir üstü olmalıdır.
5. 0: Texture map’in hiç kenarının olmadığını belirtir.
6. GL_RGBA: kullanılacak texel türünü belirtir.
7. GL_UNSIGNED_BYTE: piksellerin veri türünü belirtir.
8. image: asıl imge verisini içeren pointer.
Texture-mapping (5/7)
• display callback’inde texture mapping açılıyor (enable) ve
glTextEnvf yüzeydeki herhangi renk bilgisinin yerine texture olacağını
belirtiyor.
• display‘in içinde 2 tane dörtgen çiziliyor ve her köşe için tanımlanacak
texel köşe noktasından önce tanımlanıyor.
glBegin (GL_QUADS);
glTexCoord2f (0.0, 0.0);
glVertex3f (-2.0, -1.0, 0.0);
glTexCoord2f (0.0, 1.0);
glVertex3f (-2.0, 1.0, 0.0);
...
• Texture mapping nasıl yapılacağını söyleyen parametreleri de anlatacak
olursak, init’in içindeki glTexParameteri fonksiyonu bu işi yapıyor.
Texture-mapping (6/7)
• OpenGL’de texture map’in indeksleri s ve t olarak adlandırılır. Aşağıdaki
çağrılar bu indekslerin 0-1 aralığından çıktığında ne yapılması gerektiğini
söyler:
• glTexParameteri (GL_TEXTURE_2D,GL_TEXTURE_WRAP_S, GL_REPEAT);
• glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
• Burada texture’ı tekrarlatmasını söylüyoruz.
• Bir texel’in boyutunun oluşan görüntüdeki bir piksel ile tam olarak
eşleşmesi her zaman olmaz.
• Geometriye göre bazen bir texel birden çok pikseli kaplar (magnification), bazen de
bir piksel birden çok texel’i kaplar (minification).
Texture-mapping (7/7)
• OpenGL texture-mapping’i her pikseli, texture uzayındaki bir noktaya
atarken her köşe ile ilgili değerleri interpolate eder.
• Bu performans açısından hızlıdır ama görüntü açısından sorunlar yaratabilir.
Bu nedenden dolayı OpenGL bize filtreleme imkanı sunar.
• Nearest-neighbour
• Two-by-two average
• Programın hızlı çalışmasını istediğimizden nearest-neighbour kullandık:
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER,
GL_NEAREST);
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
GL_NEAREST);
Aliasing (1/2)
• Texture-mapping nasıl çalışır?
• Yüzey render edilirken, frame buffer’a
yazılacak olan yüzey pikselleri texture map’in
indekslerine çevrilir.
• Scaling ve perspektif etkilerin kullanıldığı
yüzeyler, orijinal texture map’in
scale’inden farklı görünür. Bu da aliasing
oluşturur.
• Bu sorun hareketli yüzeylerde daha fazla göze
çarpar.
Aliasing (2/2)
• Çözüm:
• Farklı scale’lerde kullanılacak farklı texture’lar kullanmak.
• Mip-mapping
• Daha düşük çözünürlüklü texture’lar kullanmak. Herbiri bir üst seviyenin yarı boyutunda.
• 32x32, 16x16, 8x8, 4x4, 2x2, 1x1 piksel boyutlarında.
Download