Gönderen Konu: Kod ile 3d obje yaratma  (Okunma sayısı 15129 defa)

Kod ile 3d obje yaratma

« : 20.04.2006 02:11:27 »
Hızlı düğmeleri aç

skate

İleti: 5.245

A Sinner Scener
Çevrimdışı
  • Administrator
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.akaydin.com/
3D masterlara ufak bir iki soru.

1) şu anda 3DSMax ile çözdüğüm bazı şeyleri artık doğrudan kodun içinden çözmeye çalışıyorum. Örneğin kalınlığı olan yani iç ve dış yüzeylerini görebildiğimiz bir yarım küreyi (bir nevi kubbe) kod ile oluşturmaya kalktığımda bazı sorunlar yaşadım. Aklıma birkaç fikir geldi ama hiçbiri de işe yaramadı. DirectX kullanıyorum ancak API farketmez, bana mantığını anlatırsanız sevinirim.

2) 3DSMax'deki objeleri birbirinden çıkarma olayı kod ile mümkün müdür? Aslında mümkün olduğunu bazı 3d oyunlardan biliyorum ancak asıl merak ettiğim bunu yapmak için hazır API fonksiyonları var mı?

Kod ile 3d obje yaratma

« Yanıtla #1 : 20.04.2006 06:46:07 »
Hızlı düğmeleri aç

anesthetic

İleti: 403

Çevrimdışı
  • ****
  • Sr. Member
    • Profili Görüntüle
    • http://resident.tr-demoscene.info/
1) Aklıma gelen ek basit yöntem şu: normal bir küre oluşturup sonra (kutuplar üçgen, aralar kare (ya da çift üçgen), ve çift sayıda paralel olacak (tam ekvatordan geçen bir poligon şeridi olacak)) alt kısmı küçültüp içeri sokmak. şöyle ki:

if (vertex.y < 0) vertex..y *= -0.8 ;

Alt kürenin ön yüzü yine dışarı bakacağı için sorun değişmeyecek. Plastik bir topu parmağımızla içeri doğru bastırmış gibi olduk. Çift sayıda paralel olduğu için ortadaki iki paralel aynı hizaya geldi ve bir kalınlık oluşturdu. Gerçi iki kutup arasında 180 derece elde etmedik ama paralel sayısı fazlaysa 180'e epey yakın oldu.

2) Noktanın poligonun içinde olduğunu nasıl buluyorsak meshin içinde olduğunu öyle buluyoruz. ıçten dışa ya da dıştan içe bir çizgi çekip, her üçgenin düzlem denklemini kullanarak kesip kesmediğine bakıyoruz. Tek sayıda kesme varsa nokta meshin içerisindedir.

iki mesh de kapalı ise mesh2'nin mesh1 içinde olan noktalarını buluyoruz ve bu noktaları bağlı oldukları poligonlarla birlikte atıyoruz. Koparılmış ikinci meshte sadece bir ya da iki üçgene bağlı noktalar bize yüzeyin kenarlarını (kapalılığın bittiği eğriyi) verecek. Bu eğrinin içini gridlememiz lazım. Ama bu çok zor bir problem, nispeten kolay hale çevirmek için bu sefer mesh1'in mesh2 içinde olduğu noktaları bulup bir yüzey oluşturuyoruz. Yine bu yeni yüzeyin kenarlarını bulduktan sonra iki eğriyi gridliyoruz (bu da okul projesinde gerekmişti ama %100 çalışan bir yol hala bulamadım.)

Tabi ki yüksek poligonlarda işe yarayan bir yol. Düşük poligonlarda çalışması için üçgenleri bölmek filan gerekiyor. Onun için üçgenler değil de yüzey denklemleri tutmak daha mantıklı gibi.

Hazır API bilmiyorum ama yapılamaz gibi de gelmiyor.

Kod ile 3d obje yaratma

« Yanıtla #2 : 20.04.2006 09:10:52 »
Hızlı düğmeleri aç

skate

İleti: 5.245

A Sinner Scener
Çevrimdışı
  • Administrator
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.akaydin.com/
Çok saol Anes, iki cevap da istediğim gibiydi. Özellikle birincisi işime yarayacaktır.

Bunu sormamın nedeni biraz da "millet nasıl yapıyor acaba" idi. Benim de aklıma bir yüzeyi 10x10 gibi facelere bölünmüş ince ve yayvan bir dikdörtgen prizmayı, yani kalınlığı olan bir dikdörtgen yüzeyin vertexlerini trigonometrik bir işlemle yarım küre gibi pozisyona sokmaktı. Bu arada şu anda ihtiyacım olduğu haliyle dikdörtgenin köşelerinin bulunduğu açıları zaten kamera görmeyecekti. Ama yine de kendim bir çözüm denemeden sizlere soriim dedim. ıyi ki de sormuşum, senin yöntem daha iyi sonuç verir gibi duruyor.

Kod ile 3d obje yaratma

« Yanıtla #3 : 20.04.2006 09:15:05 »
Hızlı düğmeleri aç

skate

İleti: 5.245

A Sinner Scener
Çevrimdışı
  • Administrator
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.akaydin.com/
Hemen ikinci bir soru soriim. Facelerin normallerini terse çevirsem objenin içindeyken onu görüp, dışındayken görememiş mi olurum? Normallerle oynaşırken garip şeyler oldu çünkü. Bazı ploygonları hiç göremez hale geldim v.s.

Amacım bir bakıma içinde olduğum kürenin iç yüzeyini görebilmek aslında. Daha önce bunu 3DSMax'de hazırladığım kalınlığı olan bir yarım küreyle yapıyordum, şimdi koda dökesim geldi :)

Kod ile 3d obje yaratma

« Yanıtla #4 : 20.04.2006 09:44:07 »
Hızlı düğmeleri aç

jimqode

İleti: 215

Çevrimdışı
  • ***
  • Full Member
    • Profili Görüntüle
    • http://
Alıntı
Originally posted by skate@Apr 20 2006, 08:15 AM
Hemen ikinci bir soru soriim. Facelerin normallerini terse çevirsem objenin içindeyken onu görüp, dışındayken görememiş mi olurum? Normallerle oynaşırken garip şeyler oldu çünkü. Bazı ploygonları hiç göremez hale geldim v.s.

Amacım bir bakıma içinde olduğum kürenin iç yüzeyini görebilmek aslında. Daha önce bunu 3DSMax'de hazırladığım kalınlığı olan bir yarım küreyle yapıyordum, şimdi koda dökesim geldi :)
[post=7132]Quoted post[/post]
[/b]

Yuzey sadece normallerin baktigi yonde gorunur olur. Yani tahminin dogru. Isik kaynagindan gelen isin, normale gore simetriginden geri doner. Ayni lisede ogrendigimiz duzlem ayni gibi dusunebilirsin.
/*
Planet Retro - Retrocomputing News and Blogs
*/

Kod ile 3d obje yaratma

« Yanıtla #5 : 20.04.2006 10:26:42 »
Hızlı düğmeleri aç

Hydrogen

İleti: 932

Çevrimdışı
  • 7DX Organizer
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.glance.ws
Kalinligi olan yarim kureyi pek anlayamadim. iglo gibi bir sekil mi kastettigin? Yani ici bos bir yarim kure.
Eger oyle ise normallerini ters cevirmek kurenin kalinliginin icinde gezmeye yarayacaktir. Meraktan sordum.

Kod ile 3d obje yaratma

« Yanıtla #6 : 20.04.2006 15:45:38 »
Hızlı düğmeleri aç

skate

İleti: 5.245

A Sinner Scener
Çevrimdışı
  • Administrator
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.akaydin.com/
Alıntı
Originally posted by Hydrogen@Apr 20 2006, 09:26 AM
Kalinligi olan yarim kureyi pek anlayamadim. iglo gibi bir sekil mi kastettigin? Yani ici bos bir yarim kure.
Eger oyle ise normallerini ters cevirmek kurenin kalinliginin icinde gezmeye yarayacaktir. Meraktan sordum.
[post=7134]Quoted post[/post]
[/b]
Kalınlığı olan yarım küreyi portakalı ikiye kesip içini yemişsin gibi düşünebilirsin :) Yani doğru anlamışsın. Ancak benim normallerini terse çevirmekten bahsettiğim şey standart bir küreydi. Yani kalınlığı olmayan ve normalde dışını görüp, içine girdiğimizde iç yüzeyini göremediğimiz bir küre. Kalınlığı olan bir objenin normallerini terse çevirmekten bahsetmedim yani.

Kod ile 3d obje yaratma

« Yanıtla #7 : 20.04.2006 19:07:35 »
Hızlı düğmeleri aç

anesthetic

İleti: 403

Çevrimdışı
  • ****
  • Sr. Member
    • Profili Görüntüle
    • http://resident.tr-demoscene.info/
ışıklandırma için "normal dot (ışık - vertex)" işlemi yapılır. eğer bu değer negatif çıkarsa 0'a alınır. sen normalleri tersine çevirdiğinde bu işlem de tersine dönecektir. dolayısıyla ışık görmesi gereken yerleri ışıksız göreceksin. Işık olmaması gereken yerleri de ışıklı.

ANCAK

kürenin içine girdiğinde onu görüp göremenle alakalı değil bu. Çünkü poligon culling açıksa ekrana sadece saat yönünün tersindeki üçgenler basılacaktır. Eğer dışarıdan küreyi görebiliyorsan yani üçgenler saat yönünün tersindeyse, içine girdiğinde üçgenler artık saat yönünde basılmaya başlayacaklar, dolayısıyla daha ışık hesaplarına girmeden tüm yüzeyler elenecek.

Hep kürenin içinde olacaksan, üçgenlerin indis sıralarını tersine çevir; {vertex1, vertex2, vertex3}ken {vertex1, vertex3, vertex2} yap mesela. eğer bi arkadaşa bakıp çıkacaksan, o süre boyunca culling metodunu directx fonksiyonları ile değiştir (clockwise-counterclockwise) ya da cullingi kapat.

Kod ile 3d obje yaratma

« Yanıtla #8 : 20.04.2006 21:10:31 »
Hızlı düğmeleri aç

skate

İleti: 5.245

A Sinner Scener
Çevrimdışı
  • Administrator
  • *****
  • Hero Member
    • Profili Görüntüle
    • http://www.akaydin.com/
Çok saol Anes, haklısın normalleri tersine çevirince olay çözülmüyor. Ben de bunun yerine daha farklı bir yöntemle çözdüm sorunu, vertex pozisyonlarının tersini aldım. Böylece kürenin içinde oliim ya da olmiim her zaman iç yüzeyler görünür halde, dış yüzey ise hiçbir şekilde görünmüyor.

Kod: [Seç]
struct VertexEx
{
    D3DXVECTOR3 pos;
    D3DXVECTOR3 norm;
    float tu;
    float tv;
};

...
...
...

VertexEx *pVerts;
mesh->LockVertexBuffer(0, (LPVOID *)&pVerts);

int numVerts = mesh->GetNumVertices();

for (i = 0; i < numVerts; i++)
{
    pVerts->pos *= -1.0f;
    //pVerts->norm *= -1.0f;
    pVerts->tu=asinf(pVerts->norm.x)/D3DX_PI+0.5f;
    pVerts->tv=asinf(pVerts->norm.y)/D3DX_PI+0.5f;
    pVerts++;
}

mesh->UnlockVertexBuffer();

Eğer loopun içindeki remli satırı kaldırırsam bu defa da texture olduğu gibi görünüyor ve ışık kaynaklarından etkilenmiyor. Her ikisini de farklı amaçlarla kullanacağım yeri geldikçe.

Yardımcı olan herkese teşekkürler.