evcil.net noktanın egemenliği

1911 / 020

C# ve OpenGL

OpenGL (Open Graphics Library - Açık grafik kütüphanesi), mevcut OpenGL
destekli grafik donanımınızın sağladığı olanaklardan, uygulamalarınızda sonuna kadar
faydalanabilmeniz için kullanıcıya, kolay anlaşılabilir ve kullanılabilir fonksiyonlar
sağlayan endüstri standartı haline gelmiş bir grafik kütüphanesidir.
İsmindeki Açık (Open) kelimesi OpenGL'in açık kaynak kodlu olduğunu değil,
ARB (Architecture Review Board - Yapı geliştirme, takip kurulu) olarak adlandırılan
ve endüstrinin önde kuruluşları (3DLabs, ATI, NVidia, IBM, Mirosoft, SGI vs.) tarafından
geliştirilen, yani bir şirketin tekeli altında olmayan bir kütüphane olduğunu göstermektedir.
Mevcut sürümü 1.4 olan kütüphanenin 2. sürümü üzerine çalışmalar ARB tarafından
sürdürülmektedir. OpenGL, yine ARB tarafından kütüphanenin yeni sürümüne kadar güncel
tutulmasını sağlayacak olan ve yeni teknolojilerin kullanılmasına izin veren "eklentiler"
(extensions) ile birlikte kullanıldığında, güncel bir oyun programlayabilmek için
fazlasıyla yeterli bir kütüphanedir.

OpenGL, üzerinde çalıştığı platform ve içinde kullanıldığı programlama dilinden
bağımsızdır. Windows, Linux, BeOs, OS/2 vs. altında çalışır ve fonksiyonları
C/C++/C#, Java, Ada, Fortran, Perl, Phyton vs. tarafından çağırılabilir.
OpenGL C dili kullanılarak yazıldığı ve object-oriented olmadığı için, C#
ve Java gibi yalnızca object-oriented olan dillerle birlikte kullanılabilmesi için
OpenGL fonksiyonlarını belli sınıflar (class) dahilindeki metodlar olarak çağırabilmemize
olanak sağlayacak, özel olarak yazılmış (ARB den bağımsız) dönüştürücü (wrapper)
sınıflara ihtiyaç duyarız. C# altında OpenGL fonksiyonlarına erişebilmemizi sağlayan
bu dönüştürücü kütüphane CsharpGL adı altında title="CSGL">csgl.sourceforge.net adresinde açık kaynak kodlu olarak geliştirilip,
kullanıma sunulmaktadır. Paketin, bu yazının yazılma aşamasındaki en son sürümü
csgl.1.4.1.dll adı altında sitede sunulmakta idi ve gl, glu
ve bunlardan ayrı olarak geliştirilen ve yüksek seviye işlemleri kolaylaştıran glut
kütüphanesininde tamamına yakınını desteklemekteydi.

OpenGL kütüphanesinin C# altında kullanılabilmesi için öncelikle csgl.versiyonnumarası.dll
paketi csgl.sourceforge.net downloads
bölümünden indirilip, paketin içindeki libinstall klasörünün altındaki install.bat
dosyası çalıştırılmalıdır. (Kurulum dosyası yolu: csgl.versiyonnumarası.dll/ libinstall/install.bat)
Bu script, csgl.dll ve csgl.native.dll dosyalarını Windows işletim sisteminizin
Syste32 klasörü altına kopyalar. ( %SystemRoot%system32) Kod yazma işlemine başlayabilmek
için .NET geliştirme ortamınızda yeni bir C# Windows uygulaması açtıktan sonra,
bütünleşik geliştirme ortamınızın (IDE) sağ tarafında yer alan Solution Explorer
penceresinin içinde bulunan projenizin referanslar kısmına csgl kütüphanesini
eklemeniz gerekmektedir. (Bu işlem References düğümüne sağ tuşla tıkladıktan sonra
Add Reference komutunu çalıştırarak açılan pencerede Gözat (Browse) tuşu ile %systemRoot%System32
altındaki csgl.dll inin seçilerek projeye eklenmesi ile gerçekleştirilebilir)

width="213" />

Artık projemiz OpenGL kullanılabilir hale gelmiştir. İşin eğlenceli kısmına yani
kod yazmaya geçebiliriz. Şimdi C# OpenGL kodunu bölüm bülüm inceleyelim. Öncelikle
OpenGL fonksiyonlarını kullanabilmemiz için CsGL.OpenGL isim-uzayını ekliyoruz.

using System;
using System.Drawing;
using System.Windows.Forms;
using CsGL.OpenGL; // C#GL OpenGL isimuzayının eklenmesi

Daha sonra Form sınıfından, OpenGL uygulamamız için uyarlamak üzere yeni bir sınıf
türetiyoruz ve özelliklerini atıyoruz.

public class GLCanvas : Form
{
// View adı ile tanımladığımız OpenGL
// kontrolüne ait yeni bir üye oluşturulması
View view = new View();

public GLCanvas() // Sınıfın yapıcı (constructor) metodu
{

Text = "C# OpenGL Merhaba Dünya"; // Pencere başlığının ayarlanması
view.Dock = DockStyle.Fill; // OpenGL kontrolünün pencerenin içini tamamiyle
// dolduracak şekilde ayarlanması
Controls.Add(view); // Kontrolün pencereye eklenmesi
}

public static void Main()

{
GLCanvas glc = new GLCanvas(); // GLCanvas türünden yeni bir üye oluşturulması
Application.Run(glc); // Uygulamanın çalıştırılması
}
}

Yukarıdaki kısım, projemizi çalıştırıp ekrana pencerenin çıkmasını sağlayan kısımdı,
asıl işi yapan şimdi inceleyeceğimiz bölümdür. Bu kısım OpenGLControl arayüzünden
(interface) türettiğimiz kontrolün metodlarını yazdığımız kısımdır.

class View : OpenGLControl

{
// glDraw metodu, programın ana kısmı olarak görebileceğimiz
// bütün çizim işlerinin yapıldığı kısımdır. Controlumüzün

// ekrana her yeniden çizilişinde bu metod çağırılır. Yani OpenGL
// uygulamamızın tazeleme oranı 100 fps (frame per second - saniyedeki
// kare sayısı) ise, bu metod içindeki işlemler saniyede 100 defa

// yapılıyor demektir.
public override void glDraw()
{
// glClear ile renk ve derinlik tampon beleklerini boşaltarak, ekranı temizliyoruz
GL.glClear(GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT);

// glLoadIdentity şu anda kullanmakta olduğumuz matrisi sıfırlar (varsayılan hale
çevirir)
GL.glLoadIdentity();
// glTranslatef kullanarak ekrana çizilecek olan cisimleri bulundukları yerden
// parametre olarak verdiğimiz koordinatlara taşırız. Burada çizeceğimiz çizgiyi
// daha iyi görülebilir olması için z ekseninde 10 birim ileri taşıyoruz
GL.glTranslatef( 0.0f, 0.0f, -10.0f );
// glColor3f RGB cinsinden çizim rengini belirlememizi sağlar, değerler 0 ile 1
// arasında olmalıdır
GL.glColor3f(0.5f, 1, 1);

// Burdan itibaren esas çizimin yapıldığı kısımdır
// Aşağıdaki 4 satır kod ekrana çizgi çizdirir
// Çizgi, Begin ve End metodları arasına, Begin metoduna

// parametre olarak çizgi çizmek istediğimizi belirten GL_LINES
// sabiti gönderildikten sonra 3 Boyutlu uzayımızda koordinatları
// glVertex3d metoduna parametre olarak verilen iki nokta tanımlayarak
// çizilmiştir. End metodu aralarına çizgi çizilmek için verilen noktaların
// bittiğini belirtmektedir. Diğer sabitlerden bazıları; GL_LINE_LOOP,

// GL_POLYGON, GL_TRIANGLES vs.
GL.glBegin(GL.GL_LINES);
GL.glVertex3d(0.0, 0.0, 0.0);
GL.glVertex3d(2.0, 2.0, 0.0);
GL.glEnd();
}

Not: OpenGL yapısı ve fonksiyonları hakkında: OpenGL durum (state) bazlı
çalışır, yani OpenGL fonksiyonlarını kullanarak değiştirdiğimiz bir değer, yine
aynı fonksiyon tarafından değiştirilmeden program akışı içinde önceki değerinde
kalır. Daha açık olmak için, örnek olarak, glColor3f metodu kullanarak çizim rengi
belirlendiğinde, bu komuttan sonraki bütün çizimler, yine bu metodla aksi belirtilinceye
kadar, aynı renkte çizilmeye devam eder. Metod isimlerine aşinalık kazanmak için
biraz irdeleyecek olursak, hepsi gl ön eki ile başlar ve atama yapan komutların
sonundaki 3f, 3d, 2i vs. eklerinin de sayısal kısmı fonksiyona gönderilecek olan
parametre sayısını, ardından gelen harf de parametrelerin tipini ( float, integer,
double gibi) belirler.

InitGLContext, GL penceremizin (kontrolümüzün veya ''canvas''ın da denebilir) özelliklerini
belirlemek için kullanılır. Işıklandırma değerleri ve sahnedeki (scene) sabit ışıkların
pozisyonları da genelde bu kısımda belirlenir. Pencereye burda belirtilen özellikler
doğrultusunda çizim yapılır.

protected override void InitGLContext()

{
// glShadeModel, Gölgeleme modelini belirler,

// GL_SMOOTH, yumuşak geçişli gölgelemeye karşılık gelir
GL.glShadeModel(GL.GL_SMOOTH);

// glClearColor, arka plan rengini belirler,

// parametreleri RGB Alpha türünden 0-1 arasındadır
GL.glClearColor(0.0f, 0.0f, 0.0f, 0.5f);
// glClearDepth metodu derinlik tampon belleğindeki herbir pixele
// hangi değerin atanacağını belirtir
GL.glClearDepth(1.0f);
// GL_DEPTH_TEST özelliğinin aktif hale getirilmesi ve derinlik fonksiyonun
// GL_LEQUAL olarak ayarlanması, sahnede birbirlerinin görünümünü engelliycek

// şekilde arka arkaya duran nesnelerden arkada olanların ekrana çizilmesini
// engelleyerek performans artışını sağlamak amacıyla kullanılmaktadır
GL.glEnable(GL.GL_DEPTH_TEST);
GL.glDepthFunc(GL.GL_LEQUAL);
// glhint metodu ve gönderilen aşağıdaki parametreler, OpenGL render
// motorunu daha iyi sonuçlar verecek doğru perspektif hesaplamaları
// yapması için zorlamak için kullanılmaktadır
GL.glHint(GL.GL_PERSPECTIVE_CORRECTION_HINT, GL.GL_NICEST);
}

OnSizeChanged metodu pencerenin boyutunun değiştirilmesi olayında çalışır. GL kontrolü
içindeki çizimin, nesnelerin oranlarının, pencerenin yeni aldığı boyutlara göre,
doğru görüntüyü sağlamak için, yeniden hesaplanıp ekrana çizilmesini sağlamak içindir.
Bu metod yapılacak olan uygulamalarda %99 aynı kaldığı için üzerinde çok fazla değişiklik
yapılması gerekmez!

protected override void OnSizeChanged(EventArgs e)
{
base.OnSizeChanged(e);

Size s = Size;
// Yeni boyutlara göre görünüş oranlarının yeniden hesaplanması
double aspect_ratio = (double)s.Width /(double) s.Height;

// Matris biçimi projeksiyona çevrilip sıfırlandıktan sonra
// yeni görünüş oranlarıyla perspektif hesaplanarak, matris modelview
// olarak yeniden atanır ve sıfırlanır, oranlar pencerenin yeni boyutlarına
// uygun olarak yeniden hesaplanmış ve sahnenin perspektifi ayarlanmış olur.
GL.glMatrixMode(GL.GL_PROJECTION);
GL.glLoadIdentity();
GL.gluPerspective(45.0f, aspect_ratio, 0.1f, 100.0f);

GL.glMatrixMode(GL.GL_MODELVIEW);
GL.glLoadIdentity();
}
} // OpenGl kontrol sınıfımızın sonu

width="589" />

Görüldüğü gibi, OpenGL sağladığı geniş olanakların yanısıra kullanımı kolay
olan bir kütüphanedir. Bu uygulamada OpenGL yapısını daha iyi anlayabilmek için
ekrana bir çizgi çizdirmekle yetindik. Grafik ve OpenGL konusunda daha detaylı bilgi
almak için www.opengl.org (OpenGL in
resmi sitesidir) adresine, örnek program kodları içinde çok sayıda OpenGL dersinin
bulunduğu nehe.gamedev.net adresine
başvurabilirsiniz.

Yazan: Emre Bilgili

No description. Please complete your profile.
Comments (0) Trackbacks (0)

No comments yet.


Leave a comment


No trackbacks yet.

Sayfalar

Kısımlar

Desteklediklerimiz

Ay bazında arşiv

Haberleşme