void render_lodder_sphere(int group, Vertex spherepos, Vertex spherepos2, float diam, float powr, float push, float timex) { Vertex *loddata[MAX_LOD_REDUCTION+1]; Vertex *v, *n; int vc=loddermesh->groups[group]->vc; int fc=loddermesh->groups[group]->fc; int *i=loddermesh->groups[group]->indices; float *c; unsigned char *lodlevels; // assign lod buffers, 0=original loddata[0]=loddermesh->groups[group]->vertices; for (int i=0; i<MAX_LOD_REDUCTION; i++) loddata[i+1]=lodder_vertices[group][i]; v=tmpmalloc(sizeof(Vertex)*vc); n=tmpmalloc(sizeof(Vertex)*vc); c=tmpmalloc(sizeof(float)*vc*4); lodlevels=tmpmalloc(vc); // calc vertices for (int x=0; x<vc; x++) { Vertex l0pos=loddata[0][x]; float xx=(l0pos.x-spherepos.x); float yy=(l0pos.y-spherepos.y); float zz=(l0pos.z-spherepos.z); float xx2=(l0pos.x-spherepos2.x); float yy2=(l0pos.y-spherepos2.y); float zz2=(l0pos.z-spherepos2.z); float dist=sqrt(xx*xx+yy*yy+zz*zz); float dist2=sqrt(xx2*xx2+yy2*yy2+zz2*zz2); float powah=r0(diam-dist)/diam; // 0..1 sphere float powah2=r0(diam-dist2)/diam; float lod=clamp((powah+powah2)*powr); //lod=clamp(powr); float lodfract=lod*(float)MAX_LOD_REDUCTION; int bufnum=(int)floor(lodfract); lodfract=fmod(lodfract, 1.0); c[x*3+0]=c[x*3+1]=c[x*3+2]=clamp((lod-0.1)*4.0); // calc lodded pos if (lod==0.0) { v[x]=l0pos; lodlevels[x]=0; } else if (lod==1.0) { v[x]=loddata[MAX_LOD_REDUCTION][x]; lodlevels[x]=1; } else { Vertex l0=loddata[bufnum][x]; Vertex l1=loddata[bufnum+1][x]; v[x].x = l0.x*(1.0-lodfract)+l1.x*(lodfract); v[x].y = l0.y*(1.0-lodfract)+l1.y*(lodfract); v[x].z = l0.z*(1.0-lodfract)+l1.z*(lodfract); lodlevels[x]=1; } // push Vertex pd=new_v(v[x].x-spherepos.x, v[x].y-spherepos.y, v[x].z-spherepos.z); Vertex pd2=new_v(v[x].x-spherepos2.x, v[x].y-spherepos2.y, v[x].z-spherepos2.z); normalize(&pd); normalize(&pd2); v[x].x+=push*powah*pd.x+push*powah2*pd2.x; v[x].y+=push*powah*pd.y+push*powah2*pd2.y; v[x].z+=push*powah*pd.z+push*powah2*pd2.z; // little something for normal n[x]=new_v(0.0, 0.00001, 0.0); } // calc normals for (int x=0; x<fc; x++) { Vertex fnorm; Vertex *v1, *v2, *v3; Vertex *n1, *n2, *n3; v1=&v[i[x*3+0]]; v2=&v[i[x*3+1]]; v3=&v[i[x*3+2]]; n1=&n[i[x*3+0]]; n2=&n[i[x*3+1]]; n3=&n[i[x*3+2]]; calc_fnorm_nn(v1, v2, v3, &fnorm); n1->x+=fnorm.x; n1->y+=fnorm.y; n1->z+=fnorm.z; n2->x+=fnorm.x; n2->y+=fnorm.y; n2->z+=fnorm.z; n3->x+=fnorm.x; n3->y+=fnorm.y; n3->z+=fnorm.z; } // normalize normals, for lod 0 use original normal for (int x=0; x<vc; x++) { if (lodlevels[x]==0) n[x]=loddermesh->groups[group]->normals[x]; else normalize(&n[x]); } // render arrays // glUniform1fARB(glGetUniformLocationARB(shader, "depthmult"), 1.0); glue_disableallarrays(); glEnableClientState(GL_VERTEX_ARRAY); glVertexPointer(3, GL_FLOAT, 0, v); glEnableClientState(GL_NORMAL_ARRAY); glNormalPointer(GL_FLOAT, 0, n); /* Vertex *t=loddermesh->groups[group]->texcoords; if (t) { glClientActiveTexture(GL_TEXTURE0_ARB); glEnableClientState(GL_TEXTURE_COORD_ARRAY); glTexCoordPointer(3, GL_FLOAT, 0, t); }*/ // alkup. verteksit texturekoordinaateiks glClientActiveTexture(GL_TEXTURE1_ARB); glActiveTexture(GL_TEXTURE1_ARB); glEnableClientState(GL_TEXTURE_COORD_ARRAY); glTexCoordPointer(3, GL_FLOAT, 0, loddata[0]); glDrawElements(GL_TRIANGLES, fc*3, GL_UNSIGNED_INT, i); /* // wireframe //glUniform1fARB(glGetUniformLocationARB(shader, "depthmult"), 0.0); //renderflags(GLUE_BLEND_ALPHAADD|GLUE_CHECK_DEPTH); renderflags(GLUE_BLEND|GLUE_CHECK_DEPTH); glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); glEnable(GL_POLYGON_OFFSET_LINE); glPolygonOffset(1.0, 1.0); //glEnable(GL_LINE_SMOOTH); glLineWidth(glueXres/320); glueDisabletexture(); glDisableClientState(GL_NORMAL_ARRAY); glDisableClientState(GL_TEXTURE_COORD_ARRAY); glEnableClientState(GL_COLOR_ARRAY); glColorPointer(3, GL_FLOAT, 0, c); glDrawElements(GL_TRIANGLES, fc*3, GL_UNSIGNED_INT, i); glue_disableallarrays(); glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); glDisable(GL_POLYGON_OFFSET_LINE); */ glue_disableallarrays(); tmpfree(lodlevels); tmpfree(c); tmpfree(n); tmpfree(v); }
void glueMpeg2_get(Mpeg2 *mpg, Texture *dst, int sync_channel, float fps, int border, int skip_frames, int reset_on_error) { unsigned char *tmpbuf; int framecnt=0; float curtime; #ifdef USE_FMODEX if(sync_channel==-1) // no audio sync curtime = timeGetTime(); else // get time from audio channel curtime = fmod_gettick_channel(sync_channel)+(1000.0/fps); #else curtime = timeGetTime(); #endif if (mpg->end==1) { glueMpeg2_reset(mpg); } if (mpg->prevtime==0) { getframe(mpg, dst); if (mpg->end==2) { glueMpeg2_reset(mpg); return; } if (mpg->end==3) { if (reset_on_error) glueMpeg2_reset(mpg); return; } } else if (curtime-mpg->prevtime < 1000.0/fps) return; else { int x; framecnt=(curtime-mpg->prevtime)/(1000.0/fps); if (skip_frames==0 && framecnt>1) framecnt=1; for (x=0; x<framecnt; x++) { getframe(mpg, dst); if (mpg->end==2) { glueMpeg2_reset(mpg); return; } if (mpg->end==3) { if (reset_on_error) glueMpeg2_reset(mpg); return; } } } if (mpg->prevtime==0) mpg->prevtime=curtime; else mpg->prevtime+=1000.0/fps*framecnt; //mpg->prevtime=timeGetTime(); tmpbuf=tmpmalloc(dst->xres*dst->yres*4); if (mpg->info->display_fbuf) { int w, h; w=mpg->info->sequence->width; h=mpg->info->sequence->height; if (dst->xres==w && dst->yres==h && (!border)) { glueReloadtexture(dst, mpg->info->display_fbuf->buf[0]); } else { int x; memset(tmpbuf, 0, dst->xres*dst->yres*4); if (dst->xres < w || dst->yres < h) glueErrorf("erreur: ur texture too small for ur videoz (%ix%i vs %ix%i)", w, h, dst->xres, dst->yres); for (x=0; x<h; x++) memcpy(tmpbuf+x*dst->xres*4, mpg->info->display_fbuf->buf[0]+x*w*4, dst->xres*4); if (border) { for (x=0; x<w; x++) { blask(tmpbuf, x); blask(tmpbuf, x+(h-1)*dst->xres); } for (x=0; x<h; x++) { blask(tmpbuf, x*dst->xres); blask(tmpbuf, x*dst->xres+w-1); } } dst->scale.x=(float)w/dst->xres; dst->scale.y=(float)h/dst->yres; glueReloadtexture(dst, tmpbuf); } } tmpfree(tmpbuf); }