mehdadoo
Member
مواردی که میخوام براتون دربارشون بگم، هیچ وقت قدیمی نمیشن و چیزایی هستن که هر برنامه نویس سه بعدی باید بدونه. از فلش پلایر ۱۰ استفده میکنم.
اولین نکته 3D وجود بعد دیگری به غیر از طول و عرضه، که ما بهش میکیم عمق که با z نشونش میدیم.برای این آموزش فرض میکنیم، که اشیا هرچه دورتر از ما میشن، عمقشون افزایش پیدا میکنه. همینطور برخلاف پیش فرض فلش که نقطه (0,0) در بالا و سمت چپ قرار داره، نقطه مرکزی (0,0,0) رو ما در مرکز صفحه نمایش در نظز میگیریم.
پرسپکتیو قانونیه که با استفاده از اون ما تشخیص میدیم یک شی به ما نزدیک یا دور هستش. یا به قولی دیگه، ما چه جوری میتونیم کاری کنیم یه شیه به نظز نزدیکتر یا دورتر از ما دیده بشه.
از میان قوانین دقیق پرسپکتیو، دو تاش به درد ما میخورند. ۱-اشیا هر چه دورتر بشن، کوچیک تر باید دیده بشن ۲- اشیا هرچه که دورتر برن، نزدیک تر به نقطه مرکز دیده میشن.
بنابراین این دو قانون بسیار ساده ابزار ما برای شبیه سازی بعد عمق یا z هستند. یعنی:۱- اشیا رو بزرگ یا کوچک کنیم. ۲-اشیا را از نقطه مرکزی دورتر یا نزدیک تر کنیم.
یک توضیح که میتونید نخونیدش.
برای شبیه سازی این قوانین، یک نکته دیگه هم هست. ما یک شی داریم، یک صفحه نمایش، و یک عدد که نشون دهنده عمق شیه یا Z هست، یک چشم، و یک عدد تازه دیگه، فاصله چشم از صفحه نمایش. البته منظوزم از چشم اون چیزیه که به نوعی مثل دوربین داره از کل اشیاعکس میگیره. به عدد آخر در همه جا حتی عکاسی Focal Length - fl میگن. اون عدد رو ۲۰۰ فرض میگیریم.
برای محاسبه نسبت بزرگنمایی یک شی سه بعدی، در صفحه دو بعدی مانیتور، لازمه از یک قانونی که همه استفاده میکنند استفاده کنیم. کار سختی نیست:
این فرمول یک عددی بین ۰.۰ تا ۱.۰ رو بیرون میده، که نسبت کوچک نمایی و همینطور نزدیک شدن شی به نقطه مرکزیه.
حالا کافیه scaleX و scaleY شیه رو یا این عدد ضرب کنیم. همینطور حاصلضرب x و y شیه با این نسبت، مکان شی رو در صفحه نمایشگر رو نشون خواهد داد.
به همین سادگی.
مرحله بعدی برای نمایش قدرت انجین سه بعدیمون، نوشتن فرمولی هستش که با استفاده ازش چرخش شی رو بتونیم اندازه گیریم کنیم. یا به قول دیگه ای، دوربین رو دور شیه بچرخونیم.
این فرمول با سرعت بالا ساده(در واقع پیچیده!) شده توسط قوانین الجبرا.
این فرمول یک شی رو نسبت به نقطه (0,0) روی محور z به اندازه زاویه تعیین شده میچرخونه.
تمام جمله های قبلی مربوط به تقطه بود، ولی من برای قابل درک تر بودن از کلمه شی استفاده کردم. پس وقتشه یک کلاس برای نقطه درست کنیم و همه فرمول هایی که گفته شد رو توش بذاریم.
Point3D.as
مدل سازها شاید از poly modeling استفاده کنند، ولی در واقع هر شکل بیشتر از سه ضلع، در نهایت برای رندر شدن به مثل تبدیل میشن. مثلث پایه به تصویر کشیدن مدل سه بعدیه.
کافیه سه Point3D رو به هم وصل کنیم، و دیگه تمامی امکانات انجین سه بعدی، رومون باز میشه. پس هر مدل از مثلث ها تشکیل شده، و هر مثلث از سه نقطه. مثلث های یک مدل در اکثر موارد از نقطه های مشترکی استفاده میکنند.عکس triangles.png راحت تر توضیح میده.
پس اگر نقطه های
رو داشته باشیم، برای ساخت یک مربع، مثلث ها این گونه خواهند بود:
این مهمه که برای تعیین نقطه های مثلث در جهت گردش عقربه ساعت یا برخلاف جهتش عمل کنیم. باید برای ساخت همه مثلث ها از یک راه استفده کنیم. مثلا
غلطه چون برای ساخت مثلث t1 بر جهت حرکت عقربه ها نقطه ها رو انتخاب کردیم ولی برای t2 برخلا حرکت عقربه ها. اهمیت همسان بودن قاعده انتخاب نقطه ها در قانون بعدی خودش رو نشون میده.
اگر مثلثی پشت به دوربین بود، نباید اون رو نقاشی کنیم. به این کار backface culling مگین. برای تشخیص اینکه یک مثلث آیا پشت به دوربین هست یا نه، نقطه وسط مثلث رو پیدا میکنیم و یک بردار ازش بیرون میکشم. ریاضی ۳ رو یادتون هست. ضرب بردارها.
اگر ضرب بردار فرضی که از دوربین به شی رسم میشه با برداری که از مرکز سه نقطه مثلث به بیرون رسم میشه مثبث باشه، اون وقت پشت مثلث به دوربین هست.
نیازی به یادآوری قوانین بردار نیست، چون قبلا با استفاده از الجبرا فرمول خیلی با سرعت بالایی برای محاسبه backface culling طراحی شده و ما از اون استفاده میکنیم.
در کلاس Triangle3D تمامی مطالب گفته شده درباره مثلث به کد تبدیل شده، و با مطالعه اون کلاس کل داستان قابل درک تر میشه.
حالا وقتشه که از دو کلاس Point3D و Triangle3D استفاده کنیم، و یک مدل سه بعدی بسازیم. کلاس Main.as
حرف A رو به صورت نقطه نقطه در یک Array ذخیره میکنیم، و بعد با استفاده از این نقطه ها مثلث هایی رو درست میکنیم، و اون وقت اولین مدل سه بعدیمون را خواهیم داشت.
برای نقاشی مدل سه بعدی، نقطه های هر مثلث رو به هم وصل میکنیم و با استفاده از moveTo LineTo در یک graphics object مثلث ها رو رسم میکنیم.
یه نکته هست، اونم اینه رندر گرفتن یک مدل، مثل کار نقاش ها میمونه. یعنی لایه لایه روی هم چیز هایی رو میکشن. ما هم باید تمامی مثلث ها رو لایه لایه روی هم نقاشی کنیم. طبیعیه که لایه ای که دورتر قرار داره باید اول رسم بشه.
مثلا اگر داخل یک محفظه Array تمامی مثلث های مدلمون رو داشته باشیم، باید اون Array رو با توجه به عمق هر مثلث ترتیب بندی کنیم.
برای محاسبه عمق هر مثلث میشه از میانگین عمق های سه نقطه مثلث استفاده کرد، اما ما نزدیک ترین مثلث به دوربین رو نقطه z مثلث فرض میکنیم.
برای ترتیب بندی، از فانکشن ساده
فانکشن Array.sortOn تمامی اعضای یک array رو با توجه به یک property ترتیب بندی میکنه. ما مثلث های موجود در triangles Array رو با توجه به عمقشون ترتیب بندی کردیم.
باید بدونید آموزش ترتیب بندی درست مثلث ها در یک کتاب جا نمیشه، و این راحت ترین راه بود که عرضه شد!
حالا با command
mxmlc main.as -output main.swf
کامپایل میکنیم.
و به همین سادگی BasicHomeMadeVision3D رو با main.swf به رخ میکشیم!
البته من کمی جلوتر رفتم و مدل سه بعدی که برای بازی مولتی پلایر westRace ساخته بودم رو با استفاده از python در blender به xml خروجی گرفتم و نتیجش رو در Load3D.swf میتونید ببینید. برای این کار با استفاده از امکانات Native فلش پلایر ۱۰ و Affine Rendering تونستم texture رو هم نقاشی کنم.البته اون با زبان Haxe نوشته شده.
تمامی این قوانین به پلتفورم های دیگه هم میتونه اطلاق بشه.
Special thanks to grant skinner, keith peters, nicollas cannasse.
اولین نکته 3D وجود بعد دیگری به غیر از طول و عرضه، که ما بهش میکیم عمق که با z نشونش میدیم.برای این آموزش فرض میکنیم، که اشیا هرچه دورتر از ما میشن، عمقشون افزایش پیدا میکنه. همینطور برخلاف پیش فرض فلش که نقطه (0,0) در بالا و سمت چپ قرار داره، نقطه مرکزی (0,0,0) رو ما در مرکز صفحه نمایش در نظز میگیریم.
پرسپکتیو قانونیه که با استفاده از اون ما تشخیص میدیم یک شی به ما نزدیک یا دور هستش. یا به قولی دیگه، ما چه جوری میتونیم کاری کنیم یه شیه به نظز نزدیکتر یا دورتر از ما دیده بشه.
از میان قوانین دقیق پرسپکتیو، دو تاش به درد ما میخورند. ۱-اشیا هر چه دورتر بشن، کوچیک تر باید دیده بشن ۲- اشیا هرچه که دورتر برن، نزدیک تر به نقطه مرکز دیده میشن.
بنابراین این دو قانون بسیار ساده ابزار ما برای شبیه سازی بعد عمق یا z هستند. یعنی:۱- اشیا رو بزرگ یا کوچک کنیم. ۲-اشیا را از نقطه مرکزی دورتر یا نزدیک تر کنیم.
یک توضیح که میتونید نخونیدش.
برای شبیه سازی این قوانین، یک نکته دیگه هم هست. ما یک شی داریم، یک صفحه نمایش، و یک عدد که نشون دهنده عمق شیه یا Z هست، یک چشم، و یک عدد تازه دیگه، فاصله چشم از صفحه نمایش. البته منظوزم از چشم اون چیزیه که به نوعی مثل دوربین داره از کل اشیاعکس میگیره. به عدد آخر در همه جا حتی عکاسی Focal Length - fl میگن. اون عدد رو ۲۰۰ فرض میگیریم.
برای محاسبه نسبت بزرگنمایی یک شی سه بعدی، در صفحه دو بعدی مانیتور، لازمه از یک قانونی که همه استفاده میکنند استفاده کنیم. کار سختی نیست:
کد:
[LEFT]scale = fl / ( fl + z);[/LEFT]
حالا کافیه scaleX و scaleY شیه رو یا این عدد ضرب کنیم. همینطور حاصلضرب x و y شیه با این نسبت، مکان شی رو در صفحه نمایشگر رو نشون خواهد داد.
به همین سادگی.
مرحله بعدی برای نمایش قدرت انجین سه بعدیمون، نوشتن فرمولی هستش که با استفاده ازش چرخش شی رو بتونیم اندازه گیریم کنیم. یا به قول دیگه ای، دوربین رو دور شیه بچرخونیم.
این فرمول با سرعت بالا ساده(در واقع پیچیده!) شده توسط قوانین الجبرا.
کد:
[LEFT]x1 = cos(angle) * x - sin(angle) * y;
y1 = cos(angle) * y + sin(angle) * x;[/LEFT]
تمام جمله های قبلی مربوط به تقطه بود، ولی من برای قابل درک تر بودن از کلمه شی استفاده کردم. پس وقتشه یک کلاس برای نقطه درست کنیم و همه فرمول هایی که گفته شد رو توش بذاریم.
Point3D.as
مدل سازها شاید از poly modeling استفاده کنند، ولی در واقع هر شکل بیشتر از سه ضلع، در نهایت برای رندر شدن به مثل تبدیل میشن. مثلث پایه به تصویر کشیدن مدل سه بعدیه.
کافیه سه Point3D رو به هم وصل کنیم، و دیگه تمامی امکانات انجین سه بعدی، رومون باز میشه. پس هر مدل از مثلث ها تشکیل شده، و هر مثلث از سه نقطه. مثلث های یک مدل در اکثر موارد از نقطه های مشترکی استفاده میکنند.عکس triangles.png راحت تر توضیح میده.
پس اگر نقطه های
کد:
p1=(0, 0,0); p2=(10, 0,0);
p3=(0,10,0); p4=(10,10,0);
کد:
t1=(p1,p2,p3); t2=(p2,p3,p4);
کد:
t2=(p4,p3,p2);
اگر مثلثی پشت به دوربین بود، نباید اون رو نقاشی کنیم. به این کار backface culling مگین. برای تشخیص اینکه یک مثلث آیا پشت به دوربین هست یا نه، نقطه وسط مثلث رو پیدا میکنیم و یک بردار ازش بیرون میکشم. ریاضی ۳ رو یادتون هست. ضرب بردارها.
اگر ضرب بردار فرضی که از دوربین به شی رسم میشه با برداری که از مرکز سه نقطه مثلث به بیرون رسم میشه مثبث باشه، اون وقت پشت مثلث به دوربین هست.
نیازی به یادآوری قوانین بردار نیست، چون قبلا با استفاده از الجبرا فرمول خیلی با سرعت بالایی برای محاسبه backface culling طراحی شده و ما از اون استفاده میکنیم.
در کلاس Triangle3D تمامی مطالب گفته شده درباره مثلث به کد تبدیل شده، و با مطالعه اون کلاس کل داستان قابل درک تر میشه.
حالا وقتشه که از دو کلاس Point3D و Triangle3D استفاده کنیم، و یک مدل سه بعدی بسازیم. کلاس Main.as
حرف A رو به صورت نقطه نقطه در یک Array ذخیره میکنیم، و بعد با استفاده از این نقطه ها مثلث هایی رو درست میکنیم، و اون وقت اولین مدل سه بعدیمون را خواهیم داشت.
برای نقاشی مدل سه بعدی، نقطه های هر مثلث رو به هم وصل میکنیم و با استفاده از moveTo LineTo در یک graphics object مثلث ها رو رسم میکنیم.
یه نکته هست، اونم اینه رندر گرفتن یک مدل، مثل کار نقاش ها میمونه. یعنی لایه لایه روی هم چیز هایی رو میکشن. ما هم باید تمامی مثلث ها رو لایه لایه روی هم نقاشی کنیم. طبیعیه که لایه ای که دورتر قرار داره باید اول رسم بشه.
مثلا اگر داخل یک محفظه Array تمامی مثلث های مدلمون رو داشته باشیم، باید اون Array رو با توجه به عمق هر مثلث ترتیب بندی کنیم.
برای محاسبه عمق هر مثلث میشه از میانگین عمق های سه نقطه مثلث استفاده کرد، اما ما نزدیک ترین مثلث به دوربین رو نقطه z مثلث فرض میکنیم.
برای ترتیب بندی، از فانکشن ساده
کد:
triangles.sortOn("depth", Array.DESCENDING | Array.NUMERIC);
باید بدونید آموزش ترتیب بندی درست مثلث ها در یک کتاب جا نمیشه، و این راحت ترین راه بود که عرضه شد!
حالا با command
mxmlc main.as -output main.swf
کامپایل میکنیم.
و به همین سادگی BasicHomeMadeVision3D رو با main.swf به رخ میکشیم!
البته من کمی جلوتر رفتم و مدل سه بعدی که برای بازی مولتی پلایر westRace ساخته بودم رو با استفاده از python در blender به xml خروجی گرفتم و نتیجش رو در Load3D.swf میتونید ببینید. برای این کار با استفاده از امکانات Native فلش پلایر ۱۰ و Affine Rendering تونستم texture رو هم نقاشی کنم.البته اون با زبان Haxe نوشته شده.
تمامی این قوانین به پلتفورم های دیگه هم میتونه اطلاق بشه.
Special thanks to grant skinner, keith peters, nicollas cannasse.
پیوست ها
آخرین ویرایش: