⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nurbrefine.c

📁 [Game.Programming].Academic - Graphics Gems (6 books source code)
💻 C
字号:
/* * NurbRefine.c - Given a refined knot vector, add control points to a surface. * * John Peterson */#include <stdlib.h>#include <stdio.h>#include <math.h>#include "nurbs.h"/* * Given the original knot vector ukv, and a new knotvector vkv, compute * the "alpha matrix" used to generate the corresponding new control points. * This routines allocates the alpha matrix if it isn't allocated already. * * This is from Bartels, Beatty & Barsky, p. 407 */static voidCalcAlpha( double * ukv, double * wkv, long m, long n, long k, double *** alpha ){    register long i, j;    long brkPoint, r, rm1, last, s;    double omega;    double aval[MAXORDER];    if (! *alpha)	/* Must allocate alpha */    {	CHECK( *alpha = (double **) malloc( (long) ((k+1) * sizeof( double * ))) );	for (i = 0; i <= k; i++)	    CHECK( (*alpha)[i] = (double *) malloc( (long) ((m + n + 1)						    * sizeof( double ))) );    }    for (j = 0; j <= m + n; j++)    {	brkPoint = FindBreakPoint( wkv[j], ukv, m, k );	aval[0] = 1.0;	for (r = 2; r <= k; r++)	{	    rm1 = r - 1;	    last = MIN( rm1, brkPoint );	    i = brkPoint - last;	    if (last < rm1)		aval[last] = aval[last] * (wkv[j + r - 1] - ukv[i])			    / (ukv[i + r - 1] - ukv[i]);	    else		aval[last] = 0.0;	    for (s = last - 1; s >= 0; s-- )	    {		i++;		omega = (wkv[j + r - 1] - ukv[i]) / (ukv[i + r - 1] - ukv[i]);		aval[s + 1] = aval[s+1] + (1 - omega) * aval[s];		aval[s] = omega * aval[s];	    }	}	last = MIN( k - 1, brkPoint );	for (i = 0; i <= k; i++)	    (*alpha)[i][j] = 0.0;	for (s = 0; s <= last; s++)	    (*alpha)[last - s][j] = aval[s];    }}/* * Apply the alpha matrix computed above to the rows (or columns) * of the surface.  If dirflag is true do the U's (row), else do V's (col). */voidRefineSurface( NurbSurface * src, NurbSurface * dest, Boolean dirflag ){    register long i, j, out;    register Point4 * dp, * sp;    long i1, brkPoint, maxj, maxout;    register double tmp;    double ** alpha = NULL;    /* Compute the alpha matrix and indexing variables for the requested direction */    if (dirflag)    {	CalcAlpha( src->kvU, dest->kvU, src->numU - 1, dest->numU - src->numU,		   src->orderU, &alpha );	maxj = dest->numU;	maxout = src->numV;    }    else    {	CalcAlpha( src->kvV, dest->kvV, src->numV - 1, dest->numV - src->numV,		   src->orderV, &alpha );	maxj = dest->numV;	maxout = dest->numU;    }    /* Apply the alpha matrix to the original control points, generating new ones */    for (out = 0; out < maxout; out++)	for (j = 0; j < maxj; j++)	{	    if (dirflag)	    {		dp = &(dest->points[out][j]);		brkPoint = FindBreakPoint( dest->kvU[j], src->kvU,					   src->numU-1, src->orderU );		i1 = MAX( brkPoint - src->orderU + 1, 0 );		sp = &(src->points[out][i1]);	    } else {		dp = &(dest->points[j][out]);		brkPoint = FindBreakPoint( dest->kvV[j], src->kvV,					   src->numV-1, src->orderV );		i1 = MAX( brkPoint - src->orderV + 1, 0 );		sp = &(src->points[i1][out]);	    }	    dp->x = 0.0;	    dp->y = 0.0;	    dp->z = 0.0;	    dp->w = 0.0;	    for (i = i1; i <= brkPoint; i++)	    {		tmp = alpha[i - i1][j];		sp = (dirflag ? &(src->points[out][i]) : &(src->points[i][out]) );		dp->x += tmp * sp->x;		dp->y += tmp * sp->y;		dp->z += tmp * sp->z;		dp->w += tmp * sp->w;	    }	}    /* Free up the alpha matrix */    for (i = 0; i <= (dirflag ? src->orderU : src->orderV); i++)	free( alpha[i] );    free( alpha );}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -