PMG http://forum.pmg.org.ru/ |
|
Помогите с алгоритмом генерации специальной сферы. http://forum.pmg.org.ru/viewtopic.php?f=4&t=4070 |
Страница 1 из 1 |
Автор: | @lpha [ 28 авг 2007 19:14 ] |
Заголовок сообщения: | Помогите с алгоритмом генерации специальной сферы. |
Здравствуйте. Помогите мне, пожалуйста, с одной проблемой – никак не получается вручную сгенерировать нужную мне сферу. Да-да казалось бы такая простая вещь как D3dxCreateSphere могла бы подойти, но мне нужна не обычная сфера, которая сжимает свои линии к полюсам, а сфера с равными сегментами. Мне же нужно чтобы вы 1) помогли подкорректировать его так, чтобы код генерировал сферу без сжатия к полюсам с равными сегментами и 2) – помогли с индексным буфером(который как вы видите, соединяет только вершины сегмента, а не сегменты между собой). Версию кода в несколько упрощенном виде я приведу здесь. Это генерирует обыкновенную сферу. Если вы не поленитесь написать простой класс и вставить в него _vb , _ib в качестве буферов и несколько несложных переменных типа unsigned int. HRESULT PLANET::Init() { UINT segmentary = 16, //общее кол-во сегментов columnsnum = segmentary, //кол-во колонок rowsnum = segmentary, //максимальное кол-во сегментов в колонке segmentsnum = segmentary*segmentary;//кол-во сегментов _numrendprimitives = segmentsnum*2; //кол-во отрисовывающихся примитивов _numvvertexes = segmentsnum*4; //кол-во вершин для vertex buffer _numivertexes = segmentsnum*6; //кол-во вершин для index buffer (*_pDev)->CreateVertexBuffer ( _numvvertexes *sizeof(PlanetVertex), D3DUSAGE_DYNAMIC, D3DFVF_XYZ | D3DFVF_TEX1, D3DPOOL_DEFAULT, &_vb, NULL ); PlanetVertex* pattern; _vb->Lock(0,0,(void**)&pattern,0); //ПРОЦЕДУРНАЯ ГЕНЕРАЦИЯ СФЕРЫ //переменные скругления сферы float lattitude = 0.0f; float longitude = 0.0f; const float _lattitudelimit = 360.0f; const float _longitudelimit = 360.0f; float lattitudeshift = _lattitudelimit/(float)columnsnum; float longitudeshift = _longitudelimit/(float)rowsnum; //вычисляемые значения(для каждой вершины в квадрате) float x1,x2,x3,x4, y1,y2,y3,y4, z1,z2,z3,z4, //вычисляемые значения скругления fx1, fy1, fz1, fx2, fy2, fz2, fx3, fy3, fz3, fx4, fy4, fz4; for (UINT i = 0, //главный индекс c = 0, //счетчик столбцов r = 0; //счетчик строк c < segmentary; c++, lattitude+=lattitudeshift ) { fx1 = cos(D3DXToRadian(lattitude)); fx2 = cos(D3DXToRadian(lattitude)); fx3 = cos(D3DXToRadian(lattitude+lattitudeshift)); fx4 = cos(D3DXToRadian(lattitude+lattitudeshift)); x1 = fx1; x2 = fx2; x3 = fx3; x4 = fx4; for( r = 0; r < rowsnum; r++, i+=4, longitude+=longitudeshift ) { fy1 = sin(D3DXToRadian(longitude))*sin(D3DXToRadian(lattitude)); fy2 = sin(D3DXToRadian(longitude+longitudeshift))*sin(D3DXToRadian(lattitude)); fy3 = sin(D3DXToRadian(longitude+longitudeshift))*sin(D3DXToRadian(lattitude+lattitudeshift)); fy4 = sin(D3DXToRadian(longitude))*sin(D3DXToRadian(lattitude+lattitudeshift)); fz1 = cos(D3DXToRadian(longitude))*sin(D3DXToRadian(lattitude)); fz2 = cos(D3DXToRadian(longitude+longitudeshift))*sin(D3DXToRadian(lattitude)); fz3 = cos(D3DXToRadian(longitude+longitudeshift))*sin(D3DXToRadian(lattitude+lattitudeshift)); fz4 = cos(D3DXToRadian(longitude))*sin(D3DXToRadian(lattitude+lattitudeshift)); y1 = fy1; y2 = fy2; y3 = fy3; y4 = fy4; z1 = fz1; z2 = fz2; z3 = fz3; z4 = fz4; // x y z pattern[i] = PlanetVertex(x1, y1, z1 , 0.0f, 1.0f); pattern[i+1] = PlanetVertex(x2, y2, z2 , 0.0f, 0.0f); pattern[i+2] = PlanetVertex(x3, y3, z3 , 1.0f, 0.0f); pattern[i+3] = PlanetVertex(x4, y4, z4 , 1.0f, 1.0f); } } _vb->Unlock(); //создание индексного буффера (*_pDev)->CreateIndexBuffer ( _numivertexes * sizeof(WORD), D3DUSAGE_DYNAMIC, D3DFMT_INDEX16, D3DPOOL_DEFAULT, &_ib, NULL ); WORD* i; _ib->Lock(0,0,(void**)&i,0); for(UINT q = 0,//счетчик цикла rsi = 0,//индекс m = 0; //значение q < segmentsnum; q++, rsi+=6, m+=4) { i[rsi] = m; i[rsi+1] = m+1; i[rsi+2] = m+2; i[rsi+3] = m+3; i[rsi+4] = m; i[rsi+5] = m+2; } _ib->Unlock(); return S_OK; } //код рендеринга VOID PLANET::Draw() { //...// (*_pDev)->SetFVF(PLANET_FVF); (*_pDev)->SetStreamSource(0,_vb,0,sizeof(PlanetVertex)); (*_pDev)->SetIndices(_ib); (*_pDev)->DrawIndexedPrimitive ( D3DPT_TRIANGLELIST, 0,0, _numivertexes,0, _numrendprimitives ); } Я пока не беру в расчет такие вещи как радиус, точное кол-во сегментов. При этой генерации возникают проблемы связанные с несколько неправильной работой z-буффера(в cull режиме CCW) Я полагаю это связано с неправильным алгоритмом(пофиксите если найдете ок?) Вопрос: А для чего мне такая сфера ? Мне нужна сфера-планета как в старой RTS Populous:The beginning , кто играл, тот знает, кто не играл – советую ознакомиться – незаслуженно забытый шедевр. Хочу сделать нечто похожее на фан-римейк ^_^ Кто хочет присоединиться – icq 227929521. Принимаю всех, кто хоть что-то умеет. PS: Разумеется вы можете использовать этот простой код для процедурных генераций всего чего угодно.. А если поэксперементировать с параметрами синуса и косинуса выходит все что угодно – от ленты мёбиуса до молекул ДНК.. |
Автор: | MagicWolf [ 29 авг 2007 12:39 ] |
Заголовок сообщения: | |
Я когда делал сферу на RM: http://pmg.org.ru/rm/rm02.htm - Урок 2. Моделирование объектов с помощью Direct3D Retained Mode. Делал верхнюю и нижнюю часть веером, а по бокам полоски. Но мне кажется, всегда можно найти нужную модель или создать ... |
Автор: | @lpha [ 29 авг 2007 14:04 ] |
Заголовок сообщения: | |
Ум.. retained mode? Понятие не имею как можно его использовать, как впрочем и opengl.. Да и в странице на которую ссылается ваша ссылка описаны скорее генерация кубов чем сфер. 3dsmax9 также не генерирует то что мне нужно, а вручную делать.. хм.. я же не ищу легких путей.. и потом мне хотелось бы сделать именно процедурную генерацию.. подобно как в будущем Spore. Я полагаю такую сферу можно сделать последовательно уменьшая и увеличивая кол-во сегментов в соответствии со скруглением. Но сил для создания этого у меня не хватает. Help me! PS Ладно уж про индексный буфер молчу - помогите хотя бы с этим.. Ведь вроде бы все так просто. |
Автор: | MagicWolf [ 30 авг 2007 16:05 ] |
Заголовок сообщения: | |
Что такое "сфера с равными сегментами"? В каком смысле с равными? |
Автор: | @lpha [ 30 авг 2007 18:35 ] |
Заголовок сообщения: | |
Всмысле не с сжимающимися к полюсам линиями и равными сегментами повсюду. Геосфера близко подходит под это понятие, но ее стыки будут мешать думаю.. Вот что максимум получается у меня после долгих мучений Подушка, тьфу.. |
Автор: | MagicWolf [ 31 авг 2007 08:53 ] |
Заголовок сообщения: | |
Не понимаю: "не с сжимающимися к полюсам линиями" что ты имеешь ввиду, по определению к полюсам все сжимается . |
Автор: | @lpha [ 31 авг 2007 10:32 ] |
Заголовок сообщения: | |
Вот такая она должна быть со всех сторон Надеюсь на глаз нетрудно определить что в ней нет ни стыков, ни сжатий и все сегменты в ней абсолютно равны друг другу ? |
Автор: | MagicWolf [ 31 авг 2007 16:50 ] |
Заголовок сообщения: | |
Понял. Надо подумать, может что и вспомню ... |
Автор: | @lpha [ 31 авг 2007 22:43 ] |
Заголовок сообщения: | |
Давайте.. Буду ждать.. |
Автор: | MagicWolf [ 05 сен 2007 09:45 ] |
Заголовок сообщения: | |
А почему ты решил что это вообще возможно для не криволинейных сегментов? |
Автор: | @lpha [ 06 сен 2007 23:43 ] |
Заголовок сообщения: | |
Мне так показалось.. А как сделать для криволинейных ? |
Автор: | MagicWolf [ 07 сен 2007 08:40 ] |
Заголовок сообщения: | |
Я думаю это проще. Например, взять сферу и разделить ее на две половины, получиться два одинаковых криволинейных куска и так делить дальше ... |
Автор: | @lpha [ 08 сен 2007 20:32 ] |
Заголовок сообщения: | |
Не понял ничего.. ну да ладно.. |
Автор: | MagicWolf [ 10 сен 2007 11:26 ] |
Заголовок сообщения: | |
Рекурсивное деление, до нужно уровня. Разделим сферу на две одинаковые части - две полусферы, затем эти полусферы поделим попалам, затем, эти четвертики, еще раз, и так далее, до нужного числа делений. Соответственно, опеределяем параметры этих кусков, и аппроксимируем их треугольниками... |
Страница 1 из 1 | Часовой пояс: UTC + 3 часа [ Летнее время ] |
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group http://www.phpbb.com/ |