Yaklaşık 1 senedir Unity ile VR üzerinde çalışmaktayım. Bundan önce Unreal Engine üzerinde birkaç proje geliştirmiştim. Her iki motoru da kullanmış biri olarak Unity vs Unreal Engine karşılaştırması hakkında, internet üzerinde bulamayacağınız, klişelerden uzak bir rehber hazırlamak istedim. Sanıyorum bu foruma ilk defa gelenler kafaları çoğunlukla "Unity mi yoksa Unreal Engine mi kullansam?" olarak karışmış insanlar. Umarım biraz da olsa faydası olur bu yazdıklarımın.
Öncelikle şunu belirteyim, teknik konulara inmem gerekebilir bazı yerlerde, kafanıza takılan bir yer olursa konu altından yardımcı olmaya devam edebilirim.
Öncelikle şunu belirteyim, teknik konulara inmem gerekebilir bazı yerlerde, kafanıza takılan bir yer olursa konu altından yardımcı olmaya devam edebilirim.
- Dil:
Kullanılan dillerden başlayacak olursak, Unity C# kullanırken Unreal Engine C++ kullanmakta. C#, içerisinde pointer bulundurmayan bir dil, Java'ya oldukça benzer, kendi garbage collection sistemi var. Sözün özü, kod yazarken başınız daha az ağrır, hatalı yazdığınız kodlar dolayısıyla nadiren crash yersiniz. Unreal Engine'deki gibi "hangi class'ı nasıl nerede include etsem", "acaba hangi referansları hafızadan silmeyi unuttum da hafızam doldu bu kadar" vb. şeyler hakkında kara kara düşünmezsiniz, her class için ayrı ayrı header yazmanıza gerek kalmaz.
- Scripting:
Scripting olayına bakacak olursak, Unity'de sadece bir Script yazarsınız, scripti neyin üzerinde çalışacaksa onun üzerine attach edersiniz. Bütün kodlama mantığı bunun üzerinde ilerler.
Unreal Engine'de ise işler biraz daha derli toplu yürür. Kullandığınız scene, player controller, AI controller ve benzeri oyun motoruna ait tüm parçaların classları hazır olarak arka planda çalışır, bu class'ları istediğiniz gibi genişletebilirsiniz, her biri için ayrı ayrı tonlarca class oluşturmanıza gerek kalmaz.
Unity'de bir obje üzerinde birden fazla aynı scripti çalıştıramazsınız, objenizi çalıştırabilecek hale getirseniz de bir sürü zaman harcamış olursunuz yazacağınız ekstra kodlar için. Unreal Engine'de rahat rahat yazılan class'ları tak-çıkar yapabilirsiniz.
Unity'de compile süreleri ise daha kısa. Unity siz kodunuzda değişiklik yaptıkça otomatik olarak arkada kodunuzu compile eder, genelde de bu işlem 4-5 saniye kadar sürer. Unreal'de C++ compile işlemi yaklaşık 15-20 saniye sürmekte.
Unreal'in blueprintleri ile kodlama bilmeyen birisi bile programlama yapabilir, Unity'de olduğu gibi kolayca prototip çıkarılabilir; fakat kullanılan blueprintler uzun vadede ayağınıza dolanmaya başlar, performans sıkıntıları yaşamaya başlarsınız. Blueprintler hakkında pek konuşmak istemiyorum; fakat blueprintler C++'a göre büyük ölçüde yavaş çalışmakta ve yine aynı şekilde Unity C#'ına göre de yavaş çalışmakta. Bu yüzden büyük çaplı projelerde birkaç durum dışında blueprint'in esamesini bile okumamak gerekiyor.
- Collision sistemi:
Collision sistemi Unity'de gerçekten; ama gerçekten berbat durumda. O kadar berbat ki, tövbe edersiniz bir daha kullanmamak için Unity'i projenizin çok ayrıntılı collision gereksinimleri varsa.
Giriş yapacak olursam, Unity'de Unreal'de olduğu gibi box, sphere, capsule tarzında collider'lar var, buraya kadar her şey güzel. Birinci sıkıntı şu ki, Unity'de eğer bir objenizde birden fazla collider varsa, bu collider'lara ayrı ayrı referans alamıyorsunuz kodunuzda, veya her birinin ayrı ayrı collision event'larına ulaşamıyorsunuz. Her birinin yaptığı collision'lar objenin ortak collision'u olmuş oluyor. Bu sorunu çözmek için objenize alt objeler ekleyip onlara "teker teker" collision alanlarınızı eklemeniz gerekiyor, bu da oldukça eziyetli bir durum. Unreal'de objenize eklediğiniz collision alanları otomatik olarak yeni objeymiş gibi eklendiği için, ve kolayca düzenlenebildikleri için çok daha verimli oluyor. Ayrıca rahat rahat referans alabiliyorsunuz bu collision'lara kodunuz içerisinde.
Bir diğer konu ise mesh collider. Unity'de konkav bir objeye, objenin şeklini doğru şekilde yansıtan bir mesh collider oluşturamazsınız(Unity izin vermiyor), parametreleri oynayarak bir şekilde oluştursanız da objenizin şekliyle alakasız, işinize yaramayacak bir collider yaratmış olursunuz. Unreal'da ise mesh collider'i objenin şekliyle neredeyse aynı olarak uzun bir hesaplama sonucu çıkartabilirisiniz, paşa paşa da kullanırsınız projenizde. Son olarak, mesh collider'lar Unity'de OnTriggerStart, OnTriggerEnd, OnTriggerStay eventlarını doğru düzgün çağırmamakta. Hatta yıllardır süregelen bir bug olduğu söylenir: mesh collider kullanıyorsanız yukarıda yazdığım trigger eventları düzgün çalışmıyor. Kısacası mesh collider işi bitik Unity'de. Objenin şekline benzer bir collision'u bir sürü küçük küçük box collider ile oluşturmanız gerekiyor, bu da bir sürü zaman demek.
Son olarak, Unity'de OnHit gibi bir event yok. Hit durumu OnCollisionStart olarak ele almanız gerekiyor, bu da bir sürü fazladan kod yazmak demek. Unreal'de çarpma durumunu OnHit event'i ile çok kolay ele alabiliyorsunuz oysa ki.
Sonuç olarak, Unity'de collision management olayı bir hayli karışık durumda, Unreal'de ise kesinlikle daha derli toplu. Collision'larla ince işlere giren bir projeniz varsa tercihiniz kesinlikle Unreal'den yana olsun.
- Input Sistemi:
Unity'de inputlar her frame'de çağırılan Update fonksiyonu içerisine yazılacak if kontrolleri içerisinde yakalanmakta. ( Mesela if(a_tusu.IsPressed()) { } ) Bu da input management işini spagettiye çevirmekte. Unreal'de ise bu işi tanımladığınız inputları, her tuşa özel bir event fonksiyonu ile kolayca halledebilmektesiniz. Unity üzerinde de aynı sistem ekstra yazacağınız kodlarla kurulabilir; fakat yine zamanınızdan çalmış olacak bu durum da.
- Open-Source:
Unity'nin en kötü yönlerinden birine geldik. Unity'de hangi internal fonksiyon nasıl çalışıyor bilemezsiniz. Sadece girdisini, çıktısını bilirsiniz, bir kara kutu gibi. Bu da kod yazarken beklenmedik bir durumla karşılaştığınızda Unity'nin kendi fonksiyonları içerisinde sorunun köküne inmek yerine, alakasız, okunmaya çalışıldığında adeta gözleri kanatan kestirme yol kodlar yazmanıza sebep olur. Unreal'de ise eğer internal bir fonksiyon istediğiniz gibi çalışmıyorsa, önce fonksiyon nasıl yazılmış, neyi nasıl yapıyor okuyabilir; sonrasında sorun çıkaran bir nokta varsa bu kod üzerinde değişiklik yapabilirsiniz. Unity'de bu iş için ayrı class bile yazmanıza gerek olabilir.
- Prefab Sistemi:
Unity'nin iyi mi yoksa kötü mü bilemediğim bir noktası da Prefab sistemi. Prefab'lar Unreal'deki blueprint objelerine oldukça benzemekte. Mesela oyun içerisine bir obje yerleştirdiniz, üzerinde oynamalar yaptınız, parametrelerini değiştirdiniz. Sonrasında objenin bu halini "prefab" olarak kaydedebiliyorsunuz, fotoğrafını çekmek gibi bir şey yani. Sonrasında bu prefab'ı tekrar tekrar kullanabiliyorsunuz oyununuzda. Yalnız şöyle bir şey var ki, Unity'de runtime esnasında elinizde prefab'ı olmayan bir objeyi oluşturamıyorsunuz(Boş obje bile buna dahil, boş bir objenin prefab'ini öncelikle oluşturmanız gerekiyor kendiniz). Bu da yine ekstra bir sürü iş demek oluyor.
- Default Shader:
Pek fazla şey yazmak istemiyorum bu konuda, zira Unity'nin kendi default shader'ı rezalet durumda. Unity Store'da bu durumu çözebileceğiniz iki adet shader bulunmakta. Birinin adı "Alloy Shader Framework" ve ücretsiz, diğerinin adını hatırlayamadım, ama 60$ gibi uçuk bir fiyata satılıyor. Bu şekilde Unreal'in render kalitesine yaklaşabiliyorsunuz. Yaklaşabiliyorsunuz dedim, çünkü normal bir developer olarak Unreal'in kalitesini yakalamak pek kolay değil. Unity Shader Language kullanarak materyalinizin karakteristik özelliklerine göre shader yazmanız gerekmekte eğer kaliteli işler çıkartmak isterseniz kendiniz; fakat Unity'de shader kodlama işi başlı başına ayrı ve zor bir konu, oralara hiç girmeyeyim. Unreal'de ise blueprint'e benzer bir arayüzle kolayca kendi shader'larınızı oluşturabiliyorsunuz.
- Runtime:
Unity editör üzerinde runtime esnasında yaptığınız değişiklikleri doğrudan kaydedemezsiniz. Mesela oyununuzu başlattınız, test ediyorsunuz. Birkaç parametreye ince ayar çekmek istediniz, yaptınız ayarlamalarınızı, Control+S yaptınız; ama o da ne? Unity size "Runtime esnasında değişiklikleri kaydedemezsiniz" gibi bir hata veriyor. Tek yolu ilgili objeleri tek tek prefab olarak kaydetmek, sonrasında play mode'dan çıkıp bu prefabları asıl objeniz ile değiştirmek. Oldukça zaman alan bir iş uzun vadede. Unreal'de ise hot-reload sistemi sayesinde kafanıza göre istediğiniz zaman değişiklik kaydı alabilirsiniz.
- Yıl olmuş 2018, hala aylık ücret:
Yılın 2018 olmuş olmasına rağmen, Unity ek özellikler için hala sizden aylık ücret talep etmekte ve bu şekilde Pro olarak ayrı bir sürümü bulunmakta. Eğer $100.000 üzeri gelir etmekteyse takımınız veya şirketiniz, Unity'den aylık olarak lisans almış olmanız gerekmekte geliştirme süreci boyunca.
Ücretsiz sürüm beyaz tema ile birlikte gelmekte ve gerçekten birkaç saat kullanım sonrası gözleri acıtmakta. Son olarak, ücretsiz sürüm ile build ettiğiniz oyunların içerisine Unity'nin bir tür veri toplama aracı ekleniyor, o oyunu oynayan tüm kullanıcılarından donanımsal istatistik verileri toplanıyor. Ayrıca, oyununuzu bazı platformlara (Xbox, Windows Store vs.) build edemiyorsunuz lisans olmadan.
- Buglar:
Buraya Unity şöyle, Unreal böyle diye yazmak istemiyorum karşılaştırma amaçlı, çok uzun olur. Özet geçecek olursam bu konu hakkında, Unity'de kesinlikle daha fazla bug bulunmakta; fakat Unreal'e göre daha az crash yiyor. Misal Mesh Collider'lar ile ilgili bir bug'u yukarıda paylaştım. Yine bir örnek olarak Unity 2017.2 versiyonuna kadar VR projelerinde sahnenize Unity'nin kendi içerisinde bulunan sistemle ağaç eklediğinizde ağaçlar kameranız ile birlikte aynı yöne dönmekteydi, bu da saçma sapan bir görüntü ortaya çıkartmaktaydı. Forum sitelerinde bas bas bağıran kullanıcılar olmasına rağmen; yaklaşık 1 senelik zaman dilimi sonrası bu sorunu çözdüler. Bunun gibi daha bir sürü sorunla karşılaşmanız mümkün Unity'de.
- Dokümantasyon ve Community:
Bu konuda Unity'e laf yok, zira mükemmel bir dokümantasyonları var ve community'si çok canlı, kaynak çok fazla. Unreal'in özellikle C++ ile ilgili kısmında dokümantasyon berbat, hadi diyelim dokümantasyonu olmayan bir fonksiyon çıktı karşınıza, kodlarına bakayım dediniz, kodlar içerisinde "// I don't know how I got this working" tarzı bir comment görmeniz yüksek ihtimalli. Gerçi Unreal'de dokümantasyonun da iki çeşidi oluyor. Birisi içi boş dokümantasyon, fonksiyonun parametre çeşitleri ve döndüğü değişkenin tipi yazıyor mesela içinde sadece. Nasıl çalıştığına dair bir cümle bile yok. Diğeri ise içi dolu dokümantasyon, içinde örnek kodlar, nasıl çalıştığı gibi ayrıntılı bilgiler de bulunmakta. Unity'de neredeyse her fonksiyon / değişken için ayrıntılı açıklamalar ve örnek kodlar bulunmakta.
- Sonuç:
Sonuç olarak, Unity ve Unreal oyun motorlarının ikisinde de aynı sonuçlara bir şekilde ulaşabilirsiniz. Kısa vadede(prototip çıkarma aşaması) Unity size çok cazip gelir; fakat proje ilerledikçe ayağınıza dolanmaya başlar kronik sıkıntıları. Unreal Engine ise uzun vadede yardımınıza koşar, projeniz her daim düzenli bir şekilde ilerler; fakat başlangıç aşamasında elinize çalışan bir prototip geçmesi uzunca bir vaktinizi alabilir. Bunun ana sebebi Unity'nin neredeyse hiçbir şeyi size hazır olarak sunmuyor olması, her şeyi kendinizin kodlamanızın gerekmesi, Unreal'in ise aklınıza ne gelirse size bir şekilde ucundan da olsa sunuyor olması diyebilirim. Unity'de en ufak bir gereksinimiz için bile kod yazmanız gerekirken Unreal'de gereken şeyi hazır olarak bulma ihtimaliniz oluyor.
Elimden geldiğince anlaşılır karşılaştırmaya çalıştım bu iki oyun motorunu, aklıma gelen başka karşılaştırmalar olursa buraya eklemeye devam edeceğim.