Войти
ПрограммированиеФорумГрафика

Unlimited Detail (196 стр)

Страницы: 1195 196 197 198221 Следующая »
#2925
(Правка: 22:52) 22:43, 16 сен. 2013

Вий
та пускай датасет будет дырявый, главное чтобы алгоритм бодро работал
а позже можно будет утилиту написать для конвертирования и экспорта сцены из 3dsMax.


#2926
22:43, 16 сен. 2013

mitroxa
Зачем забей?
Просто датасет не имеет смысл хранить в виде вокселей со стороной 0.25 мм, вот в чем суть. Это не очень удобно, но жить можно.

#2927
0:20, 17 сен. 2013

В общем датасет в текущем виде все еще занимает слишком много места и я решил его слегка пожать:
Весь объем, занимаемый датасетом, будет попилен на кубы со стороной 4 метра.
В файле будут лежать кубы в следующем виде:
количество кубов в файле = N (32 бита), список координат кубов  (16 бит * 3) и количество точек в каждом (32 бита), а также индекс первой точки куба в массиве точек(32 бита), массив точек кубов - координаты точки в кубе (16 бит * 3) и цвет точки в кубе (8 бит * 3), итого выйдет 51 бит на точку против 99, то есть данные уменьшатся примерно в 2 раза.
Будем надеяться, что они лягут более-менее равномерно и будет легко с ними проводить разные интересные операции.

#2928
0:32, 17 сен. 2013

Там вроде неравномерно распределены точки. наверно снимали двумя камерами возле центра координат, соответственно около центра плотность точек выше, чем дальше от центра, тем меньше.

#2929
0:36, 17 сен. 2013

susageP
> Основная проблема точки на разном расстояние, при разных проекций.
Не вижу проблемы тут. Объединяться будут количество точек >=  8, и маловероятно, что они будут все в одной плоскости. И даже если будут, просто будет на экране в одном месте много точек, что в этом плохого?

#2930
(Правка: 4:15) 4:13, 17 сен. 2013

split_cubes.cpp

+ Показать

Дружелюбные данные в новом формате занимают 1,369,894,578 байт в несжатом виде (было 2,283,144,510) то есть 60%.
С одной стороны, это не такое уж крутое сжатие, с другой - теперь данные отлично умещаются в 32-битном адресном пространстве.
Но самое замечательное - теперь они разделены на кучу небольших кубиков, с которыми можно работать независимо друг от друга

#2931
7:41, 17 сен. 2013

Запилите процедурную генерацию ландшафта, а то качать модель лень.

#2932
(Правка: 14:16) 8:26, 17 сен. 2013

Suslik
> что браво? что он float в int сконвертил? oh wow.
"лиха беда начало". -)

Если Вий или еще кто решит впиливать себе в код процедурные ландшафты предлагаю губку Менгера
http://www.iquilezles.org/www/articles/menger/menger.htm
https://www.shadertoy.com/results?query=tag%3Dmenger
https://www.shadertoy.com/view/4sX3Rn

Для доп. сжатия можно попробовать предложенные ранее tmtlib'ом вейвлеты Хаара
http://iquilezles.org/www/articles/wavelet/wavelet.htm
в которых, что забавно, iq использует кривую Мортона для обхода элементов. -)

Еще забавно своевременнной мне показалась свежая статья iq про отсутствие необходимости в тригонометрии (т.е. замена cos\sin и acos\asin на dot\cross умножения векторов)
http://iquilezles.org/www/articles/noacos/noacos.htm

А также Branchless DDA от fb39ca4
https://www.shadertoy.com/view/4dX3zl

#2933
4:32, 20 сен. 2013
cubes | Unlimited Detail
#2934
(Правка: 5:29) 5:16, 20 сен. 2013
#include <windows.h>
#include <cstdlib>
#include <cstdio>
#include <cmath>
#include <limits>
#include <cstring>
#define IO_BUFFER_SIZE (64*1024*1024)
template<typename T> struct Tuple2{T x;T y;};
#pragma pack(push)
#pragma pack(1)
struct CubePoint{WORD x,y,z;unsigned char r,g,b;};
struct Cube{int pointsCount;int offsetPoints;WORD x,y,z;};
struct CubesHeader{int count;};
#pragma pack(pop)
HINSTANCE hInstance=0;HWND hw=0;int scrWid,scrHei,scrWid_1,scrHei_1;BITMAPINFOHEADER 
bmiBackBuffer={sizeof(BITMAPINFOHEADER),0,0,1,32,BI_RGB,0,0,0,0,0};
char* windowClassName="test_render_cubes";int kS[256]={0};int keyDownCount[256]={0};int keyUpCount[256]={0};int keyWasPressed[256]={0};LRESULT CALLBACK windowProcedure(HWND hWnd,UINT uMsg,WPARAM 
wParam,LPARAM lParam){switch(uMsg){
case WM_DESTROY:PostQuitMessage(0);return 0;
case WM_KEYDOWN:kS[wParam & 0xff]=1;keyDownCount[wParam & 0xff]++;keyWasPressed[wParam & 0xff]=1;return 0;
case WM_KEYUP:kS[wParam & 0xff]=0;keyUpCount[wParam & 0xff]++;return 0;
case WM_TIMER:
case WM_PAINT:return 0;}
return DefWindowProc(hWnd,uMsg,wParam,lParam);}BOOL CALLBACK dialogProcedure(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam){static Tuple2<short> resolutions[]={{0,0}/*KEEP*/,{640,480},
{800,600},{1024,600},{1024,768},{1280,800},{1280,1024},{1366,768},{1440,900},{1600,1200},{1680,1050}};static 
Tuple2<short> zooms[]={{1,1},{2,2},{3,3},{4,4}};enum{RESOLUTION=1,ZOOM=3,SOUND=5,WINDOWED=7,PLAY=8,EXIT=9,COUNT=10};struct SettingsDialogItem{int value;HWND handle;char* type;char* text;DWORD style;DWORD getType;};static SettingsDialogItem items[COUNT]={{0,0,"STATIC","Resolution",SS_RIGHT|WS_VISIBLE|WS_CHILD,CB_GETCURSEL},{0,0,"COMBOBOX","",CBS_DROPDOWNLIST|WS_VISIBLE|WS_CHILD|WS_TABSTOP,CB_GETCURSEL},{0,0,"STATIC","Zoom",SS_RIGHT| WS_VISIBLE| WS_CHILD,CB_GETCURSEL},{0,0,"COMBOBOX","",CBS_DROPDOWNLIST|WS_VISIBLE|WS_CHILD|WS_TABSTOP,CB_GETCURSEL},
{0,0,"STATIC","Sound",SS_RIGHT|WS_VISIBLE|WS_CHILD,CB_GETCURSEL},{0,0,"COMBOBOX","",CBS_DROPDOWNLIST|WS_VISIBLE|WS_CHILD|WS_TABSTOP|WS_DISABLED,CB_GETCURSEL},
{0,0,0,0,0,CB_GETCURSEL},{0,0,"BUTTON","Windowed",BS_AUTOCHECKBOX|WS_VISIBLE|WS_CHILD|WS_TABSTOP,BM_GETCHECK},{0,0,"BUTTON","PLAY",BS_PUSHBUTTON|WS_VISIBLE|WS_CHILD|WS_TABSTOP,CB_GETCURSEL},
{0,0,"BUTTON","EXIT",BS_PUSHBUTTON|WS_VISIBLE|WS_CHILD|WS_TABSTOP,CB_GETCURSEL}};static int dialogResult=0;switch(message){case WM_INITDIALOG:{SetWindowText(hwnd,"Unlimited Horror  3d by Vii[NML]");resolutions[0].x=GetSystemMetrics(SM_CXSCREEN);resolutions[0].y=GetSystemMetrics(SM_CYSCREEN);RECT rect={0,0,250,170};AdjustWindowRect(&rect,WS_POPUP| WS_BORDER| WS_SYSMENU| DS_MODALFRAME| WS_CAPTION,0);int width=rect.right-rect.left;int height=rect.bottom-rect.top;SetWindowPos(hwnd,HWND_TOPMOST,(resolutions[0].x-width)/2,(resolutions[0].y-height)/2,width,height,0);for(int i=0;i<COUNT;++i){SettingsDialogItem &item=items[(i+PLAY)%COUNT];item.handle=CreateWindowA(item.type,item.text,item.style,10+(((i+PLAY)%COUNT)%2)*120,10+(((i+PLAY)%COUNT)/2)*30,110,item.type && !strcmp
(item.type,"COMBOBOX") ? 255 : 30,hwnd,0,hInstance,0);}SendMessage(items[WINDOWED].handle,BM_SETCHECK,1,0);SendMessage(items[RESOLUTION].handle,CB_ADDSTRING,0,(LPARAM)"keep");for(int i=1;i<sizeof(resolutions)/sizeof(Tuple2<short>);++i){char data[32];wsprintfA(data,"%hdx%hd",resolutions[i].x,resolutions[i].y);SendMessage(items[RESOLUTION].handle,CB_ADDSTRING,0,(LPARAM)data);}for(int i=0;i<sizeof(zooms)/sizeof(Tuple2<short>);++i){char data[32];wsprintfA(data,"%hdx%hd",zooms[i].x,zooms[i].y);SendMessage(items[ZOOM].handle,CB_ADDSTRING,0,(LPARAM)data);}SendMessage(items[SOUND].handle,CB_ADDSTRING,0,(LPARAM)"44100");SendMessage(items[SOUND].handle,CB_ADDSTRING,0,(LPARAM)"off");
for(int i=0;i<COUNT;++i)SendMessage(items[i].handle,CB_SETCURSEL,0,0);}return 1;
case WM_COMMAND:if(lParam ==(LPARAM)items[EXIT].handle)DestroyWindow(hwnd);if(lParam !=(LPARAM)items[PLAY].handle)return 1;break;
case WM_DESTROY:PostQuitMessage(dialogResult);return 1;
case WM_CLOSE:DestroyWindow(hwnd);return 1;
default:return 0;}dialogResult=1;for(int i=0;i<COUNT;++i)items[i].value=SendMessage(items[i].handle,items[i].getType,0,0);DestroyWindow(hwnd);int resolution=items[RESOLUTION].value;int windowed=items[WINDOWED].value;if(!windowed && resolution){DEVMODE deviceMode={0};deviceMode.dmSize=sizeof(deviceMode);if(EnumDisplaySettingsEx(NULL,ENUM_CURRENT_SETTINGS,&deviceMode,0)){
deviceMode.dmPelsWidth=resolutions[resolution].x;deviceMode.dmPelsHeight=resolutions[resolution].y;
deviceMode.dmFields=0x001c0000;ChangeDisplaySettings(&deviceMode,CDS_FULLSCREEN);}}
WNDCLASSEX wc={0};wc.cbSize=sizeof(WNDCLASSEX);wc.style=CS_HREDRAW| CS_VREDRAW;wc.lpfnWndProc=windowProcedure;wc.hInstance=hInstance;wc.lpszClassName=windowClassName;RegisterClassEx(&wc);DWORD dwStyle=WS_POPUP|WS_MAXIMIZE;if(windowed)dwStyle=WS_CAPTION|WS_SYSMENU|(resolution?0:WS_MAXIMIZE);hw=CreateWindowEx(NULL,windowClassName,windowClassName,dwStyle,0,0,resolutions[resolution].x,resolutions[resolution].y,NULL,NULL,hInstance,NULL);if(windowed){scrWid=resolutions[resolution].x;scrHei=resolutions[resolution].y;RECT rcClient,rcWindow;POINT ptDiff;GetClientRect(hw,&rcClient);GetWindowRect(hw,&rcWindow);ptDiff.x=(rcWindow.right-rcWindow.left)-rcClient.right;ptDiff.y=(rcWindow.bottom-rcWindow.top)-rcClient.bottom;MoveWindow(hw,rcWindow.left,rcWindow.top,scrWid+ptDiff.x,scrHei+ptDiff.y,1);GetClientRect(hw,&rcClient);scrWid=rcClient.right-rcClient.left;scrHei=rcClient.bottom -rcClient.top;}else{SetWindowPos(hw,HWND_TOPMOST,0,0,resolutions[resolution].x,resolutions[resolution].y,0);RECT rect;GetClientRect(hw,&rect);scrWid=rect.rightrect.left;scrHei=rect.bottomrect.top;ShowCursor(0);}ShowWindow(hw,SW_SHOW);UpdateWindow(hw);scrWid/=zooms[items[ZOOM].value].x;scrHei/=zooms[items[ZOOM].value].y;scrWid_1=scrWid-1;scrHei_1=scrHei-1;bmiBackBuffer.biHeight=-scrHei;bmiBackBuffer.biWidth=scrWid;return 1;}bool settingsDialog(){hInstance=GetModuleHandle(NULL);HGLOBAL hgbl=GlobalAlloc(GMEM_ZEROINIT,1024);LPDLGTEMPLATE lpdt=(LPDLGTEMPLATE)GlobalLock(hgbl);lpdt->style=WS_POPUP| WS_BORDER| DS_MODALFRAME| WS_CAPTION;GlobalUnlock(hgbl);HWND hDialog=CreateDialogIndirect(hInstance(LPDLGTEMPLATE)hgbl,0,(DLGPROC)dialogProcedure);ShowWindow(hDialog,SW_SHOW);MSG msg;int status;while((status=GetMessage(&msg,0,0,0))>0)if(!IsDialogMessage(hDialog,&msg))DispatchMessage(&msg);GlobalFree(hgbl);return(status==0 && msg.wParam);}void exitGame(){ExitProcess(0);}void ef(DWORD* buffer){for(int i=0;i<256;++i){keyWasPressed[i]=kS[i];keyDownCount[i]=0;keyUpCount[i]=0;}RECT rect;HDC hdc=GetDC(hw);GetClientRect(hw,&rect);StretchDIBits(hdc,rect.left,rect.top,rect.right-rect.left,rect.bottom-rect.top,0,0,scrWid,scrHei,buffer,(BITMAPINFO*)(void*)&bmiBackBuffer,DIB_RGB_COLORS,SRCCOPY);ReleaseDC(hw,hdc);MSG msg;while(PeekMessage(&msg,0,0,0,PM_NOREMOVE)){if(msg.message==WM_QUIT){exitGame();return;}if(GetMessage(&msg,NULL,0,0)){DispatchMessage(&msg);if(msg.message==WM_PAINT)break;}else break;}}DWORD totalAllocated=0;void* allocate(DWORD size){GlobalCompact(size);void* data=GlobalAlloc(GPTR,size);if(!data){char msg[128];wsprintfA(msg,"Can't allocate %lu bytes of memory(already allocated %lu bytes)",size,totalAllocated);MessageBox(0,msg,windowClassName,0);exitGame();}totalAllocated+=size;return data;}void freeMemory(void* ptr){GlobalFree(ptr);}DWORD* dibCreate(DWORD wid,DWORD hei){int size=wid*hei*4+44;BYTE* ptr=(BYTE*)(void*)allocate(size);*((DWORD*)(void*)(ptr+0))=40;*((DWORD*)(void*)(ptr+4))=wid;*((DWORD*)(void*)(ptr+8))=hei;*((WORD*)(void*)(ptr+12))=1;*((WORD*)(void*)(ptr+14))=32;return(DWORD*)(void*)(ptr+44);}void dibFree(DWORD* p){freeMemory((BYTE*)(void*)p-44);}DWORD dibWidth(DWORD* pd){return pd[-10];}DWORD dibHeight(DWORD* pd){return pd[-9];}int main(int argc,const char* argv[]){FILE *in=fopen(argv[1],"rb");setvbuf(in,NULL,_IOFBF,IO_BUFFER_SIZE);FreeConsole();if(!settingsDialog()){fclose(in);return 0;}DWORD *dib=dibCreate(scrWid,scrHei);fseek(in,0,SEEK_END);long sizeBytes=ftell(in);BYTE* rawData=(BYTE*)malloc(sizeBytes);fseek(in,0,SEEK_SET);size_t br=fread(rawData,1,sizeBytes,in);fclose(in);
CubesHeader &header=*(CubesHeader*)(void*)rawData;Cube *cubes=(Cube*)(void*)(rawData+sizeof(CubesHeader));CubePoint *points=(CubePoint*)(void*)(rawData+sizeof(CubesHeader)+sizeof(Cube)*header.count);long halfScreenWidht=scrWid/2;long halfScreenHeight=scrHei/2;long screenDistance=scrWid/2;long eY=4096*400;long eX=4096*330;long eZ=4096*46;unsigned int frame=0;
while(!keyWasPressed[VK_ESCAPE]){frame++;bool cl=0;if(kS[VK_RIGHT]){eY+=1024;cl=1;}if(kS[VK_LEFT]){eY-=1024;cl=1;}if(kS[VK_UP]){eX-=1024;cl=1;}if(kS[VK_DOWN]){eX+=1024;cl=1;}if(kS['R']){eZ+=1024;cl=1;}if(kS['F']){eZ-=1024;cl=1;}if(cl)memset(dib,0,scrWid*scrHei*sizeof(DWORD));for(int c=0;c<header.count;++c){Cube &cube=cubes[c];long baseX=(long)(((DWORD)cube.x)<<16);long baseY=(long)(((DWORD)cube.y)<<16);long baseZ=(long)(((DWORD)cube.z)<<16);if(baseX>eX)continue;for(int i=frame % 123;i<cube.pointsCount;i+=123){CubePoint point=points[cube.offsetPoints+i];long x=baseX|(DWORD)point.x;long y=baseY|(DWORD)point.y;long z=baseZ|(DWORD)point.z;if(x<eX){long X=(-x+eX);long sx=(y-eY)*screenDistance/X+halfScreenWidht;long sy=halfScreenHeight-(z-eZ)*screenDistance/X;if(sx>0 && sy>0 && sx<scrWid && sy<scrHei)dib[sx+sy*scrWid]=(((DWORD)point.r)<<16)|(((DWORD)point.g)<<8)|(((DWORD)point.b));}}}ef(dib);}exitGame();return 0;}
#2935
19:36, 20 сен. 2013

Вий, это специальный стиль кода "для краткости" или случайно так вышло? -)

#2936
19:37, 20 сен. 2013

Zvz
> Вий, это специальный стиль кода "для краткости" или случайно так вышло? -)
10 000 символов на пост - ограничение форума

#2937
19:39, 20 сен. 2013

Вий
http://puu.sh/4vRcC.png лучше б в 2 поста разложил, ей богу

#2938
1:19, 21 сен. 2013

Вий
Сколько мс кадр?

Рандомно отсортировал точки, преобразовал в бинарный формат, и написал самый простейший алгоритм, который пришел в голову: http://pastebin.com/gdi7iwar

Изображение

Быстродействие все равно зависит от количества точек попадающих в кадр на обработку, на скрине обрабатываются 2 млн точек, скорость 160мс. Если смотреть выше к небу скорость возрастает до 50 мс, если в центр карты падает до 300мс.

#2939
(Правка: 4:07) 3:44, 21 сен. 2013

1.1 млн точек - 49 мс
если улететь подальше - то 1-4 мс

Страницы: 1195 196 197 198221 Следующая »
ПрограммированиеФорумГрафика