El Método es no aktuell, kommt dafür aber con el zugänglichen Befehlssatz de. Heutzutage verwendet uno VBOs (vertex buffer objects). La idea Es el gleiche aber en mi Ejemplo con glDrawArrays se anstatt el Video-RAM el herkömmliche Arbeitsspeicher verwendet. Dennoch es en una vielfaches más rápido como z.B. una oGL("DrawList", N) con tausenden oGL("Sphere", ...) en él.
Yo speichere Vertex-Daten (Punkte) de Kugeln en una Zona, welcher entonces en un Arbeitsgang cada Frame dargestellt se. Ohne Texturkoordinaten oder sin Normalen es todavía más rápido. En uno schnellen Grafikkarte scheint hier el einzige Nadelöhr el RAM a ser.
Achtung: el initiale Erstellung dauert möglicherweise muy lang, danach dejar se aber mehrere tausend Kugeln con hoher Framerate darstellen.
Oben en el Code puede testweise Normalen y Textur ausgeschaltet voluntad:
usetex& = 1
usenormal& = 1
Hier el verwendete Textur (a el XProfan Icon angelehnt):
Hier todos Listing. Wenn uno el Función para el Kugel y el Entrada-Abfrage ausklammert, es el Code muy überschaubar.
$H windows.ph
$H opengl.ph
Declarar tex&[5]
Declarar xrot!, yrot!, zrot!, xpos!, ypos!, zpos!,xsrot!,ysrot!,zsrot!,xspos!,yspos!,zspos!
Declarar smooth%,mb&,mousestartx%,mousestarty%,mousex%,mousey%
Declarar ende%,hPic&
Declarar sphere&,frame&,time&,fps&, usetex&,usenormal&
usetex& = 1
usenormal& = 1
declarar vertex#,normal#,texture#,count&
Dim vertex# ,200000000
Dim normal# ,200000000
Dim texture# ,(200000000/3*2)
proc Sphere
parámetros px!,py!,pz!,fRadius!, iStacks%,iSlices%
declarar t1a!, t1b!, n1a!, n1b!, n1c!, v1a!, v1b!, v1c!, t2a!, t2b!, n2a!, n2b!, n2c!, v2a!, v2b!, v2c!
declarar PI!,PIx2!,drho!,dtheta!,ds!,dt!,t!,s!,x!,y!,z!
declarar rho!,srho!,crho!,srhodrho!,crhodrho!
declarar theta!,stheta!,ctheta!,i%,j%,k%
PI! = Pi()
PIx2! = Pi() * 2.0
drho! = PI! / iStacks%
dtheta! = PIx2! / iSlices%
ds! = 1.0 / iSlices%
dt! = 1.0 / iStacks%
t! = 1.0
s! = 0.0
k% = 0
whileloop 0, (iStacks%-1)
i% = &bucle
rho! = i% * drho!
srho! = sin(rho!)
crho! = cos(rho!)
srhodrho! = sin(rho! + drho!)
crhodrho! = cos(rho! + drho!)
s! = 0.0
whileloop 0, iSlices%
inc k%
j% = &bucle
theta! = if(j% = iSlices%, 0.0, j% * dtheta!)
stheta! = -sin(theta!)
ctheta! = cos(theta!)
x! = stheta! * srho!
y! = ctheta! * srho!
z! = crho!
if (j% > 1)
Float vertex#,(count&*24) = v1a!,v1b!,v1c!
caso usetex& : Float texture#,(count&*16) = t1a!,t1b!
caso usenormal& : Float normal#,(count&*24) = n1a!,n1b!,n1c!
inc count&
Float vertex#,(count&*24) = v2a!,v2b!,v2c!
caso usetex& : Float texture#,(count&*16) = t2a!,t2b!
caso usenormal& : Float normal#,(count&*24) = n2a!,n2b!,n2c!
inc count&
endif
v1a! = (x! * fRadius!)+px!
v1b! = (y! * fRadius!)+py!
v1c! = (z! * fRadius!)+pz!
t1a! = s!
t1b! = t!
n1a! = x!
n1b! = y!
n1c! = z!
Float vertex#,(count&*24) = (x! * fRadius!)+px!,(y! * fRadius!)+py!, (z! * fRadius!)+pz!
caso usetex& : Float texture#,(count&*16) = s!,t!
caso usenormal& : Float normal#,(count&*24) = x!,y!,z!
inc count&
x! = stheta! * srhodrho!
y! = ctheta! * srhodrho!
z! = crhodrho!
if (j% > 0)
Float vertex#,(count&*24) = v1a!,v1b!,v1c!
caso usetex& : Float texture#,(count&*16) = t1a!,t1b!
caso usenormal& : Float normal#,(count&*24) = n1a!,n1b!,n1c!
inc count&
Float vertex#,(count&*24) = v2a!,v2b!,v2c!
caso usetex& : Float texture#,(count&*16) = t2a!,t2b!
caso usenormal& : Float normal#,(count&*24) = n2a!,n2b!,n2c!
inc count&
endif
t2a! = s!
t2b! = (t! - dt!)
n2a! = x!
n2b! = y!
n2c! = z!
v2a! = (x! * fRadius!)+px!
v2b! = (y! * fRadius!)+py!
v2c! = (z! * fRadius!)+pz!
caso usetex& : Float texture#,(count&*16 ) = t2a!,t2b!
s! = s! + ds!
caso usenormal& : Float normal#,(count&*24) = n2a!,n2b!,n2c!
Float vertex#,(count&*24) = v2a!,v2b!,v2c!
inc count&
endwhile
t! = t! - dt!
endwhile
ENDPROC
Proc MouseKeyboard
mousex% = %MouseX
mousey% = %MouseY
if mb& = 0
caso isKey(~VK_LBUTTON) : mb& = 1
caso isKey(~VK_RBUTTON) : mb& = 2
endif
if (not(isKey(~VK_RBUTTON)) & not(isKey(~VK_LBUTTON)))
'Startposition fürs rotieren y Zoomwen otra vez nullen
mb& = 0
mousestartx% = %mousex
mousestarty% = %mousey
xsrot! = xrot!
ysrot! = yrot!
zspos! = zpos!
endif
'Tastaturrotation
caso isKey(~VK_LEFT) : yrot! = yrot! - 1.0
caso isKey(~VK_RIGHT) : yrot! = yrot! + 1.0
caso isKey(~VK_UP) : xrot! = xrot! + 1.0
caso isKey(~VK_DOWN) : xrot! = xrot! - 1.0
'Mausrotation
if (mb& = 1)
yrot! = ysrot! - (mousestartx% - %mousex) * 0.4
xrot! = xsrot! - (mousestarty% - %mousey) * 0.4
endif
'Mauszoom
if (mb& = 2) & (abs(mousestarty% - %mousey) > 10)
zpos! = zspos! + (mousestarty% - %mousey) * 0.03
'Wenn darüber hinaus bewegt wurde, se lo beim Richtungswechsel trotzdem direkt rückwärts ir
'Unschöner Hack, Rechnen wäre el feinere Weg ...
mientras que (zpos! > -2.0)
dec mousestarty%
zpos! = zspos! + (mousestarty% - %mousey) * 0.03
endwhile
mientras que (zpos! < -15.0)
inc mousestarty%
zpos! = zspos! + (mousestarty% - %mousey) * 0.03
endwhile
endif
'Tastaturzoom
caso isKey(~VK_SUBTRACT) : zpos! = zpos! - 0.06
caso isKey(~VK_ADD) : zpos! = zpos! + 0.06
'Zoom begrenzen
caso (zpos! > -2.0) : zpos! = -2.0
caso (zpos! < -15.0) : zpos! = -15.0
'Sonstige Tastatureingaben
caso IsKey(27) : Ende% = 1
ENDPROC
Proc DrawGLScene
oGL("Clear")
ogl("Origin",0,0,-0.2)
oGL("Move", xpos!, ypos!, zpos!)
oGL("Rotate", xrot!,yrot!,zrot!)
oGL("glDrawArrays",~GL_TRIANGLES, 0 ,count&-1)'mode, first, count
oGL("Show")
ENDPROC
' Hauptprogramm
' -------------
windowstyle 1+2+4+8+16
windowtitle "Sphere"
window (%maxx * 0.5 -480), (%maxy * 0.5 - 300) - 960,600'kompatible Schreibweise
UseIcon "Gesicht"
oGL("Init", %hWnd, 1,1,1,1)
oGL("PosMode",1)
oGL("glEnable", ~GL_CULL_FACE)
'oGL("glShadeModel", ~GL_FLAT)
caso usetex& : oGL("glEnableClientState",~GL_TEXTURE_COORD_ARRAY_EXT)
caso usenormal& : oGL("glEnableClientState",~GL_NORMAL_ARRAY_EXT)
oGL("glEnableClientState",~GL_VERTEX_ARRAY_EXT)
caso usetex& : oGL("glTexCoordPointer",2,~GL_DOUBLE,0,texture#)
caso usenormal& : oGL("glNormalPointer",~GL_DOUBLE,0,normal#)
oGL("glVertexPointer",3,~GL_DOUBLE,0,vertex#)
hPic&=create("HPIC",-1,"smile.png")
tex&[1]=ogl("getTextureBmp",hPic&,2)
DeleteObject hPic&
oGL("Texture",tex&[1],1)
'oGL("Texture",0,1)
whileloop 0, 500
'Sphere(X, Y, Z, Größe, Scheiben, Segmente)
Sphere((rnd(1000)-500)*0.01,(rnd(1000)-500)*0.01,(rnd(1000)-500)*0.01,0.05,6,6)
endwhile
zpos! = -5
xrot! = -90
yrot! = 0
time& = &gettickcount
Sinestar encargado ende%
if (frame& MOD 100 = 0)
time& = ((&gettickcount - time&) * 0.01) + 1
fps& = 1000 / time&
setText %hWnd, str$(fps&) + " fps"
time& = &gettickcount
endif
MouseKeyboard()
DrawGLScene()
inc frame&
EndWhile
oGL("Done")
End
|