Kimler Sitede
Şu anda 8 ziyaretçi çevrimiçiBağış
| Kutu Yerleştirme Oyunu Yapımı |
| Makale - Visual Basic | |||
| Yazar ugokhan | |||
| Salı, 28 Ağustos 2007 18:31 | |||
|
Bu bölümde sokoban ve box world oyunlarının bir benzerini yapacağız. Bu iki oyunda amaç, bir labirent içerisinde dağınık olarak verilmiş nesneleri belirtilen karelere eksiksiz yerleştirmektir. Fakat oyunda bazı kısıtlar vardır. Nesneler hareket ettirilirken sadece itilebilir ama çekilemezler. Ayrıca, sadece bir adet nesne itilebilir. Arka arkaya duran iki nesne varsa bunlar hareket edemez. Çok güzel bir zeka oyunudurlar. Oyunları oynamamışsanız tavsiye ederim. Biz de kendi oyunumuzu yapmaya başlayalım. Labirent Yapısını OluşturmakBu oyunda en önemli şey labirent oluşturmaktır. Bunu, tıpkı yılan oyunu nda olduğu gibi iki boyutlu bir dizi üzerinde gerçekleştirebiliriz. Aşağıdaki labirent SOKOBAN oyununun 12. Level'indeki labirenttir. Görsel olarak değiştirdim tabiki. ![]()  Burada, çöp adamı kullanarak kırmızı kutuları, pembe karelere getireceğiz. Veri yerleşmesine dikkat edelim. Boşluklar : 0, Duvarlar : 1, Hedef Kareler : 2, Nesneler : 4 ve Çöp Adam : 5 değerindedir. 3 olan karenin anlamı ise oyun başlarken 1 adet nesne hedef karelerden birine yerleşmiştir. Tabiki bu değerler isteğe bağlıdır. Daha değişik değerler de verilebilir. Programı yazarken sürekli olarak tablo üzerindeki değerleri kontrol edeceğiz. Mesela çöp adamın hangi karede olduğunu bulmak için değeri 5 olan karenin koordinatlarına bakacağız. Oyunun bitip bitmediğini 4 değeri olan hiçbir kutu kalmamasından veya 3 değeri taşıyan kare sayısının hedef seviyeye eşit olmasından anlayacağız. Kısacası, iki boyutlu bir tablo üzerinde oyunla ilgili herşeyi görebileceğiz.
Şeklindeki bir kod ile işimizi görebiliriz. Labirent Dosyası OluşturmakBu oyunda bir çok labirente ihtiyacımız olacak. Bunu sürekli diziler olarak programın içerisine yerleştirmektense bir text dosyaya kaydetmek daha iyi olur. Bu şekilde istediğimiz kadar labirenti programımızın hacmini zorlamadan kaydedebiliriz. Her bir level gelince istenilen labirent dosyadan okunur. Bir labirenti kaydederken istediğiniz yapıyı kullanabilirsiniz. Ben kolay anlaşılması için şu şekilde bir yapı kullanacağım. Tablonun bir satırındaki bütün karelerin değerlerini ardarda yazarak bir satır olarak dosyaya ekleyeceğim. Böylece istediğim zaman String işlemleri ile buradan değerleri okuyabilirim. Mesela yukarıdaki tabloda, ilk satırdaki değerleri ardarda yazarsak 001111000 değerini buluruz. Bir altındaki satırda ise 001501000 değerini elde ederiz. Bu şekilde 8 satır için de aynısını yapalım. Dosya yapımız şöyle oluşur:
Başta da dediğim gibi siz farklı bir yöntemle de verileri saklayabilirsiniz. Dosya üzerinde bu şekilde bir sürü veri alt alta yerleşecek. Herhangi bir hata yapmazsak her 8 satırlık parti bir haritaya karşılık gelecektir. Böylece istediğimiz leveli yüklemek için sekizlik partilere göre dosyayı okuruz. Şimdi basit bir şekilde C:\oyun.dat adresindeki bir dosya üzerinden haritaları okumakla ilgili kodları yazalım.
Ne yaptık burada? Open komutu ile ilgili dosyayı okuma maksatlı olarak açtık. Sonra her bir satırı saydırmak için OkunanSatir adlı bir döngü yaptık. Bu değişken hangi satırda olduğumuzu tutacak. Input komutu ile bir satırlık bilgiyi okuduktan sonra tekrar bir for-next döngüsü kullanarak bu seferde okunan data içerisindeki karakterleri tek tek alıp Tablo dizisine yükledik. Karakterleri parçalarken Mid fonksiyonunu kullandık. Elde ettiğimiz karakterleri de Val fonksiyonu ile integer tipine çevirdik. Bütün döngü işlemleri bittikten sonra Close komutu ile ilgili dosyayı kapattık. Artık labirentle ilgili tüm bilgiler Tablo adlı diziye yüklendi. Bu sadece bir tane labirentin kayıtlı olduğu dosya yapısı içindir. Mesela biz 7. leveli yüklemek istiyoruz. O zaman ilk 6 oyun için sekizlik paketleri boş sayıp sonrasındaki ilk sekizlik paketi okuruz. Yani 6x8=48 satırı boş okuruz. Sonraki ilk sekiz paket 7 nolu levelin değerleridir. Bu çok mu etkin bir yöntem? Tabiki değil ama örneğe bu şekilde başladık. Siz daha etkin bir yapı kullanabilirsiniz. Şimdi bu işlemle ilgili kodları yazalım:
Bu kodu yukarıdak kod parçasının başına ilave edersek istediğimiz levelden önceki levellerin değerlerini atlamış oluruz. Birinci level için 1-1=0 olacağı için 1 to 0 durumu olur ve döngü çalışmaz. Böylece boş okuma yapılmaz ve ilk sekizlik bölüm okunur. İkinci level için 2-1=1 olacağı için döngü 1 defa çalışır ve 1x8 =8 satırı boş sayar. Dosya Okuma Sırasında Verileri AlmakAdamın bulunduğu koordinatları her seferinde tablo üzerinden takip etmek yerine dosyadan okuma sırasında bir değişkene yükleyelim. Yapacağı hareketlere göre de bu değişkenlerin değerlerini değiştirelim.
Yukarıdaki dosya okuma kodları arasına, adamın koordinatını yakalama kodlarını ekleyelim. Ayrıca ilgili leveldaki hedef kutu sayısının ne olduğunu bulmak için de kodlarımızı ekleyelim. Hedef kutu sayısı demek, yerleşim işlemini kontrol etmek için kaç tane yerleşmiş kutu olduğunun sayısıdır. Yukarıdaki resme göre 2 ve 3 değerine sahip toplam karelerdir ve 4 tane kutu yerleşmiş ise görev tamamlanmış demektir. Aynı mantıkla kutu sayıları da toplanabilir. 3 ve 4 nolu kareleri saydırabiliriz.
Böylece dosyadan okuma esnasında istenilen bilgiler toplanmış olur. Adamın HareketleriOyunda yön tuşları ile adamı hareket ettirebiliriz. Adamı hareket ettirirken dikkat edeceğimiz en önemli husus, önündeki karenin değeridir. Adam hareket ederken boş yürüyebilir veya bir kutuyu itebilir. Kutuyu itebilmesi için de bir şart vardır. O kutunun arkası boş olmalıdır. Adamın hareket edebilmesi ile ilgili mantık şeması şu şekildedir. ![]() Mesela adamın aşağı gitmesini istersek Tablo ( AdamX , AdamY + 1 ) değerine bakarız. Bu karenin değeri 1 ise adam hareket edemez. Çünkü önünde duvar vardır. Diğer durumlarda gidebilir diye düşünürsek bir küçük hata yaparız. Zira aşağı doğru iki adet kutu arka arkaya duruyorsa bu iki kutu hareket edemeyeceği için adam da hareket edemez. Yukarıdaki şekilde bunu görebilirsiniz. Aynı zamanda üzerinde kutu bulunan bir kare sadece 4 değeri değil 3 değeri de alabilir. ![]() Görüldüğü gibi adamın önündeki kare 0 veya 2 değerinde ise bu kareye gider. Eğer kare değeri 1 ise gidemez. Buraya kadar kesin sonuçlar vardır. Fakat 3 ve 4 değerleri için (yani önünde kutu varsa) ayrı bir sorgulama daha lazımdır. Bu karelerin de arkasındaki kareyi kontrol etmek gerekir (kutunun arkası boş mu, dolu mu?). Bu kareler 0 ve 2 ise adam kutuyu iterek ilerleyebilir. Aksi halde o yönde ilerleme yapamaz. Bir SELECT-CASE yapısı içerisinde IF-THEN-ELSE yapısını da kullanarak bu sorgulamaları yapabilirsiniz. Ayrıca sorgulama işlemi için Function da oluşturabilirsiniz. Bu daha etkin olur. Hareketin gerçekleşme durumunu True/False olarak bu fonksiyondan döndürebilirsiniz. Buraya kadar, sokoban ve box world tarzı oyunların yapısı hakkında kendi oluşturduğum algoritma mantığı üzerinde açıklamalar yaptım. Bu algoritmadan daha etkin ve hızlı olan başka algoritmalar da yapılabilir. Örnek yarım kalmış gibi gözükebilir fakat amacım oyuna kaynak kod yazmak değil algoritmaları açıklamaktır. Bu yüzden mantığını anladığınız andan itibaren parçaları birleştirmek size kalmıştır. Kolay gelsin. Takıldığınız noktalarda iletişim sayfasından mail atabilirsiniz. Programın full proje halini buradan indirebilirsiniz. Program dili : Visual Basic 6.0
|


