JAVA’da Grafik, Animasyon ve Multimedia
JAVA’da Grafik, Animasyon ve Multimedia
1.1 Giriş
Bilgisayar grafikleri, bilgisayarda yapılan çizimler ve resimlerdir. Animasyonlar, bilgisayardaki çizimleri hareketlendirme uygulamalarıdır. Multimedia ise ses, metin, resim, grafik, animasyon ve film gibi öğelerin birarada kullanılışıdır.
Geleneksel C ve C++, genelde karakter modunda bir giriş/çıkış (I/O) ile sınırlı idi. C++'ın bazı sürümleri, grafik yapmayı sağlayan platform bağımlı sınıf kütüphanelerine sahipti fakat bu kütüphenlerin kullanımı ile yapılan uygulamalar taşınabilir olmuyordu. Java'nın grafik özellikleri de platform bağımsız yani taşınabilirdir. Grafik yoğunluklu Java Applet'leri geliştirilebilir ve dünyanın her yerindeki insanlara WWW aracılığı ile ulaştırılabilir. Alan kişiler de yerel Java platformlarında kolaylıkla bu programları çalıştırabilirler.
1.2 Grafik
Bu bölümde, java.awt paketinin ekran üzerindeki çizim yetenekleri tanıtılacaktır. Bu bölümle ilgili olarak, java sınıf hiyerarşisinin bir parçası Şekil 1'de görülmektedir.
Şekil 1: java.awt hiyerarşisinin bir parçası
Sınıflar : Şekildeki her bir sınıf, Object sınıfını doğrudan devralmaktadır.
Color : Renklerle ilgili metotları ve sabitleri içermektedir.
Font : Yazıtipleri (font) ile ilgili metotları ve sabitleri içermektedir.
Fontmetrics: Font bilgisinin elde edilmesi ile ilgili metotları içermektedir.
Polygon : Çokgen çiziminde kullanılan metotları içermektedir.
Graphics : Metinlerin, çizgilerin, dikdörtgenlerin ve diğer şekillerin çizimi ile ilgili metotları içermektedir.
Toolkit : Sistemin grafik bilgisinin alınması ile ilgili metotları içermektedir (Görüntülenebilir yazıtipleri, ekran çözünürlüğü gibi).
Java ile çizim yapmaya başlamadan önce, java koordinat sistemini anlamak gerekir. Java koordinat sistemi, ekran üzerindeki her olası noktayı tanımlamakta kullanılan düzendir. Normal olarak ekranın sol üst köşesi orijindir (0,0). Koordinat çifti, x koordinatı (yatay koordinat) ve y koordinatından (düşey koordinat) oluşmaktadır. x koordinatı orijinden yatay olarak sağa doğru uzaklıktır. y koordinatı da orijinden düşey olarak aşağı doğru uzaklıktır. Yazılar ve şekiller ekran üzerinde koordinatları belirtilerek görüntülenirler. Koordinat birimi piksel'dir (pixel). Piksel, koordinat çözünürlüğünün en küçük birimidir (Şekil 2).
Şekil 2: Java koordinat sistemi (Birimler piksel cinsindendir)
1.3 Grafiklerin durumları ve grafik nesneleri
Grafiklerin durumu ekrana çizim yapmayı sağlar. Bir graphics nesnesi, bilginin nasıl çizileceğini kontrol ederek grafiklerin durumunu yönetir. Graphics nesneleri, çizim, yazıtipi ve renk işlemleri gibi metotlar içerir. Applet'in paint metodundaki argümanlardan birisi olan Graphics nesnesi g, applet grafiklerinin durumunu yönetir.
Çizim için bir graphics nesnesi kullanılmalıdır. Graphics sınıfı soyut sınıftır. Örneklenemez. Bunun nedeni, Java'nın taşınabilirliğinde aranmalıdır. Çünkü, çizimlerin java'yı destekleyen her platformda farklı şekilde yapılmasından dolayı, çizim yeteneklerini tüm sistemlerde implement eden sadece bir tane sınıfın olması uygun değildir. Örnek olarak üzerinde windows çalışan bir PC'nin bir dikdörtgen çizimini sağlayan grafik yetenekleri, bir unix iş istasyonunun dikdörtgen çizmesini sağlayan grafik yeteneklerinden farklıdır. Macintosh'unkiler de bu ikisinden farklıdır. Java her platforma uyarlandığında, tüm çizim yeteneklerinin implement edildiği bir Graphics sınıfı oluşturulur. Bu implementasyon, platform bağımsız bir şekilde grafik kullanan programları yazmamızı sağlayan arayüzü sunan Graphics sınıfının yardımı ile bizden gizlenir.
Component sınıfının paint metodu Graphics nesnesini argüman olarak alır. Graphics nesnesi, bir Component için bir çizim işlemi olduğunda paint metoduna geçirilir. Component sınıfı AWT içindeki sınıfların çoğunun superclass'ıdır. paint metodunun başlığı şu şekildedir :
public void paint(Graphics g) Graphics nesnesi g, sistemin türetilmiş Graphics sınıfının bir nesnesine referans alır. Component sınıfı, Applet sınıfının dolaylı base class'ıdır. Applet sınıfının yeteneklerinin çoğu, component sınıfından devralınır. Component sınıfı içinde tanımlı paint metodu normalde birşey yapmaz, programcı tarafından override edilmelidir.
Paint metodu nadiren programcı tarafından çağrılır. Bunun nedeni grafik çiziminin event-driven bir işlem olmasıdır. Applet, en başta çalıştırıldığında, paint metodu otomatik olarak çağrılır (Applet'in init ve start metotlarının ardından). Paint metodu, bir olay (event) olduğunda tekrar çağrılır (kullanıcının applet'in boyutlarını değiştirmesi gibi).
Programcının paint metodunu çağırması gerektiğinde çağrı, Component sınıfının repaint metodu ile yapılır. repaint metodu, Component sınıfının update metodunu, önceki çizimlerden oluşan Component zeminini silmek üzere çağırır ve sonra update, paint'i doğrudan çağırır. repaint metodu overridden değildir. update metodu nadiren çağrılır ve bazen overridden'dır. update metodunu override etmek animasyonların düzgünleştirilmesi için yararlıdır. Repaint ve update başlıkları şu şekildedir :
public void repaint()public void update(Graphics g)update metodu, paint metodu tarafından otomatik olarak sunulan, Graphics nesnesini argüman olarak alır.
1.4 String'lerin, character'lerin ve byte'ların çizimi
String'lerin, character'lerin ve byte'ların çizimi için Graphics metotları
public abstract void drawString (String string, // string to be drawnint x, // x coordinateint y ) // y coordinateDraws a string in the current font and color at the coordinate (x,y).public void drawChars( char chars[ ], // array to be drawn int offset, // starting subscript (index) int number, // number of elements to drawint x, // x coordinateint y ) // y coordinateDraws series of characters in the current font and color at the coordinate (x,y).public void drawBytes( byte bytes[ ], // array of bytes int offset, // starting subscript (index) int number, // number of elements to drawint x, // x coordinateint y ) // y coordinateDraws series of bytes in the current font and color at the coordinate (x,y).(x,y), string'in sol alt köşesine denk geleceği için (0,0)'a çizilecek bir String görünmeyecektir.
1.5 Renk denetimi
Renkler, ekran görüntüsünü güzelleştirir. Kullanıcılar en önce programın renklerinden etkilenirler.
Renk sabitleri ve metotları, Object sınıfını devralan Color sınıfı içinde tanımlıdırlar. Önceden tanımlanmış renk sabitleri, renk metotları ve constructor'ları şu şekildedir (Ayrıca renk ile ilgili Graphics metotlarından da ikisi gösterilmiştir) :
public final static Color orange orange 255,200,0public final static Color pink pink 255,175,175public final static Color cyan cyan 0,255,255public final static Color magenta magenta 255,0,255public final static Color yellow yellow 255,255,0public final static Color black black 0,0,0public final static Color white white 255,255,255public final static Color gray gray 128,128,128public final static Color lightGray lightGray 192,192,192public final static Color darkGray darkGray 64,64,64public final static Color red red 255,0,0public final static Color green green 0,255,0public final static Color blue blue 0,0,255public Color( int r, // 0-255 red content int g, // 0-255 green contentint b) // 0-255 blue contentCreates a color based on red, green and blue contents.public Color( float r, // 0.0-1.0 red content float g, // 0.0-1.0 green contentfloat b) // 0.0-1.0 blue contentCreates a color based on red, green and blue contents.public int getRed() // Color classreturns a value between 0 and 255 representing the red content.public int getBlue() // Color classreturns a value between 0 and 255 representing the blue content.public int getGreen() // Color classreturns a value between 0 and 255 representing the green content.public abstract Color getColor() // Graphics classReturns a Color object representing the current color for the graphics context.public abstract void setColor(Color c) // Graphics classSets the current color for drawing with the graphics context.Her renk, bir RGB (Red, Green, Blue) değerinden oluşturulur. Üç parçadan oluşmaktadır ve her bir parça 0, 255 arası tamsayı veya 0.0 ile 1.0 arasında reel sayı olabilir. İlk parça kırmızı, ikinci parça yeşil ve üçüncü parça mavi miktarını belirtir. Parçanın değeri büyüdükçe, o rengin miktarı da büyür. Java, programcılara 256*256*256 (yaklaşık 16.7 milyon) renk seçeneği sunar. Tüm bilgisayarlar, bu renklerin tümünü görüntüleme yeteneğine sahip değildirler. Böyle bir durumda, bilgisayar en yakın rengi gösterecektir.
1.6 Yazıtipi (font) denetimi
Yazıtipi metotlarının ve sabitlerinin çoğu, Object sınıfından devralan Font sınıfının parçalarıdır. Font sabitleri, Font constructor ve Graphics metodu setFont aşağıdaki gibidir :
public final static int PLAIN // Font class A constant representing a plain font stylepublic final static int BOLD // Font class A constant representing a bold font stylepublic final static int ITALIC // Font class A constant representing a italic font stylepublic Font( String s, // font name int style, // font styleint size) // font point sizeCreates a Font object with the specified font, style and size.public abstract void setFont(Font f) // Graphics classSets the current font to the font, style and size specified by the Font object f.yazıtipi biçimleri (font styles) : PLAIN, BOLD, ITALIC
Font constructor üç argüman alır :
font name (yazıtipi ismi) : Courier, Helvetica, TimesRoman gibi programın çalıştığı sistemin desteklediği yazıtipi.
font style (yazıtipi biçimi) : Font.PLAIN, Font.ITALIC, Font.BOLD gibi normal, eğik ve koyu biçim. Aynı anda hem koyu hem de eğik yazı için Font.ITALIC+Font.Bold kullanılabilir.
font size (yazıtipi boyutu) : Yazıtipi boyutları noktalar cinsindendir. Bir nokta, bir inç'in 72'de biridir.
Bunlar dışında, anlık yazıtipi bilgisini elde etmeye yarayan metotlar, yazıtipi biçimini test eden metotlar ve yazıtipi ölçütlerini elde etmeye yarayan metotlar da vardır. Yazıtipi ölçütleri yazıtipinin yüksekliği (height), yazıtipinin taban çizgisinden aşağısındaki kısmı (descent), yazıtipinin taban çizgisinden üstündeki kısmı (ascent), height ve ascent arasındaki fark (leading) gibi değerlerdir (Şekil 3).
Şekil 3: Yazıtipi ölçütleri (font metrics)
Toolkit, java ve sistem arasında etkileşim kurarak sistem hakkında bilgi elde edilebilmesini sağlar. Toolkit sınıfı, Object sınıfını devralır. Örnek olarak, Toolkit sınıfının getFontList metodu, sistemde yüklü olan font isimlerini String'ler dizisi olarak döndürür.
1.7 Çizgi
(x1,y1) noktası ile (x2,y2) noktası arasında şu anki renk ile çizgi çizilmesi :
public abstract void drawLine(int x1, int y1, int x2, int y2) // Graphics classÖrnek : g.drawLine(10,10,230,95);
1.8 Dikdörtgen
Sol üst köşesinden (x,y), width genişliğinde ve height yüksekliğinde şu anki renkte bir dikdörtgen çizim metodu :
public void drawRect(int x, int y, int width, int height) // Graphics classSol üst köşesinden (x,y), width genişliğinde ve height yüksekliğinde içi şu anki renk ile dolu bir dikdörtgen çizim metodu :
public void fillRect(int x, int y, int width, int height) // Graphics classSol üst köşesinden (x,y), width genişliğinde ve height yüksekliğinde zemin renginde bir dikdörtgen çizim metodu :
public void clearRect fillRect(int x, int y, int width, int height)// Graphics class1.9 Yuvarlak Köşeli Dikdörtgen
Şu anki renkte ve belirtilen genişlik ve yükseklikte yuvarlak köşeli dikdörtgen çizim metodu (arcWidth, köşesinden itibaren ne kadar genişlikte bir bölümünün, arcHeight de köşesinden itibaren ne kadar yükseklikte bir bölümün yuvarlatılacağını göstermektedir):
public abstract void drawRoundRect(int x, int y, int width, int height, int arcWidth, int arcHeight) // Graphics classarcWidth ile arcHeight'in aynı olması durumunda köşelerde çeyrek daireler oluşur.
Yuvarlak köşeli ve içi dolu (katı) dikdörtgen çizim metodu ise şu şekildedir :
public abstract void fillRoundRect(int x, int y, int width, int height, int arcWidth, int arcHeight) // Graphics class1.10 Üç Boyutlu Dikdörtgen
Üç boyutlu dikdörtgen çizim metodu (b true olduğunda yükseltilecek, false olduğunda alçaltılacaktır) :
public void draw3DRect(int x, int y, int width, int height, Boolean b)// Graphics classİçi dolu üç boyutlu dikdörtgen çizim metodu :
public void fill3DRect(int x, int y, int width, int height, Boolean b)// Graphics class1.11 Oval (Elips)
Kendisini çevreleyen dikdörtgenin sol üst köşesi (x,y) olacak şekilde, belirtilen genişlik ve yükseklikte, şu anki renk ile oval çizme metodu :
public abstract void drawOval(int x, int y, int width, int height)// Graphics classKendisini çevreleyen dikdörtgenin sol üst köşesi (x,y) olacak şekilde, belirtilen genişlik ve yükseklikte, içi şu anki renk ile dolu oval çizme metodu :
public abstract void fillOval(int x, int y, int width, int height)// Graphics class1.12 Yay
Yay, bir oval parçasıdır. Yay açıları derece cinsinden ölçülür. Yay, iki açı arasında çizilir: derece cinsinden yayın başladığı başlangıç açısı (starting angle) ve yayın bitiş açısı (arc angle). Yay, bu iki açı arasında oluşturulur. Yay çizim metodu :
public abstract void drawArc(int x, int y, int width, int height,int startAngle, int arcAngle) // Graphics classİçi dolu yay çizim metodu :
public abstract void fillArc(int x, int y, int width, int height,int startAngle, int arcAngle) // Graphics classPozitif ve negatif yay açıları Şekil 4'te görülmektedir :
Şekil 4: Pozitif ve negatif yay açıları
1.13 Çokgen
Çokgenler çok kenarlı şekillerdir. ilk drawPolygon metodu üç argüman alır : x koordinatlarını içeren tamsayı dizisi, y koordinatlarını içeren tamsayı dizisi ve çokgendeki noktaların sayısı. Son noktayı ilk noktadan farklı tanımlamak açık çokgen çizmeyi sağlar yani ilk nokta ile son nokta bağlanmaz :
public abstract void drawPolygon(int xPoints[ ], int yPoints[ ], int points)İkinci drawPolygon metodu, argüman olarak Polygon nesnesi gerektirir :
public void drawPolygon(Polygon p)İçi dolu çokgenler, fillPolygon metodu ile çizilirler. Anlık renk çokgeni doldurmakta kullanılır. İçi dolu çokgenler her zaman için kapalı çokgenlerdir. Son nokta ilk noktayla aynı değilse bile otomatik olarak ilk noktaya bağlanır:
public abstract void fillPolygon(int xPoints[ ], int yPoints[ ], int points)public void fillPolygon(Polygon p)Yeni bir çokgen nesnesi oluşturmak için (nokta içermeyen) :
public Polygon() // Polygon classYeni bir çokgen nesnesi oluşturmak için :
public Polygon(int xValues[ ], int yValues[ ], int numberOfPoints)1.14 Ekran işlemleri
copyArea metodu, kare bir ekran bölgesini ekranda başka bir yere kopyalar. Argümanları 6 tanedir. İlk ikisi, kopyalanacak alanın sol üst köşesinin koordinatlarıdır. Üçüncü ve dördüncü argümanlar, kopyalanacak alanın genişlik ve yüksekliğini belirtir. Son iki argüman ise, kopyalanacak alanın ilk iki argümandan göreceli uzaklığını belirtir:
public abstract void copyArea(int x, int y, int width, int height, int dx, int dy) // Graphics class1.15 Çizim modları
Çizim modu, grafiklerin nasıl çizileceğini belirtir. Varsayılan çizim modu, şekillerin birbiri üzerine çizildiği, overwrite paint mode'dur. Şekil çizildiğinde, altında kalan tüm şekilleri kapatır. Diğer çizim modu ise XOR paint mode'dur. Tüm şekiller, üst üste biner.
XOR çizim moduna Graphics'in setXORMode metodu ile geçilir. Başlığı ve örnek bir deyim aşağıda gösterilmektedir :
public abstract void setXORMode(Color c)g.setXORMode(Color.yellow);1.16 Grafik metotlarının kullanımını gösteren bir örnek
// Demonstration of Graphics Capabilities of Java// Aybars UGUR 2.12.1997// This program was compiled and interpreted by JDK 1.1.4import java.applet.*;import java.awt.*;public class graphs extends Applet{ private int red1, green1, blue1; private int xValues[] = { 120, 140, 150, 190 }; private int yValues[] = { 10, 40, 50, 30 }; private Polygon p1; Font font1; public void init() { // RGB color values for a specific color 1 red1 = 100; green1 = 125; blue1 = 255; font1 = new Font("TimesRoman",Font.BOLD+Font.ITALIC, 24); // Adds polygon points p1 = new Polygon(); p1.addPoint(165,205); p1.addPoint(175,220); p1.addPoint(270,270); p1.addPoint(200,290); p1.addPoint(130,250); p1.addPoint(165,205); } public void paint(Graphics g) { g.setColor(new Color(red1, green1, blue1)); // set current color g.setFont(font1); // set current font g.drawString("ABC", 50, 33); // draw ABC string using color1, font1 // RGB info is displayed in the status bar showStatus("Current RGB: " + g.getColor().toString()); g.setColor(Color.red); // current color is changed to red g.drawString("Times Roman : 24", 150,33); // Draws a black horizontal line under text g.setColor(Color.black); g.drawLine(50,40, 300,40); // draws 3 rectangles g.drawRect(75,50, 50,75); g.fillRect(150,50, 50,75); g.clearRect(175,50, 50,75); // erases the half of the previous rect // draws rounded rectangles g.drawRoundRect(200,50, 50,50, 10,10); g.fillRoundRect(275,50, 50,50, 25,25); g.fillRoundRect(75,150, 25,25, 25,25); g.setColor(Color.blue); // draws 3-D Rectangles g.draw3DRect(125,150, 25,25, true); // Raised g.fill3DRect(175,150, 25,25, false); // Lowered // draws ovals g.drawOval(225,150, 25,25); g.fillOval(275,150, 50,25); // draws arcs g.drawArc(75,200, 25,25, 0,110); g.fillArc(125,200, 25,25, -70, -110); // draws polygons g.fillPolygon(xValues, yValues, 4); g.drawPolygon(p1); // copies area g.copyArea(75,150, 50,50, 25,-25); // raised roundrect }}