./PaxHeaders.26136/nurbs-1.3.13 0000644 0000000 0000000 00000000132 13070134113 012537 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.516614779
30 ctime=1491122251.516614779
nurbs-1.3.13/ 0000755 0001750 0001750 00000000000 13070134113 012635 5 ustar 00bect bect 0000000 0000000 nurbs-1.3.13/PaxHeaders.26136/DESCRIPTION 0000644 0000000 0000000 00000000132 13070134113 014165 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/DESCRIPTION 0000644 0001750 0001750 00000000637 13070134113 014351 0 ustar 00bect bect 0000000 0000000 Name: nurbs
Version: 1.3.13
Date: 2017-03-28
Author: Mark Spink, Daniel Claxton, Carlo de Falco, Rafael Vazquez
Maintainer: Carlo de Falco and Rafael Vazquez
Title: Nurbs.
Description: Collection of routines for the creation, and manipulation of Non-Uniform Rational B-Splines (NURBS), based on the NURBS toolbox by Mark Spink.
Categories: splines
Depends: octave (>= 3.8)
License: GPLv3+
Url: http://octave.sf.net
nurbs-1.3.13/PaxHeaders.26136/inst 0000644 0000000 0000000 00000000132 13070134113 013357 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.516614779
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/ 0000755 0001750 0001750 00000000000 13070134113 013612 5 ustar 00bect bect 0000000 0000000 nurbs-1.3.13/inst/PaxHeaders.26136/bspeval.m 0000644 0000000 0000000 00000000132 13070134113 015246 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspeval.m 0000644 0001750 0001750 00000007374 13070134113 015437 0 ustar 00bect bect 0000000 0000000 function p = bspeval(d,c,k,u)
% BSPEVAL: Evaluate B-Spline at parametric points.
%
% Calling Sequence:
%
% p = bspeval(d,c,k,u)
%
% INPUT:
%
% d - Degree of the B-Spline.
% c - Control Points, matrix of size (dim,nc).
% k - Knot sequence, row vector of size nk.
% u - Parametric evaluation points, row vector of size nu.
%
% OUTPUT:
%
% p - Evaluated points, matrix of size (dim,nu)
%
% Copyright (C) 2000 Mark Spink, 2007 Daniel Claxton, 2010 C. de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
nu = numel(u);
[mc,nc] = size(c);
% int bspeval(int d, double *c, int mc, int nc, double *k, int nk, double *u,int nu, double *p){
% int ierr = 0;
% int i, s, tmp1, row, col;
% double tmp2;
%
% // Construct the control points
% double **ctrl = vec2mat(c,mc,nc);
%
% // Contruct the evaluated points
% double **pnt = vec2mat(p,mc,nu);
%
% // space for the basis functions
%N = zeros(d+1,1); % double *N = (double*) mxMalloc((d+1)*sizeof(double));
%
% // for each parametric point i
%for col=1:nu % for (col = 0; col < nu; col++) {
% // find the span of u[col]
s = findspan(nc-1, d, u(:), k); % s = findspan(nc-1, d, u[col], k);
N = basisfun(s,u(:),d,k); % basisfun(s, u[col], d, k, N);
%
tmp1 = s - d + 1; % tmp1 = s - d;
%for row=1:mc % for (row = 0; row < mc; row++) {
p = zeros (mc, nu); % tmp2 = 0.0;
for i=0:d % for (i = 0; i <= d; i++)
p = p + repmat (N(:,i+1)', mc, 1).*c(:,tmp1+i); % tmp2 += N[i] * ctrl[tmp1+i][row];
end %
%p(row,:) = tmp2; % pnt[col][row] = tmp2;
%end % }
%end % }
%
% mxFree(N);
% freevec2mat(pnt);
% freevec2mat(ctrl);
%
% return ierr;
end % }
nurbs-1.3.13/inst/PaxHeaders.26136/nrbrect.m 0000644 0000000 0000000 00000000132 13070134113 015251 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbrect.m 0000644 0001750 0001750 00000003331 13070134113 015427 0 ustar 00bect bect 0000000 0000000 function curve = nrbrect(w,h)
%
% NRBRECT: Construct NURBS representation of a rectangular curve.
%
% Calling Sequence:
%
% crv = nrbrect()
% crv = nrbrect(size)
% crv = nrbrect(width, height)
%
% INPUT:
%
% size : Size of the square (width = height).
%
% width : Width of the rectangle (along x-axis).
%
% height : Height of the rectangle (along y-axis).
%
% OUTPUT:
%
% crv : NURBS curve, see nrbmak.
%
%
% Description:
%
% Construct a rectangle or square in the x-y plane with the bottom
% lhs corner at (0,0,0). If no rhs arguments provided the function
% constructs a unit square.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 1
w = 1;
h = 1;
end
if nargin < 2
h = w;
end
coefs = [0 w w w w 0 0 0;
0 0 0 h h h h 0;
0 0 0 0 0 0 0 0;
1 1 1 1 1 1 1 1];
knots = [0 0 0.25 0.25 0.5 0.5 0.75 0.75 1 1];
curve = nrbmak(coefs, knots);
end
%!demo
%! crv = nrbtform(nrbrect(2,1), vecrotz(35*pi/180));
%! nrbplot(crv,4);
%! axis equal
%! title('Construction and rotation of a rectangular curve.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/vecdot.m 0000644 0000000 0000000 00000000132 13070134113 015076 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecdot.m 0000644 0001750 0001750 00000002650 13070134113 015257 0 ustar 00bect bect 0000000 0000000 function dot = vecdot(vec1,vec2)
%
% VECDOT: The dot product of two vectors.
%
% Calling Sequence:
%
% dot = vecdot(vec1,vec2);
%
% INPUT:
%
% vec1 : An array of column vectors represented by a matrix of
% vec2 size (dim,nv), where is the dimension of the vector and
% nv the number of vectors.
%
% OUTPUT:
%
% dot : Row vector of scalars, each element corresponding to
% the dot product of the respective components in vec1 and
% vec2.
%
% Description:
%
% Scalar dot product of two vectors.
%
% Examples:
%
% Determine the dot product of
% (2.3,3.4,5.6) and (1.2,4.5,1.2)
% (5.1,0.0,2.3) and (2.5,3.2,4.0)
%
% dot = vecdot([2.3 5.1; 3.4 0.0; 5.6 2.3],[1.2 2.5; 4.5 3.2; 1.2 4.0]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
dot = sum(vec1.*vec2);
end
nurbs-1.3.13/inst/PaxHeaders.26136/bspderiv.m 0000644 0000000 0000000 00000000132 13070134113 015430 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspderiv.m 0000644 0001750 0001750 00000006524 13070134113 015615 0 ustar 00bect bect 0000000 0000000 function [dc,dk] = bspderiv(d,c,k)
% BSPDERIV: B-Spline derivative.
%
% MATLAB SYNTAX:
%
% [dc,dk] = bspderiv(d,c,k)
%
% INPUT:
%
% d - degree of the B-Spline
% c - control points double matrix(mc,nc)
% k - knot sequence double vector(nk)
%
% OUTPUT:
%
% dc - control points of the derivative double matrix(mc,nc)
% dk - knot sequence of the derivative double vector(nk)
%
% Modified version of Algorithm A3.3 from 'The NURBS BOOK' pg98.
%
% Copyright (C) 2000 Mark Spink, 2007 Daniel Claxton
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
[mc,nc] = size(c);
nk = numel(k);
%
% int bspderiv(int d, double *c, int mc, int nc, double *k, int nk, double *dc,
% double *dk)
% {
% int ierr = 0;
% int i, j, tmp;
%
% // control points
% double **ctrl = vec2mat(c,mc,nc);
%
% // control points of the derivative
dc = zeros(mc,nc-1); % double **dctrl = vec2mat(dc,mc,nc-1);
%
for i=0:nc-2 % for (i = 0; i < nc-1; i++) {
tmp = d / (k(i+d+2) - k(i+2)); % tmp = d / (k[i+d+1] - k[i+1]);
dc(1:mc,i+1) = tmp * (c(1:mc,i+2) - c(1:mc,i+1)); % for (j = 0; j < mc; j++) {
% dctrl[i][j] = tmp * (ctrl[i+1][j] - ctrl[i][j]);
end % }
% }
%
dk = zeros(1,nk-2); % j = 0;
dk(1:nk-2) = k(2:nk-1); % for (i = 1; i < nk-1; i++)
% dk[j++] = k[i];
%
% freevec2mat(dctrl);
% freevec2mat(ctrl);
%
% return ierr;
end % }
nurbs-1.3.13/inst/PaxHeaders.26136/nrbtestsrf.m 0000644 0000000 0000000 00000000132 13070134113 016006 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbtestsrf.m 0000644 0001750 0001750 00000003603 13070134113 016166 0 ustar 00bect bect 0000000 0000000 function srf = nrbtestsrf
% NRBTESTSRF: Constructs a simple test surface.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
% allocate multi-dimensional array of control points
pnts = zeros(3,5,5);
% define a grid of control points
% in this case a regular grid of u,v points
% pnts(3,u,v)
%
pnts(:,:,1) = [ 0.0 3.0 5.0 8.0 10.0; % w*x
0.0 0.0 0.0 0.0 0.0; % w*y
2.0 2.0 7.0 7.0 8.0]; % w*z
pnts(:,:,2) = [ 0.0 3.0 5.0 8.0 10.0;
3.0 3.0 3.0 3.0 3.0;
0.0 0.0 5.0 5.0 7.0];
pnts(:,:,3) = [ 0.0 3.0 5.0 8.0 10.0;
5.0 5.0 5.0 5.0 5.0;
0.0 0.0 5.0 5.0 7.0];
pnts(:,:,4) = [ 0.0 3.0 5.0 8.0 10.0;
8.0 8.0 8.0 8.0 8.0;
5.0 5.0 8.0 8.0 10.0];
pnts(:,:,5) = [ 0.0 3.0 5.0 8.0 10.0;
10.0 10.0 10.0 10.0 10.0;
5.0 5.0 8.0 8.0 10.0];
% knots
knots{1} = [0 0 0 1/3 2/3 1 1 1]; % knots along u
knots{2} = [0 0 0 1/3 2/3 1 1 1]; % knots along v
% make and draw nurbs surface
srf = nrbmak(pnts,knots);
end
%!demo
%! srf = nrbtestsrf;
%! nrbplot(srf,[20 30])
%! title('Test surface')
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/nrbkntins.m 0000644 0000000 0000000 00000000132 13070134113 015622 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbkntins.m 0000644 0001750 0001750 00000013601 13070134113 016001 0 ustar 00bect bect 0000000 0000000 function inurbs = nrbkntins(nurbs,iknots)
%
% NRBKNTINS: Insert a single or multiple knots into a NURBS curve,
% surface or volume.
%
% Calling Sequence:
%
% icrv = nrbkntins(crv,iuknots);
% isrf = nrbkntins(srf,{iuknots ivknots});
% ivol = nrbkntins(vol,{iuknots ivknots iwknots});
%
% INPUT:
%
% crv : NURBS curve, see nrbmak.
%
% srf : NURBS surface, see nrbmak.
%
% srf : NURBS volume, see nrbmak.
%
% iuknots : Knots to be inserted along U direction.
%
% ivknots : Knots to be inserted along V direction.
%
% iwknots : Knots to be inserted along W direction.
%
% OUTPUT:
%
% icrv : new NURBS structure for a curve with knots inserted.
%
% isrf : new NURBS structure for a surface with knots inserted.
%
% ivol : new NURBS structure for a volume with knots inserted.
%
% Description:
%
% Inserts knots into the NURBS data structure, these can be knots at
% new positions or at the location of existing knots to increase the
% multiplicity. Note that the knot multiplicity cannot be increased
% beyond the order of the spline. Knots along the V direction can only
% inserted into NURBS surfaces, not curve that are always defined along
% the U direction. This function use the B-Spline function bspkntins,
% which interfaces to an internal 'C' routine.
%
% Examples:
%
% Insert two knots into a curve, one at 0.3 and another
% twice at 0.4
%
% icrv = nrbkntins(crv, [0.3 0.4 0.4])
%
% Insert into a surface two knots as (1) into the U knot
% sequence and one knot into the V knot sequence at 0.5.
%
% isrf = nrbkntins(srf, {[0.3 0.4 0.4] [0.5]})
%
% See also:
%
% bspkntins
%
% Note:
%
% No knot multiplicity will be increased beyond the order of the spline.
%
% Copyright (C) 2000 Mark Spink, 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 2
error('Input argument must include the NURBS and knots to be inserted');
end
if ~isstruct(nurbs)
error('NURBS representation is not structure!');
end
if ~strcmp(nurbs.form,'B-NURBS')
error('Not a recognised NURBS representation');
end
degree = nurbs.order-1;
if iscell(nurbs.knots)
fmax = @(x,y) any (y > max(x)); fmin = @(x,y) any (y < min(x));
if (any(cellfun(fmax, nurbs.knots, iknots)) || any(cellfun(fmin, nurbs.knots, iknots)))
error ('Trying to insert a knot outside the interval of definition')
end
if size(nurbs.knots,2)==3
% NURBS represents a volume
num1 = nurbs.number(1);
num2 = nurbs.number(2);
num3 = nurbs.number(3);
% Insert knots along the w direction
if isempty(iknots{3})
coefs = nurbs.coefs;
knots{3} = nurbs.knots{3};
else
coefs = reshape(nurbs.coefs,4*num1*num2,num3);
[coefs,knots{3}] = bspkntins(degree(3),coefs,nurbs.knots{3},iknots{3});
num3 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num2 num3]);
end
% Insert knots along the v direction
if isempty(iknots{2})
knots{2} = nurbs.knots{2};
else
coefs = permute(coefs,[1 2 4 3]);
coefs = reshape(coefs,4*num1*num3,num2);
[coefs,knots{2}] = bspkntins(degree(2),coefs,nurbs.knots{2},iknots{2});
num2 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num3 num2]);
coefs = permute(coefs,[1 2 4 3]);
end
% Insert knots along the u direction
if isempty(iknots{1})
knots{1} = nurbs.knots{1};
else
coefs = permute(coefs,[1 3 4 2]);
coefs = reshape(coefs,4*num2*num3,num1);
[coefs,knots{1}] = bspkntins(degree(1),coefs,nurbs.knots{1},iknots{1});
coefs = reshape(coefs,[4 num2 num3 size(coefs,2)]);
coefs = permute(coefs,[1 4 2 3]);
end
elseif size(nurbs.knots,2)==2
% NURBS represents a surface
num1 = nurbs.number(1);
num2 = nurbs.number(2);
% Insert knots along the v direction
if isempty(iknots{2})
coefs = nurbs.coefs;
knots{2} = nurbs.knots{2};
else
coefs = reshape(nurbs.coefs,4*num1,num2);
[coefs,knots{2}] = bspkntins(degree(2),coefs,nurbs.knots{2},iknots{2});
num2 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num2]);
end
% Insert knots along the u direction
if isempty(iknots{1})
knots{1} = nurbs.knots{1};
else
coefs = permute(coefs,[1 3 2]);
coefs = reshape(coefs,4*num2,num1);
[coefs,knots{1}] = bspkntins(degree(1),coefs,nurbs.knots{1},iknots{1});
coefs = reshape(coefs,[4 num2 size(coefs,2)]);
coefs = permute(coefs,[1 3 2]);
end
end
else
if (any(iknots > max(nurbs.knots)) || any(iknots < min(nurbs.knots)))
error ('Trying to insert a knot outside the interval of definition')
end
% NURBS represents a curve
if isempty(iknots)
coefs = nurbs.coefs;
knots = nurbs.knots;
else
[coefs,knots] = bspkntins(degree,nurbs.coefs,nurbs.knots,iknots);
end
end
% construct new NURBS
inurbs = nrbmak(coefs,knots);
end
%!demo
%! crv = nrbtestcrv;
%! plot(crv.coefs(1,:),crv.coefs(2,:),'bo')
%! title('Knot insertion along test curve: curve and control polygons.');
%! hold on;
%! plot(crv.coefs(1,:),crv.coefs(2,:),'b--');
%!
%! nrbplot(crv,48);
%!
%! icrv = nrbkntins(crv,[0.125 0.375 0.625 0.875] );
%! plot(icrv.coefs(1,:),icrv.coefs(2,:),'ro')
%! plot(icrv.coefs(1,:),icrv.coefs(2,:),'r--');
%! hold off nurbs-1.3.13/inst/PaxHeaders.26136/nrbreverse.m 0000644 0000000 0000000 00000000132 13070134113 015767 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbreverse.m 0000644 0001750 0001750 00000005674 13070134113 016161 0 ustar 00bect bect 0000000 0000000 function nrb = nrbreverse(nrb, idir)
%
% NRBREVERSE: Reverse the evaluation directions of a NURBS geometry.
%
% Calling Sequence:
%
% rnrb = nrbreverse(nrb);
% rnrb = nrbreverse(nrb, idir);
%
% INPUT:
%
% nrb : NURBS data structure, see nrbmak.
% idir : vector of directions to reverse.
%
% OUTPUT:
%
% rnrb : Reversed NURBS.
%
% Description:
%
% Utility function to reverse the evaluation direction of a NURBS
% curve or surface.
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2013 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin > 2)
error('Incorrect number of input arguments');
end
if (iscell(nrb.knots))
% reverse a NURBS surface or volume
ndim = numel (nrb.knots);
if (nargin == 1 || isempty (idir))
idir = 1:ndim;
end
for ii = idir
nrb.knots{ii} = sort (nrb.knots{ii}(end) - nrb.knots{ii});
nrb.coefs = flipdim (nrb.coefs, ii+1);
end
else
% reverse a NURBS curve
nrb.knots = sort (nrb.knots(end) - nrb.knots);
nrb.coefs = fliplr (nrb.coefs);
end
end
%!demo
%! pnts = [0.5 1.5 3.0 7.5 8.5;
%! 3.0 5.5 1.5 4.0 4.5;
%! 0.0 0.0 0.0 0.0 0.0];
%! crv1 = nrbmak(pnts,[0 0 0 1/2 3/4 1 1 1]);
%! crv2 = nrbreverse(crv1);
%! fprintf('Knots of the original curve\n')
%! disp(crv1.knots)
%! fprintf('Knots of the reversed curve\n')
%! disp(crv2.knots)
%! fprintf('Control points of the original curve\n')
%! disp(crv1.coefs(1:2,:))
%! fprintf('Control points of the reversed curve\n')
%! disp(crv2.coefs(1:2,:))
%! nrbplot(crv1,100)
%! hold on
%! nrbplot(crv2,100)
%! title('The curve and its reverse are the same')
%! hold off
%!test
%! srf = nrbrevolve(nrbline([1 0],[2 0]), [0 0 0], [0 0 1], pi/2);
%! srf = nrbkntins (srf, {0.3, 0.6});
%! srf2 = nrbreverse (srf);
%! assert (srf.knots, cellfun(@(x) sort(1-x), srf2.knots, 'UniformOutput', false), 1e-15)
%! assert (srf.coefs, srf2.coefs(:,end:-1:1,end:-1:1))
%!test
%! srf = nrbrevolve(nrbline([1 0],[2 0]), [0 0 0], [0 0 1], pi/2);
%! srf = nrbkntins (srf, {0.3, 0.6});
%! srf2 = nrbreverse (srf, 1);
%! knt{1} = sort(1-srf2.knots{1}); knt{2} = srf2.knots{2};
%! assert (srf.knots, knt, 1e-15)
%! assert (srf.coefs, srf2.coefs(:,end:-1:1,:))
%! srf2 = nrbreverse (srf, 2);
%! knt{1} = srf2.knots{1}; knt{2} = sort(1-srf2.knots{2});
%! assert (srf.knots, knt, 1e-15)
%! assert (srf.coefs, srf2.coefs(:,:,end:-1:1))
nurbs-1.3.13/inst/PaxHeaders.26136/nrbruled.m 0000644 0000000 0000000 00000000132 13070134113 015427 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbruled.m 0000644 0001750 0001750 00000004703 13070134113 015611 0 ustar 00bect bect 0000000 0000000 function srf = nrbruled (crv1, crv2)
% NRBRULED: Construct a ruled surface between two NURBS curves.
%
% Calling Sequence:
%
% srf = nrbruled(crv1, crv2)
%
% INPUT:
%
% crv1 : First NURBS curve, see nrbmak.
%
% crv2 : Second NURBS curve, see nrbmak.
%
% OUTPUT:
%
% srf : Ruled NURBS surface.
%
% Description:
%
% Constructs a ruled surface between two NURBS curves. The ruled surface is
% ruled along the V direction.
%
% Examples:
%
% Construct a ruled surface between a semicircle and a straight line.
%
% cir = nrbcirc(1,[0 0 0],0,pi);
% line = nrbline([-1 0.5 1],[1 0.5 1]);
% srf = nrbruled(cir,line);
% nrbplot(srf,[20 20]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (iscell(crv1.knots) || iscell(crv2.knots))
error ('Both NURBS must be curves');
end
% ensure both curves have a common degree
d = max ([crv1.order, crv2.order]);
crv1 = nrbdegelev (crv1, d - crv1.order);
crv2 = nrbdegelev (crv2, d - crv2.order);
% merge the knot vectors, to obtain a common knot vector
k1 = crv1.knots;
k2 = crv2.knots;
ku = unique ([k1 k2]);
n = length (ku);
ka = [];
kb = [];
for i = 1:n
i1 = length (find (k1 == ku(i)));
i2 = length (find (k2 == ku(i)));
m = max (i1, i2);
ka = [ka ku(i)*ones(1,m-i1)];
kb = [kb ku(i)*ones(1,m-i2)];
end
crv1 = nrbkntins (crv1, ka);
crv2 = nrbkntins (crv2, kb);
coefs(:,:,1) = crv1.coefs;
coefs(:,:,2) = crv2.coefs;
srf = nrbmak (coefs, {crv1.knots, [0 0 1 1]});
end
%!demo
%! pnts = [0.5 1.5 4.5 3.0 7.5 6.0 8.5;
%! 3.0 5.5 5.5 1.5 1.5 4.0 4.5;
%! 0.0 0.0 0.0 0.0 0.0 0.0 0.0];
%! crv1 = nrbmak (pnts,[0 0 0 1/4 1/2 3/4 3/4 1 1 1]);
%! crv2 = nrbtform (nrbcirc (4,[4.5;0],pi,0.0),vectrans([0.0 4.0 -4.0]));
%! srf = nrbruled (crv1,crv2);
%! nrbplot (srf,[40 20]);
%! title ('Ruled surface construction from two NURBS curves.');
%! hold off nurbs-1.3.13/inst/PaxHeaders.26136/nrbdegelev.m 0000644 0000000 0000000 00000000132 13070134113 015727 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbdegelev.m 0000644 0001750 0001750 00000011463 13070134113 016112 0 ustar 00bect bect 0000000 0000000 function inurbs = nrbdegelev(nurbs, ntimes)
%
% NRBDEGELEV: Elevate the degree of the NURBS curve, surface or volume.
%
% Calling Sequence:
%
% ecrv = nrbdegelev(crv,utimes);
% esrf = nrbdegelev(srf,[utimes,vtimes]);
% evol = nrbdegelev(vol,[utimes,vtimes,wtimes]);
%
% INPUT:
%
% crv : NURBS curve, see nrbmak.
%
% srf : NURBS surface, see nrbmak.
%
% vol : NURBS volume, see nrbmak.
%
% utimes : Increase the degree along U direction utimes.
%
% vtimes : Increase the degree along V direction vtimes.
%
% wtimes : Increase the degree along W direction vtimes.
%
% OUTPUT:
%
% ecrv : new NURBS structure for a curve with degree elevated.
%
% esrf : new NURBS structure for a surface with degree elevated.
%
% evol : new NURBS structure for a volume with degree elevated.
%
%
% Description:
%
% Degree elevates the NURBS curve or surface. This function uses the
% B-Spline function bspdegelev, which interface to an internal 'C'
% routine.
%
% Examples:
%
% Increase the NURBS surface twice along the V direction.
% esrf = nrbdegelev(srf, [0, 2]);
%
% See also:
%
% bspdegelev
%
% Copyright (C) 2000 Mark Spink, 2010 Rafel Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 2
error('Input argument must include the NURBS and degree increment.');
end
if ~isstruct(nurbs)
error('NURBS representation is not structure!');
end
if ~strcmp(nurbs.form,'B-NURBS')
error('Not a recognised NURBS representation');
end
degree = nurbs.order-1;
if iscell(nurbs.knots)
if size(nurbs.knots,2) == 3
% NURBS represents a volume
[dim,num1,num2,num3] = size(nurbs.coefs);
% Degree elevate along the w direction
if ntimes(3) == 0
coefs = nurbs.coefs;
knots{3} = nurbs.knots{3};
else
coefs = reshape(nurbs.coefs,4*num1*num2,num3);
[coefs,knots{3}] = bspdegelev(degree(3),coefs,nurbs.knots{3},ntimes(3));
num3 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num2 num3]);
end
% Degree elevate along the v direction
if ntimes(2) == 0
knots{2} = nurbs.knots{2};
else
coefs = permute(coefs,[1 2 4 3]);
coefs = reshape(coefs,4*num1*num3,num2);
[coefs,knots{2}] = bspdegelev(degree(2),coefs,nurbs.knots{2},ntimes(2));
num2 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num3 num2]);
coefs = permute(coefs,[1 2 4 3]);
end
% Degree elevate along the u direction
if ntimes(1) == 0
knots{1} = nurbs.knots{1};
else
coefs = permute(coefs,[1 3 4 2]);
coefs = reshape(coefs,4*num2*num3,num1);
[coefs,knots{1}] = bspdegelev(degree(1),coefs,nurbs.knots{1},ntimes(1));
coefs = reshape(coefs,[4 num2 num3 size(coefs,2)]);
coefs = permute(coefs,[1 4 2 3]);
end
elseif size(nurbs.knots,2) == 2
% NURBS represents a surface
[dim,num1,num2] = size(nurbs.coefs);
% Degree elevate along the v direction
if ntimes(2) == 0
coefs = nurbs.coefs;
knots{2} = nurbs.knots{2};
else
coefs = reshape(nurbs.coefs,4*num1,num2);
[coefs,knots{2}] = bspdegelev(degree(2),coefs,nurbs.knots{2},ntimes(2));
num2 = size(coefs,2);
coefs = reshape(coefs,[4 num1 num2]);
end
% Degree elevate along the u direction
if ntimes(1) == 0
knots{1} = nurbs.knots{1};
else
coefs = permute(coefs,[1 3 2]);
coefs = reshape(coefs,4*num2,num1);
[coefs,knots{1}] = bspdegelev(degree(1),coefs,nurbs.knots{1},ntimes(1));
coefs = reshape(coefs,[4 num2 size(coefs,2)]);
coefs = permute(coefs,[1 3 2]);
end
end
else
% NURBS represents a curve
if isempty(ntimes)
coefs = nurbs.coefs;
knots = nurbs.knots;
else
[coefs,knots] = bspdegelev(degree,nurbs.coefs,nurbs.knots,ntimes);
end
end
% construct new NURBS
inurbs = nrbmak(coefs,knots);
end
%!demo
%! crv = nrbtestcrv;
%! plot(crv.coefs(1,:),crv.coefs(2,:),'bo')
%! title('Degree elevation along test curve: curve and control polygons.');
%! hold on;
%! plot(crv.coefs(1,:),crv.coefs(2,:),'b--');
%! nrbplot(crv,48);
%!
%! icrv = nrbdegelev(crv, 1);
%!
%! plot(icrv.coefs(1,:),icrv.coefs(2,:),'ro')
%! plot(icrv.coefs(1,:),icrv.coefs(2,:),'r--');
%!
%! hold off;
nurbs-1.3.13/inst/PaxHeaders.26136/bspinterpcrv.m 0000644 0000000 0000000 00000000126 13070134113 016336 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspinterpcrv.m 0000644 0001750 0001750 00000005717 13070134113 016523 0 ustar 00bect bect 0000000 0000000 function [crv, u] = bspinterpcrv (Q, p, method)
%
% BSPINTERPCRV: B-Spline interpolation of a 3d curve.
%
% Calling Sequence:
%
% crv = bspinterpcrv (Q, p);
% crv = bspinterpcrv (Q, p, method);
% [crv, u] = bspinterpcrv (Q, p);
% [crv, u] = bspinterpcrv (Q, p, method);
%
% INPUT:
%
% Q - points to be interpolated in the form [x_coord; y_coord; z_coord].
% p - degree of the interpolating curve.
% method - parametrization method. The available choices are:
% 'equally_spaced'
% 'chord_length'
% 'centripetal' (Default)
%
% OUTPUT:
%
% crv - the B-Spline curve.
% u - the parametric points corresponding to the interpolation ones.
%
% See The NURBS book pag. 364 for more information.
%
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
if (nargin < 3 || isempty (method))
method = 'centripetal';
end
n = size (Q, 2);
if (strcmpi (method, 'equally_spaced'))
u = linspace (0, 1, n);
elseif (strcmpi (method, 'chord_length'))
d = sum (sqrt (sum (diff (Q')'.^2,1)));
u = zeros (1, n);
u(2:n) = cumsum (sqrt (sum (diff(Q, [], 2).^2, 1)))/d;
% for ii = 2:n-1
% u(ii) = u(ii-1) + norm (Q(:,ii) - Q(:,ii-1)) / d;
% end
u(end) = 1;
elseif (strcmpi (method, 'centripetal'))
d = sum (sqrt (sqrt (sum (diff (Q')'.^2,1))));
u = zeros (1, n);
u(2:n) = cumsum (sqrt (sqrt (sum (diff(Q, [], 2).^2, 1))))/d;
% for ii = 2:n-1
% u(ii) = u(ii-1) + sqrt (norm (Q(:,ii) - Q(:,ii-1))) / d;
% end
u(end) = 1;
else
error ('BSPINTERPCRV: unrecognized parametrization method.')
end
knts = zeros (1, n+p+1);
for jj = 2:n-p
knts(jj+p) = 1/p * sum (u(jj:jj+p-1));
end
knts(end-p:end) = ones(1,p+1);
A = zeros (n, n);
A(1,1) = 1;
A(n,n) = 1;
for ii=2:n-1
span = findspan (n, p, u(ii), knts);
A(ii,span-p+1:span+1) = basisfun (span, u(ii), p, knts);
end
x = A \ Q(1,:)';
y = A \ Q(2,:)';
z = A \ Q(3,:)';
pnts = [x'; y'; z'; ones(size(x'))];
crv = nrbmak (pnts, knts);
end
%!demo
%! Q = [1 0 -1 -1 -2 -3;
%! 0 1 0 -1 -1 0;
%! 0 0 0 0 0 0];
%! p = 2;
%! crv = bspinterpcrv (Q, p);
%!
%! plot (Q(1,:), Q(2,:), 'xk');
%! hold on; grid on;
%! nrbkntplot (crv);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbbasisfunder.m 0000644 0000000 0000000 00000000132 13070134113 016621 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbbasisfunder.m 0000644 0001750 0001750 00000015237 13070134113 017007 0 ustar 00bect bect 0000000 0000000 function varargout = nrbbasisfunder (points, nrb)
% NRBBASISFUNDER: NURBS basis functions derivatives
%
% Calling Sequence:
%
% Bu = nrbbasisfunder (u, crv)
% [Bu, N] = nrbbasisfunder (u, crv)
% [Bu, Bv] = nrbbasisfunder ({u, v}, srf)
% [Bu, Bv, N] = nrbbasisfunder ({u, v}, srf)
% [Bu, Bv, N] = nrbbasisfunder (pts, srf)
% [Bu, Bv, Bw, N] = nrbbasisfunder ({u, v, w}, vol)
% [Bu, Bv, Bw, N] = nrbbasisfunder (pts, vol)
%
% INPUT:
%
% u - parametric coordinates along u direction
% v - parametric coordinates along v direction
% w - parametric coordinates along w direction
% pts - array of scattered points in parametric domain, array size: (ndim,num_points)
% crv - NURBS curve
% srf - NURBS surface
% vol - NURBS volume
%
% If the parametric coordinates are given in a cell-array, the values
% are computed in a tensor product set of points
%
% OUTPUT:
%
% Bu - Basis functions derivatives WRT direction u
% size(Bu)=[npts, prod(nrb.order)]
%
% Bv - Basis functions derivatives WRT direction v
% size(Bv) == size(Bu)
%
% Bw - Basis functions derivatives WRT direction w
% size(Bw) == size(Bu)
%
% N - Indices of the basis functions that are nonvanishing at each
% point. size(N) == size(Bu)
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if ( (nargin<2) ...
|| (nargout>3) ...
|| (~isstruct(nrb)) ...
|| (iscell(points) && ~iscell(nrb.knots)) ...
|| (~iscell(points) && iscell(nrb.knots) && (size(points,1)~=numel(nrb.number))) ...
|| (~iscell(nrb.knots) && (nargout>2)) ...
)
error('Incorrect input arguments in nrbbasisfunder');
end
if (~iscell (nrb.knots)) %% NURBS curve
knt = {nrb.knots};
else %% NURBS surface or volume
knt = nrb.knots;
end
ndim = numel (nrb.number);
w = reshape (nrb.coefs(4,:), [nrb.number 1]);
for idim = 1:ndim
if (iscell (points))
pts_dim = points{idim};
else
pts_dim = points(idim,:);
end
sp{idim} = findspan (nrb.number(idim)-1, nrb.order(idim)-1, pts_dim, knt{idim});
Nprime = basisfunder (sp{idim}, nrb.order(idim)-1, pts_dim, knt{idim}, 1);
N{idim} = reshape (Nprime(:,1,:), numel(pts_dim), nrb.order(idim));
Nder{idim} = reshape (Nprime(:,2,:), numel(pts_dim), nrb.order(idim));
num{idim} = numbasisfun (sp{idim}, pts_dim, nrb.order(idim)-1, knt{idim}) + 1;
end
if (ndim == 1)
B1 = reshape (w(num{1}), size(N{1})) .* N{1};
W = sum (B1, 2);
B2 = reshape (w(num{1}), size(N{1})) .* Nder{1};
Wder = sum (B2, 2);
B2 = bsxfun (@(x,y) x./y, B2, W);
B1 = bsxfun (@(x,y) x.*y, B1, Wder./W.^2);
B = B2 - B1;
varargout{1} = B;
varargout{2} = num{1};
else
id = nrbnumbasisfun (points, nrb);
if (iscell (points))
npts_dim = cellfun (@numel, points);
npts = prod (npts_dim);
val_aux = 1;
val_ders = repmat ({1}, ndim, 1);
for idim = 1:ndim
val_aux = kron (N{idim}, val_aux);
for jdim = 1:ndim
if (idim == jdim)
val_ders{idim} = kron(Nder{jdim}, val_ders{idim});
else
val_ders{idim} = kron(N{jdim}, val_ders{idim});
end
end
end
B1 = w(id) .* reshape (val_aux, npts, prod(nrb.order));
W = sum (B1, 2);
for idim = 1:ndim
B2 = w(id) .* reshape (val_ders{idim}, npts, prod(nrb.order));
Wder = sum (B2, 2);
varargout{idim} = bsxfun (@(x,y) x./y, B2, W) - bsxfun (@(x,y) x.*y, B1, Wder ./ W.^2);
end
else
npts = numel (points(1,:));
B = zeros (npts, prod(nrb.order));
Bder = repmat ({B}, ndim, 1);
for ipt = 1:npts
val_aux = 1;
val_ders = repmat ({1}, ndim, 1);
for idim = 1:ndim
val_aux = reshape (val_aux.' * N{idim}(ipt,:), 1, []);
% val_aux = kron (N{idim}(ipt,:), val_aux);
for jdim = 1:ndim
if (idim == jdim)
val_ders{idim} = reshape (val_ders{idim}.' * Nder{jdim}(ipt,:), 1, []);
else
val_ders{idim} = reshape (val_ders{idim}.' * N{jdim}(ipt,:), 1, []);
end
end
end
wval = reshape (w(id(ipt,:)), size(val_aux));
val_aux = val_aux .* wval;
W = sum (val_aux);
for idim = 1:ndim
val_ders{idim} = val_ders{idim} .* wval;
Wder = sum (val_ders{idim});
Bder{idim}(ipt,:) = bsxfun (@(x,y) x./y, val_ders{idim}, W) - bsxfun (@(x,y) x.*y, val_aux, Wder ./ W.^2);
end
end
varargout(1:ndim) = Bder(1:ndim);
end
if (nargout > ndim)
varargout{ndim+1} = id;
end
end
end
%!demo
%! U = [0 0 0 0 1 1 1 1];
%! x = [0 1/3 2/3 1] ;
%! y = [0 0 0 0];
%! w = [1 1 1 1];
%! nrb = nrbmak ([x;y;y;w], U);
%! u = linspace(0, 1, 30);
%! [Bu, id] = nrbbasisfunder (u, nrb);
%! plot(u, Bu)
%! title('Derivatives of the cubic Bernstein polynomials')
%! hold off
%!test
%! U = [0 0 0 0 1 1 1 1];
%! x = [0 1/3 2/3 1] ;
%! y = [0 0 0 0];
%! w = rand(1,4);
%! nrb = nrbmak ([x;y;y;w], U);
%! u = linspace(0, 1, 30);
%! [Bu, id] = nrbbasisfunder (u, nrb);
%! #plot(u, Bu)
%! assert (sum(Bu, 2), zeros(numel(u), 1), 1e-10),
%!test
%! U = [0 0 0 0 1/2 1 1 1 1];
%! x = [0 1/4 1/2 3/4 1] ;
%! y = [0 0 0 0 0];
%! w = rand(1,5);
%! nrb = nrbmak ([x;y;y;w], U);
%! u = linspace(0, 1, 300);
%! [Bu, id] = nrbbasisfunder (u, nrb);
%! assert (sum(Bu, 2), zeros(numel(u), 1), 1e-10)
%!test
%! p = 2; q = 3; m = 4; n = 5;
%! Lx = 1; Ly = 1;
%! nrb = nrb4surf ([0 0], [1 0], [0 1], [1 1]);
%! nrb = nrbdegelev (nrb, [p-1, q-1]);
%! aux1 = linspace(0,1,m); aux2 = linspace(0,1,n);
%! nrb = nrbkntins (nrb, {aux1(2:end-1), aux2(2:end-1)});
%! nrb.coefs (4,:,:) = nrb.coefs(4,:,:) + rand (size (nrb.coefs (4,:,:)));
%! [Bu, Bv, N] = nrbbasisfunder ({rand(1, 20), rand(1, 20)}, nrb);
%! #plot3(squeeze(u(1,:,:)), squeeze(u(2,:,:)), reshape(Bu(:,10), 20, 20),'o')
%! assert (sum (Bu, 2), zeros(20^2, 1), 1e-10)
nurbs-1.3.13/inst/PaxHeaders.26136/nrbcrvderiveval.m 0000644 0000000 0000000 00000000132 13070134113 017010 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbcrvderiveval.m 0000644 0001750 0001750 00000005721 13070134113 017173 0 ustar 00bect bect 0000000 0000000 % NRBCRVDERIVEVAL: Evaluate n-th order derivatives of a NURBS curve.
%
% usage: skl = nrbcrvderiveval (crv, u, d)
%
% INPUT:
%
% crv : NURBS curve structure, see nrbmak
%
% u : parametric coordinate of the points where we compute the derivatives
%
% d : number of partial derivatives to compute
%
%
% OUTPUT:
%
% ck (i, j, l) = i-th component derived j-1 times at the l-th point.
%
% Adaptation of algorithm A4.2 from the NURBS book, pg127
%
% Copyright (C) 2010 Carlo de Falco, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
function ck = nrbcrvderiveval (crv, u, d)
ck = arrayfun (@(x) nrbcrvderiveval__ (crv, x, d), u, 'UniformOutput', false);
ck = cat (3, ck{:});
end
function ck = nrbcrvderiveval__ (crv, u, d)
persistent nc;
if isempty (nc)
nc = [0 0 0 0 0;
1 0 0 0 0;
2 1 0 0 0;
3 3 1 0 0;
4 6 4 1 0];
end
ck = zeros (3, d+1);
wders = curvederiveval (crv.number-1, crv.order-1, crv.knots, squeeze (crv.coefs(4, :)), u, d);
for idim = 1:3
Aders = curvederiveval (crv.number-1, crv.order-1, crv.knots, squeeze (crv.coefs(idim, :)), u, d);
ck(idim, 1) = Aders(1) / wders(1);
for k = 1:d
ck(idim, k+1) = (Aders(k+1) - sum (nc(k+1, 1:k) .* wders(2:k+1).' .* squeeze (ck(idim, k:-1:1)))) / wders(1);
end
end
end
%!test
%! knots = [0 0 0 1 1 1];
%! coefs(:,1) = [0; 0; 0; 1];
%! coefs(:,2) = [1; 0; 1; 1];
%! coefs(:,3) = [1; 1; 1; 2];
%! crv = nrbmak (coefs, knots);
%! u = linspace (0, 1, 100);
%! ck = nrbcrvderiveval (crv, u, 2);
%! w = @(x) 1 + x.^2;
%! dw = @(x) 2*x;
%! F1 = @(x) (2*x - x.^2)./w(x);
%! F2 = @(x) x.^2./w(x);
%! F3 = @(x) (2*x - x.^2)./w(x);
%! dF1 = @(x) (2 - 2*x)./w(x) - 2*(2*x - x.^2).*x./w(x).^2;
%! dF2 = @(x) 2*x./w(x) - 2*x.^3./w(x).^2;
%! dF3 = @(x) (2 - 2*x)./w(x) - 2*(2*x - x.^2).*x./w(x).^2;
%! d2F1 = @(x) -2./w(x) - 2*x.*(2-2*x)./w(x).^2 - (8*x-6*x.^2)./w(x).^2 + 8*x.^2.*(2*x-x.^2)./w(x).^3;
%! d2F2 = @(x) 2./w(x) - 4*x.^2./w(x).^2 - 6*x.^2./w(x).^2 + 8*x.^4./w(x).^3;
%! d2F3 = @(x) -2./w(x) - 2*x.*(2-2*x)./w(x).^2 - (8*x-6*x.^2)./w(x).^2 + 8*x.^2.*(2*x-x.^2)./w(x).^3;
%! assert ([F1(u); F2(u); F3(u)], squeeze(ck(:, 1, :)), 1e2*eps);
%! assert ([dF1(u); dF2(u); dF3(u)], squeeze(ck(:, 2, :)), 1e2*eps);
%! assert ([d2F1(u); d2F2(u); d2F3(u)], squeeze(ck(:, 3, :)), 1e2*eps);
nurbs-1.3.13/inst/PaxHeaders.26136/basisfunder.m 0000644 0000000 0000000 00000000132 13070134113 016117 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/basisfunder.m 0000644 0001750 0001750 00000007701 13070134113 016302 0 ustar 00bect bect 0000000 0000000 function dersv = basisfunder (ii, pl, uu, u_knotl, nders)
% BASISFUNDER: B-Spline Basis function derivatives.
%
% Calling Sequence:
%
% ders = basisfunder (ii, pl, uu, k, nd)
%
% INPUT:
%
% ii - knot span index (see findspan)
% pl - degree of curve
% uu - parametric points
% k - knot vector
% nd - number of derivatives to compute
%
% OUTPUT:
%
% ders - ders(n, i, :) (i-1)-th derivative at n-th point
%
% Adapted from Algorithm A2.3 from 'The NURBS BOOK' pg72.
%
% See also:
%
% numbasisfun, basisfun, findspan
%
% Copyright (C) 2009,2011 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
dersv = zeros(numel(uu), nders+1, pl+1);
for jj = 1:numel(uu)
i = ii(jj)+1; %% convert to base-1 numbering of knot spans
u = uu(jj);
ders = zeros(nders+1,pl+1);
ndu = zeros(pl+1,pl+1);
left = zeros(pl+1);
right = zeros(pl+1);
a = zeros(2,pl+1);
ndu(1,1) = 1;
for j = 1:pl
left(j+1) = u - u_knotl(i+1-j);
right(j+1) = u_knotl(i+j) - u;
saved = 0;
for r = 0:j-1
ndu(j+1,r+1) = right(r+2) + left(j-r+1);
temp = ndu(r+1,j)/ndu(j+1,r+1);
ndu(r+1,j+1) = saved + right(r+2)*temp;
saved = left(j-r+1)*temp;
end
ndu(j+1,j+1) = saved;
end
for j = 0:pl
ders(1,j+1) = ndu(j+1,pl+1);
end
for r = 0:pl
s1 = 0;
s2 = 1;
a(1,1) = 1;
for k = 1:nders %compute kth derivative
d = 0;
rk = r-k;
pk = pl-k;
if (r >= k)
a(s2+1,1) = a(s1+1,1)/ndu(pk+2,rk+1);
d = a(s2+1,1)*ndu(rk+1,pk+1);
end
if (rk >= -1)
j1 = 1;
else
j1 = -rk;
end
if ((r-1) <= pk)
j2 = k-1;
else
j2 = pl-r;
end
for j = j1:j2
a(s2+1,j+1) = (a(s1+1,j+1) - a(s1+1,j))/ndu(pk+2,rk+j+1);
d = d + a(s2+1,j+1)*ndu(rk+j+1,pk+1);
end
if (r <= pk)
a(s2+1,k+1) = -a(s1+1,k)/ndu(pk+2,r+1);
d = d + a(s2+1,k+1)*ndu(r+1,pk+1);
end
ders(k+1,r+1) = d;
j = s1;
s1 = s2;
s2 = j;
end
end
r = pl;
for k = 1:nders
for j = 0:pl
ders(k+1,j+1) = ders(k+1,j+1)*r;
end
r = r*(pl-k);
end
dersv(jj, :, :) = ders;
end
end
%!test
%! k = [0 0 0 0 1 1 1 1];
%! p = 3;
%! u = rand (1);
%! i = findspan (numel(k)-p-2, p, u, k);
%! ders = basisfunder (i, p, u, k, 1);
%! sumders = sum (squeeze(ders), 2);
%! assert (sumders(1), 1, 1e-15);
%! assert (sumders(2:end), 0, 1e-15);
%!test
%! k = [0 0 0 0 1/3 2/3 1 1 1 1];
%! p = 3;
%! u = rand (1);
%! i = findspan (numel(k)-p-2, p, u, k);
%! ders = basisfunder (i, p, u, k, 7);
%! sumders = sum (squeeze(ders), 2);
%! assert (sumders(1), 1, 1e-15);
%! assert (sumders(2:end), zeros(rows(squeeze(ders))-1, 1), 1e-13);
%!test
%! k = [0 0 0 0 1/3 2/3 1 1 1 1];
%! p = 3;
%! u = rand (100, 1);
%! i = findspan (numel(k)-p-2, p, u, k);
%! ders = basisfunder (i, p, u, k, 7);
%! for ii=1:10
%! sumders = sum (squeeze(ders(ii,:,:)), 2);
%! assert (sumders(1), 1, 1e-15);
%! assert (sumders(2:end), zeros(rows(squeeze(ders(ii,:,:)))-1, 1), 1e-13);
%! end
%! assert (ders(:, (p+2):end, :), zeros(numel(u), 8-p-1, p+1), 1e-13)
%! assert (all(all(ders(:, 1, :) <= 1)), true)
nurbs-1.3.13/inst/PaxHeaders.26136/nrbtestcrv.m 0000644 0000000 0000000 00000000132 13070134113 016006 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbtestcrv.m 0000644 0001750 0001750 00000002004 13070134113 016160 0 ustar 00bect bect 0000000 0000000 function crv = nrbtestcrv
% NRBTESTCRV: Constructs a simple test curve.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
pnts = [0.5 1.5 4.5 3.0 7.5 6.0 8.5;
3.0 5.5 5.5 1.5 1.5 4.0 4.5;
0.0 0.0 0.0 0.0 0.0 0.0 0.0];
crv = nrbmak(pnts,[0 0 0 1/4 1/2 3/4 3/4 1 1 1]);
end
%!demo
%! crv = nrbtestcrv;
%! nrbplot(crv,100)
%! title('Test curve')
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/nrbinverse.m 0000644 0000000 0000000 00000000132 13070134113 015767 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbinverse.m 0000644 0001750 0001750 00000011145 13070134113 016147 0 ustar 00bect bect 0000000 0000000 function u = nrbinverse (nrb, x, varargin)
%
% NRBINVERSE: compute parametric point starting from physical point by
% inverting the NURBS map with a Newton scheme
%
% Calling Sequence:
%
% u = nrbinverse (nrb, x)
% u = nrbinverse (nrb, x, options)
%
% INPUT:
%
% nrb - NURBS object
% x - physical point
% options - options in the FIELD/VALUE format. Possible choices:
% 'u0' : starting point in the parametric domain for Newton
% (Default = .5 * ones (ndim, 1))
% 'MaxIter' : maximum number of Newton iterations (Default = 10)
% 'Display' : if true the some info are shown (Default = true)
% 'TolX' : tolerance for the step size in Newton iterations
% (Default = 1e-8)
% 'TolFun' : tolerance for the residual in Newton iterations
% (Default = 1e-8)
%
% OUTPUT:
%
% u - the parametric points corresponding to x
%
% Copyright (C) 2016 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
ndim = numel (nrb.number);
% % Default options
% persistent p;
% p = inputParser ();
% p.addParameter ('u0', .5*ones(ndim, 1), @(x) validateattributes (x, {'numeric'}, {'numel', ndim, '>=', 0, '<=', 1}));
% p.addParameter ('MaxIter', 10, @(x) validateattributes (x, {'numeric'}, {'scalar'}));
% p.addParameter ('Display', true, @(x) validateattributes (x, {'logical'}, {}));
% p.addParameter ('TolX', 1e-8, @(x) validateattributes (x, {'numeric'}, {'scalar'}));
% p.addParameter ('TolFun', 1e-8, @(x) validateattributes (x, {'numeric'}, {'scalar'}));
% p.parse (varargin{:});
% options = p.Results;
% Default options
options = struct ('u0' , .5*ones (ndim, 1), ...
'MaxIter' , 10, ...
'Display' , true, ...
'TolX', 1e-8, ...
'TolFun', 1e-8);
% Read the acceptable names
optionNames = fieldnames (options);
% Count arguments
nargin = length (varargin);
if (round (nargin/2) ~= nargin/2)
error ('NRBINVERSE needs propertyName/propertyValue pairs');
end
% Check options passed
for pair = reshape (varargin, 2, [])
if any (strcmp (pair{1}, optionNames))
options.(pair{1}) = pair{2};
else
error('%s is not a recognized parameter name', pair{1});
end
end
% x as column vector
x = x(:);
% Define functions for Newton iteration
f = @(U) nrbeval (nrb, num2cell (U)) - x;
jac = @(U) nrbjacobian (nrb, num2cell (U));
% Newton cycle
u_old = options.u0(:);
if (iscell (nrb.knots))
first_knot = reshape (cellfun (@(x) x(1),nrb.knots), size(u_old));
last_knot = reshape (cellfun (@(x) x(end),nrb.knots), size(u_old));
else
first_knot = nrb.knots(1);
last_knot = nrb.knots(end);
end
convergence = false;
for iter = 1:options.MaxIter
u_new = u_old - jac (u_old) \ f (u_old);
% Check if the point is outside the parametric domain
u_new = max (u_new, first_knot);
u_new = min (u_new, last_knot);
% Error control
if (norm (u_new - u_old) < options.TolX && norm (f (u_new)) < options.TolFun)
if (options.Display)
fprintf ('Newton scheme converged in %i iteration.\n', iter);
end
convergence = true;
break;
end
u_old = u_new;
end
if (~convergence)
fprintf ('Newton scheme reached the maximum number of iterations (%i) without converging.\n', options.MaxIter);
end
u = u_new;
end
function jac = nrbjacobian (nrb, u)
ders = nrbderiv (nrb);
[~, jac] = nrbdeval (nrb, ders, u);
jac = [jac{:}];
end
%!test
%! nrb = nrb4surf ([0 0], [1 0], [2 3], [5 4]);
%! p = nrbeval (nrb, {.25 .75});
%! u = nrbinverse (nrb, p, 'Display', false);
%! assert (norm (u - [.25; .75]) < 1e-8);
%!
%!test
%! nrb = nrb4surf ([0 0], [1 0], [2 3], [5 4]);
%! nrb = nrbdegelev (nrbextrude (nrb, [0 2 1]), [3 3 3]);
%! p = nrbeval (nrb, {.25 .75 .05});
%! u = nrbinverse (nrb, p, 'Display', false, 'TolX', 1e-12, 'TolFun', 1e-10);
%! assert (norm (u - [.25; .75; .05]) < 1e-8);
%!
nurbs-1.3.13/inst/PaxHeaders.26136/kntuniform.m 0000644 0000000 0000000 00000000126 13070134113 016011 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/kntuniform.m 0000644 0001750 0001750 00000003420 13070134113 016163 0 ustar 00bect bect 0000000 0000000 % KNTUNIFORM: generate uniform open knot vectors in the reference domain.
%
% [csi, zeta] = kntuniform (num, degree, regularity)
%
% INPUT:
%
% num: number of breaks (in each direction)
% degree: polynomial degree (in each direction)
% regularity: global regularity (in each direction)
%
% OUTPUT:
%
% csi: knots
% zeta: breaks = knots without repetitions
%
% Copyright (C) 2009, 2010 Carlo de Falco
% Copyright (C) 2011 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
function [csi, zeta] = kntuniform (num, degree, regularity)
if (numel(num)~=numel(degree) || numel(num)~=numel(regularity))
error('kntuniform: num, degree and regularity must have the same length')
else
for idim=1:numel(num)
zeta{idim} = linspace (0, 1, num(idim));
rep = degree(idim) - regularity(idim);
if (rep > 0)
csi{idim} = [zeros(1, degree(idim)+1-rep)...
reshape(repmat(zeta{idim}, rep, 1), 1, []) ones(1, degree(idim)+1-rep)];
else
error ('kntuniform: regularity requested is too high')
end
end
if (numel(num) == 1)
csi = csi{1};
zeta = zeta{1};
end
end
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbclamp.m 0000644 0000000 0000000 00000000132 13070134113 015410 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbclamp.m 0000644 0001750 0001750 00000007500 13070134113 015570 0 ustar 00bect bect 0000000 0000000 function ccrv = nrbclamp (crv, k, xdim)
% NRBCLAMP: Compute the knot vector and control points of the clamped curve/surface.
%
% Calling Sequence:
%
% ccrv = nrbrclamp (crv)
% ccrv = nrbrclamp (crv, k)
% ccrv = nrbrclamp (crv, k, dim)
%
% INPUT:
%
% crv : unclamped NURBS curve or surface, see nrbmak.
% k : continuity desired afterclamping (from -1 up to p-1, -1 by default)
% dim : dimension in which to clamp (all by default).
%
% OUTPUT:
%
% ccrv: NURBS curve with clamped knot vector, see nrbmak
%
% Description:
%
% Clamps a curve or surface, using an open knot vector. Computes the new
% knot vector and control points by knot insertion.
%
% Copyright (C) 2016 Monica Montardini, Filippo Remonato, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (iscell (crv.knots))
knt = crv.knots;
curve = false;
else
knt = {crv.knots};
curve = true;
end
ndim = numel (knt);
if (nargin < 2 || isempty(k))
k = (-1) * ones (1, ndim);
end
if (nargin < 3)
xdim = 1:ndim;
end
%if (iscell (crv.knots))
if (numel(k) ~= ndim)
k = k * ones(1, ndim);
end
new_knots = cell (1, ndim);
for idim = xdim
p = crv.order(idim) - 1;
U = knt{idim};
kk = k(idim);
if (kk >= p)
warning ('Taking the maximum k allowed, degree - 1')
kk = p - 1;
end
n_ins_start(idim) = max (0, p - sum(U==U(p+1)) - kk);
n_ins_end(idim) = max (0, p - sum(U==U(end-p)) - kk);
new_knots{idim} = [U(p+1)*ones(1,n_ins_start(idim)), U(end-p)*ones(1,n_ins_end(idim))];
end
% Clamp, and remove unused coefficients and knots
if (curve)
ccrv = nrbkntins (crv, new_knots{1});
ccrv.coefs = ccrv.coefs(:, n_ins_start+1 : end - n_ins_end);
ccrv.knots = ccrv.knots(n_ins_start+1 : end - n_ins_end);
else
ccrv = nrbkntins (crv, new_knots);
for idim = 1:ndim
ccrv.knots{idim} = ccrv.knots{idim}(n_ins_start(idim)+1 : end - n_ins_end(idim));
indices{idim} = n_ins_start(idim)+1 : ccrv.number(idim)-n_ins_end(idim);
end
ccrv.coefs = ccrv.coefs(1:4,indices{:});
end
ccrv.number = ccrv.number - n_ins_start - n_ins_end;
end
%!test
%! crv = nrbdegelev (nrbcirc (1, [], 0, pi/2), 2);
%! crv = nrbunclamp (crv, 3);
%! xx = linspace (0, 1, 20);
%! crv1 = nrbclamp (crv);
%! assert (crv1.knots, [0 0 0 0 0 1 1 1 1 1])
%! assert (nrbeval(crv, xx), nrbeval(crv1, xx), 1e-14)
%! crv1 = nrbclamp (crv, 2);
%! assert (crv1.knots, [-3 -2 -1 0 0 1 1 2 3 4])
%! assert (nrbeval(crv, xx), nrbeval(crv1, xx), 1e-14)
%!test
%! crv1 = nrbcirc(1,[],0,pi/4);
%! crv2 = nrbcirc(2,[],0,pi/4);
%! srf = nrbkntins (nrbdegelev (nrbruled(crv1, crv2), [3 2]), {0.25 []});
%! srf = nrbunclamp (srf, [4 2]);
%! srf1 = nrbclamp (srf);
%! xx = linspace(0,1,20);
%! assert(srf1.knots, {[0 0 0 0 0 0 0.2500 1 1 1 1 1 1] [0 0 0 0 1 1 1 1]})
%! assert (nrbeval(srf, {xx xx}), nrbeval(srf1, {xx xx}), 1e-14);
%! srf1 = nrbclamp (srf, [3 1]);
%! assert (srf1.knots, {[-2 -1.75 -1 -0.75 0 0 0.25 1 1 1.25 2 2.25 3], [-2 -1 0 0 1 1 2 3]})
%! assert (nrbeval(srf, {xx xx}), nrbeval(srf1, {xx xx}), 1e-14);
%! srf1 = nrbclamp (srf, [], 2);
%! assert(srf1.knots, {[-2.75 -2 -1.75 -1 -0.75 0 0.25 1 1.25 2 2.25 3 3.25] [0 0 0 0 1 1 1 1]})
%! assert (nrbeval(srf, {xx xx}), nrbeval(srf1, {xx xx}), 1e-14);
nurbs-1.3.13/inst/PaxHeaders.26136/nrb4surf.m 0000644 0000000 0000000 00000000126 13070134113 015362 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrb4surf.m 0000644 0001750 0001750 00000004047 13070134113 015542 0 ustar 00bect bect 0000000 0000000 function srf = nrb4surf(p11,p12,p21,p22)
%
% NRB4SURF: Constructs a NURBS bilinear surface.
%
% Calling Sequence:
%
% srf = nrb4surf(p11,p12,p21,p22)
%
% INPUT:
%
% p11 : Cartesian coordinate of the lhs bottom corner point.
%
% p12 : Cartesian coordinate of the rhs bottom corner point.
%
% p21 : Cartesian coordinate of the lhs top corner point.
%
% p22 : Cartesian coordinate of the rhs top corner point.
%
% OUTPUT:
%
% srf : NURBS bilinear surface, see nrbmak.
%
% Description:
%
% Constructs a bilinear surface defined by four coordinates.
%
% The position of the corner points
%
% ^ V direction
% |
% ----------------
% |p21 p22|
% | |
% | SRF |
% | |
% |p11 p12|
% -------------------> U direction
%
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin ~= 4
error('Four corner points must be defined');
end
coefs = cat (1, zeros (3,2,2), ones (1,2,2));
coefs(1:length(p11),1,1) = p11(:);
coefs(1:length(p12),2,1) = p12(:);
coefs(1:length(p21),1,2) = p21(:);
coefs(1:length(p22),2,2) = p22(:);
knots = {[0 0 1 1] [0 0 1 1]};
srf = nrbmak(coefs, knots);
end
%!demo
%! srf = nrb4surf([0.0 0.0 0.5],[1.0 0.0 -0.5],[0.0 1.0 -0.5],[1.0 1.0 0.5]);
%! nrbplot(srf,[10,10]);
%! title('Construction of a bilinear surface.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/nrbeval_der_p.m 0000644 0000000 0000000 00000000132 13070134113 016414 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbeval_der_p.m 0000644 0001750 0001750 00000007514 13070134113 016601 0 ustar 00bect bect 0000000 0000000 function der = nrbeval_der_p (nrb, i, points)
%
% NRBEVAL_DER_P: Compute the derivative of a NURBS object at a given point
% with respect to the coordinates of the i-th control point.
%
% Calling Sequence:
%
% der = nrbeval_der_p (crv, i, u);
% der = nrbeval_der_p (srf, i, p);
% der = nrbeval_der_p (srf, i, {u v});
% der = nrbeval_der_p (vol, i, p);
% der = nrbeval_der_p (vol, i, {u v w});
%
% INPUT:
%
% crv - NURBS curve.
% srf - NURBS surface.
% vol - NURBS volume.
% i - Index of the control point.
% u or p(1,:,:) - parametric points along u direction
% v or p(2,:,:) - parametric points along v direction
% w or p(3,:,:) - parametric points along w direction
%
% OUTPUT:
%
% der - Derivative.
% size(der) = numel(u) for curves
% or numel(u)*numel(v) for surfaces
% or numel(u)*numel(v)*numel(w) for volumes
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
[N, id] = nrbbasisfun (points, nrb);
der = zeros (1, size(N, 1));
for k = 1:numel (der)
[is, loc] = ismember (i, id(k,:)); % id is 1-based
if (is)
der(k) = N(k,loc);
else
der(k) = 0;
end
end
end
%!test %% 1D
%! nrb = nrbkntins (nrbcirc (1, [0 0], 0, pi/2), .5);
%! u = 0:.1:.9;
%! index = 1:nrb.number;
%! e = zeros (numel (u), numel (index), 1);
%! for jj = 1:numel (index)
%! deltap = .1 * rand (3, 1);
%! nrb2 = nrbmodp (nrb, deltap, index(jj));
%! der_ex = nrbeval_der_p (nrb, index(jj), u);
%! p2 = nrbeval (nrb2, u);
%! p1 = nrbeval (nrb, u);
%! der_fd = (p2 - p1) ./ deltap;
%! e(:,jj) = sqrt (sum ((repmat (der_ex, 3, 1) - der_fd).^2, 1));
%! end
%! assert (max(e(:)) < 1.e-8);
%!
%!test %% 2D
%! crv = nrbline([1 0], [2 0]);
%! nrb = nrbtransp (nrbrevolve (crv, [], [0 0 1], pi/2));
%! new_knots = linspace (1/9, 8/9, 8);
%! nrb = nrbkntins (nrb, {new_knots, new_knots});
%! u = 0:.1:.9;
%! v = u;
%! e = zeros (nrb.number(1) * nrb.number(2), numel (u), numel (v));
%! for index = 1:nrb.number(1) * nrb.number(2)
%! deltap = .1 * rand (3, 1);
%! nrb2 = nrbmodp (nrb, deltap, index);
%! der_ex = nrbeval_der_p (nrb, index, {u v});
%! p2 = nrbeval (nrb2, {u v});
%! p1 = nrbeval (nrb, {u v});
%! der_fd = (p2 - p1) ./ deltap;
%! der_ex = reshape (repmat (der_ex, 3, 1), size(der_fd));
%! e(index,:,:) = sqrt (sum ((der_ex - der_fd).^2, 1));
%! end
%! assert (max(e(:)) < 1.e-8)
%!
%!test %% 3D
%! crv = nrbline([1 0], [2 0]);
%! nrb = nrbtransp (nrbrevolve (crv, [], [0 0 1], pi/2));
%! nrb = nrbextrude (nrb, [0 0 1]);
%! u = 0:.1:.9;
%! v = u;
%! w = u;
%! e = zeros (nrb.number(1) * nrb.number(2) * nrb.number(3), numel(u), numel(v), numel(w));
%! for index = 1:nrb.number(1) * nrb.number(2) * nrb.number(3)
%! deltap = .1 * rand (3, 1);
%! nrb2 = nrbmodp (nrb, deltap, index);
%! der_ex = nrbeval_der_p (nrb, index, {u v w});
%! p2 = nrbeval (nrb2, {u v w});
%! p1 = nrbeval (nrb, {u v w});
%! der_fd = (p2 - p1) ./ deltap;
%! der_ex = reshape (repmat (der_ex, 3, 1), size (der_fd));
%! e(index,:,:,:) = sqrt (sum ((der_ex - der_fd).^2, 1));
%! end
%! assert (max (e(:)) < 1.e-8);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbdeval.m 0000644 0000000 0000000 00000000132 13070134113 015407 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbdeval.m 0000644 0001750 0001750 00000021220 13070134113 015562 0 ustar 00bect bect 0000000 0000000 function varargout = nrbdeval (nurbs, dnurbs, varargin)
% NRBDEVAL: Evaluation of the derivative and second derivatives of NURBS curve, surface or volume.
%
% [pnt, jac] = nrbdeval (crv, dcrv, tt)
% [pnt, jac] = nrbdeval (srf, dsrf, {tu tv})
% [pnt, jac] = nrbdeval (vol, dvol, {tu tv tw})
% [pnt, jac, hess] = nrbdeval (crv, dcrv, dcrv2, tt)
% [pnt, jac, hess] = nrbdeval (srf, dsrf, dsrf2, {tu tv})
% [pnt, jac, hess] = nrbdeval (vol, dvol, dvol2, {tu tv tw})
%
% INPUTS:
%
% crv, srf, vol - original NURBS curve, surface or volume.
% dcrv, dsrf, dvol - NURBS derivative representation of crv, srf
% or vol (see nrbderiv2)
% dcrv2, dsrf2, dvol2 - NURBS second derivative representation of crv,
% srf or vol (see nrbderiv2)
% tt - parametric evaluation points
% If the nurbs is a surface or a volume then tt is a cell
% {tu, tv} or {tu, tv, tw} are the parametric coordinates
%
% OUTPUT:
%
% pnt - evaluated points.
% jac - evaluated first derivatives (Jacobian).
% hess - evaluated second derivatives (Hessian).
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Carlo de Falco
% Copyright (C) 2010, 2011 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin == 3)
tt = varargin{1};
elseif (nargin == 4)
dnurbs2 = varargin{1};
tt = varargin{2};
else
error ('nrbrdeval: wrong number of input parameters')
end
if (~isstruct(nurbs))
error('NURBS representation is not structure!');
end
if (~strcmp(nurbs.form,'B-NURBS'))
error('Not a recognised NURBS representation');
end
[cp,cw] = nrbeval(nurbs, tt);
if (iscell(nurbs.knots))
if (size(nurbs.knots,2) == 3)
% NURBS structure represents a volume
temp = cw(ones(3,1),:,:,:);
pnt = cp./temp;
[cup,cuw] = nrbeval (dnurbs{1}, tt);
tempu = cuw(ones(3,1),:,:,:);
jac{1} = (cup-tempu.*pnt)./temp;
[cvp,cvw] = nrbeval (dnurbs{2}, tt);
tempv = cvw(ones(3,1),:,:,:);
jac{2} = (cvp-tempv.*pnt)./temp;
[cwp,cww] = nrbeval (dnurbs{3}, tt);
tempw = cww(ones(3,1),:,:,:);
jac{3} = (cwp-tempw.*pnt)./temp;
% second derivatives
if (nargout == 3)
if (exist ('dnurbs2'))
[cuup, cuuw] = nrbeval (dnurbs2{1,1}, tt);
tempuu = cuuw(ones(3,1),:,:,:);
hess{1,1} = (cuup - (2*cup.*tempu + cp.*tempuu)./temp + 2*cp.*tempu.^2./temp.^2)./temp;
clear cuup cuuw tempuu
[cvvp, cvvw] = nrbeval (dnurbs2{2,2}, tt);
tempvv = cvvw(ones(3,1),:,:,:);
hess{2,2} = (cvvp - (2*cvp.*tempv + cp.*tempvv)./temp + 2*cp.*tempv.^2./temp.^2)./temp;
clear cvvp cvvw tempvv
[cwwp, cwww] = nrbeval (dnurbs2{3,3}, tt);
tempww = cwww(ones(3,1),:,:,:);
hess{3,3} = (cwwp - (2*cwp.*tempw + cp.*tempww)./temp + 2*cp.*tempw.^2./temp.^2)./temp;
clear cwwp cwww tempww
[cuvp, cuvw] = nrbeval (dnurbs2{1,2}, tt);
tempuv = cuvw(ones(3,1),:,:,:);
hess{1,2} = (cuvp - (cup.*tempv + cvp.*tempu + cp.*tempuv)./temp + 2*cp.*tempu.*tempv./temp.^2)./temp;
hess{2,1} = hess{1,2};
clear cuvp cuvw tempuv
[cuwp, cuww] = nrbeval (dnurbs2{1,3}, tt);
tempuw = cuww(ones(3,1),:,:,:);
hess{1,3} = (cuwp - (cup.*tempw + cwp.*tempu + cp.*tempuw)./temp + 2*cp.*tempu.*tempw./temp.^2)./temp;
hess{3,1} = hess{1,3};
clear cuwp cuww tempuw
[cvwp, cvww] = nrbeval (dnurbs2{2,3}, tt);
tempvw = cvww(ones(3,1),:,:,:);
hess{2,3} = (cvwp - (cvp.*tempw + cwp.*tempv + cp.*tempvw)./temp + 2*cp.*tempv.*tempw./temp.^2)./temp;
hess{3,2} = hess{2,3};
clear cvwp cvww tempvw
else
warning ('nrbdeval: dnurbs2 missing. The second derivative is not computed');
hess = [];
end
end
elseif (size(nurbs.knots,2) == 2)
% NURBS structure represents a surface
temp = cw(ones(3,1),:,:);
pnt = cp./temp;
[cup,cuw] = nrbeval (dnurbs{1}, tt);
tempu = cuw(ones(3,1),:,:);
jac{1} = (cup-tempu.*pnt)./temp;
[cvp,cvw] = nrbeval (dnurbs{2}, tt);
tempv = cvw(ones(3,1),:,:);
jac{2} = (cvp-tempv.*pnt)./temp;
% second derivatives
if (nargout == 3)
if (exist ('dnurbs2'))
[cuup, cuuw] = nrbeval (dnurbs2{1,1}, tt);
tempuu = cuuw(ones(3,1),:,:);
hess{1,1} = (cuup - (2*cup.*tempu + cp.*tempuu)./temp + 2*cp.*tempu.^2./temp.^2)./temp;
[cvvp, cvvw] = nrbeval (dnurbs2{2,2}, tt);
tempvv = cvvw(ones(3,1),:,:);
hess{2,2} = (cvvp - (2*cvp.*tempv + cp.*tempvv)./temp + 2*cp.*tempv.^2./temp.^2)./temp;
[cuvp, cuvw] = nrbeval (dnurbs2{1,2}, tt);
tempuv = cuvw(ones(3,1),:,:);
hess{1,2} = (cuvp - (cup.*tempv + cvp.*tempu + cp.*tempuv)./temp + 2*cp.*tempu.*tempv./temp.^2)./temp;
hess{2,1} = hess{1,2};
else
warning ('nrbdeval: dnurbs2 missing. The second derivative is not computed');
hess = [];
end
end
end
else
% NURBS is a curve
temp = cw(ones(3,1),:);
pnt = cp./temp;
% first derivative
[cup,cuw] = nrbeval (dnurbs,tt);
temp1 = cuw(ones(3,1),:);
jac = (cup-temp1.*pnt)./temp;
if (iscell (tt))
jac = {jac};
end
% second derivative
if (nargout == 3 && exist ('dnurbs2'))
[cuup,cuuw] = nrbeval (dnurbs2, tt);
temp2 = cuuw(ones(3,1),:);
hess = (cuup - (2*cup.*temp1 + cp.*temp2)./temp + 2*cp.*temp1.^2./temp.^2)./temp;
if (iscell (tt))
hess = {hess};
end
end
end
varargout{1} = pnt;
varargout{2} = jac;
if (nargout == 3)
varargout{3} = hess;
end
end
%!demo
%! crv = nrbtestcrv;
%! nrbplot(crv,48);
%! title('First derivatives along a test curve.');
%!
%! tt = linspace(0.0,1.0,9);
%!
%! dcrv = nrbderiv(crv);
%!
%! [p1, dp] = nrbdeval(crv,dcrv,tt);
%!
%! p2 = vecnorm(dp);
%!
%! hold on;
%! plot(p1(1,:),p1(2,:),'ro');
%! h = quiver(p1(1,:),p1(2,:),p2(1,:),p2(2,:),0);
%! set(h,'Color','black');
%! hold off;
%!demo
%! srf = nrbtestsrf;
%! p = nrbeval(srf,{linspace(0.0,1.0,20) linspace(0.0,1.0,20)});
%! h = surf(squeeze(p(1,:,:)),squeeze(p(2,:,:)),squeeze(p(3,:,:)));
%! set(h,'FaceColor','blue','EdgeColor','blue');
%! title('First derivatives over a test surface.');
%!
%! npts = 5;
%! tt = linspace(0.0,1.0,npts);
%! dsrf = nrbderiv(srf);
%!
%! [p1, dp] = nrbdeval(srf, dsrf, {tt, tt});
%!
%! up2 = vecnorm(dp{1});
%! vp2 = vecnorm(dp{2});
%!
%! hold on;
%! plot3(p1(1,:),p1(2,:),p1(3,:),'ro');
%! h1 = quiver3(p1(1,:),p1(2,:),p1(3,:),up2(1,:),up2(2,:),up2(3,:));
%! h2 = quiver3(p1(1,:),p1(2,:),p1(3,:),vp2(1,:),vp2(2,:),vp2(3,:));
%! set(h1,'Color','black');
%! set(h2,'Color','black');
%!
%! hold off;
%!test
%! knots{1} = [0 0 0 1 1 1];
%! knots{2} = [0 0 0 .5 1 1 1];
%! knots{3} = [0 0 0 0 1 1 1 1];
%! cx = [0 0.5 1]; nx = length(cx);
%! cy = [0 0.25 0.75 1]; ny = length(cy);
%! cz = [0 1/3 2/3 1]; nz = length(cz);
%! coefs(1,:,:,:) = repmat(reshape(cx,nx,1,1),[1 ny nz]);
%! coefs(2,:,:,:) = repmat(reshape(cy,1,ny,1),[nx 1 nz]);
%! coefs(3,:,:,:) = repmat(reshape(cz,1,1,nz),[nx ny 1]);
%! coefs(4,:,:,:) = 1;
%! nurbs = nrbmak(coefs, knots);
%! x = rand(5,1); y = rand(5,1); z = rand(5,1);
%! tt = [x y z]';
%! ders = nrbderiv(nurbs);
%! [points,jac] = nrbdeval(nurbs,ders,tt);
%! assert(points,tt,1e-10)
%! assert(jac{1}(1,:,:),ones(size(jac{1}(1,:,:))),1e-12)
%! assert(jac{2}(2,:,:),ones(size(jac{2}(2,:,:))),1e-12)
%! assert(jac{3}(3,:,:),ones(size(jac{3}(3,:,:))),1e-12)
%!
%!test
%! knots{1} = [0 0 0 1 1 1];
%! knots{2} = [0 0 0 0 1 1 1 1];
%! knots{3} = [0 0 0 1 1 1];
%! cx = [0 0 1]; nx = length(cx);
%! cy = [0 0 0 1]; ny = length(cy);
%! cz = [0 0.5 1]; nz = length(cz);
%! coefs(1,:,:,:) = repmat(reshape(cx,nx,1,1),[1 ny nz]);
%! coefs(2,:,:,:) = repmat(reshape(cy,1,ny,1),[nx 1 nz]);
%! coefs(3,:,:,:) = repmat(reshape(cz,1,1,nz),[nx ny 1]);
%! coefs(4,:,:,:) = 1;
%! coefs = coefs([2 1 3 4],:,:,:);
%! nurbs = nrbmak(coefs, knots);
%! x = rand(5,1); y = rand(5,1); z = rand(5,1);
%! tt = [x y z]';
%! dnurbs = nrbderiv(nurbs);
%! [points, jac] = nrbdeval(nurbs,dnurbs,tt);
%! assert(points,[y.^3 x.^2 z]',1e-10);
%! assert(jac{2}(1,:,:),3*y'.^2,1e-12)
%! assert(jac{1}(2,:,:),2*x',1e-12)
%! assert(jac{3}(3,:,:),ones(size(z')),1e-12) nurbs-1.3.13/inst/PaxHeaders.26136/nrbmeasure.m 0000644 0000000 0000000 00000000132 13070134113 015755 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbmeasure.m 0000644 0001750 0001750 00000006254 13070134113 016142 0 ustar 00bect bect 0000000 0000000 % NRBMEASURE: Compute the distance between two given points along a NURBS curve.
%
% Calling Sequence:
%
% [dist, ddistds, ddistde] = nrbmeasure (nrb)
% [dist, ddistds, ddistde] = nrbmeasure (nrb, s, e)
% [dist, ddistds, ddistde] = nrbmeasure (nrb, s, e, tol)
%
% INPUT:
%
% nrb : a NURBS curve, see nrbmak.
% s : starting point in the parametric domain.
% e : ending point in the parametric domain.
% tol : tolerance for numerical quadrature, to be used in quad.
%
% OUTPUT:
%
% dist : distance between the two points along the NURBS curve.
% ddistds: derivative of the distance function with respect to the point s.
% ddistde: derivative of the distance function with respect to the point e.
%
% Description:
%
% Compute the distance between two given points along a NURBS curve, using
% quad for numerical integration. The points are given by their coordinates
% in the parametric domain.
%
% Examples:
%
% Compute the length of a circular arc constructed as a NURBS.
%
% c = nrbcirc (1, [0 0], 0, pi/2);
% s = 0; e = 1;
% l = nrbmeasure (c, s, e, 1e-7);
%
% Copyright (C) 2013 Carlo de Falco
%
% This program is free software; you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation; either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with Octave; see the file COPYING. If not, see
% .
function [dist, ddistds, ddistde] = nrbmeasure (nrb, s, e, tol)
if (nargin < 4)
tol = 1e-6;
if (nargin < 3)
e = 1;
if (nargin < 2)
s = 0;
end
end
end
nrb.knots = (nrb.knots - nrb.knots(1)) / (nrb.knots(end) - nrb.knots(1));
if (numel (s) > 1 && isscalar (e))
e = e * ones (size(s));
elseif (numel (e) > 1 && isscalar (s))
s = s * ones (size(e));
end
ders = nrbderiv (nrb);
dist = arrayfun (@(x, y) quad (@(u) len (u, nrb, ders), x, ...
y, tol), s, e);
if (nargout > 1)
ddistds = -len (s, nrb, ders);
if (nargout > 2)
ddistde = +len (e, nrb, ders);
end
end
end
function l = len (u, nrb, ders)
[~, d] = nrbdeval (nrb, ders, u);
f = d(1, :);
g = d(2, :);
h = d(3, :);
l = sqrt (f.^2 + g.^2 + h.^2);
end
%!test
%! c = nrbcirc (1, [0 0], 0, pi/3);
%! l = nrbmeasure(c, 0, 1, 1e-7);
%! assert (l, pi/3, 1e-7)
%!test
%! c = nrbcirc (1, [0 0], 0, pi/2);
%! s = zeros (1, 100); e = linspace (0, 1, 100);
%! for ii = 1:100
%! l(ii) = nrbmeasure (c, s(ii), e(ii), 1e-7);
%! endfor
%! xx = nrbeval (c, e);
%! theta = atan2 (xx(2,:), xx(1,:));
%! assert (l, theta, 1e-7)
%!test
%! c = nrbcirc (1, [0 0], 0, pi/2);
%! s = 0; e = linspace (0, 1, 100);
%! for ii = 1:100
%! l(ii) = nrbmeasure (c, s, e(ii), 1e-7);
%! endfor
%! l2 = nrbmeasure (c, s, e, 1e-7);
%! assert (l, l2, eps)
nurbs-1.3.13/inst/PaxHeaders.26136/vectrans.m 0000644 0000000 0000000 00000000132 13070134113 015437 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vectrans.m 0000644 0001750 0001750 00000003230 13070134113 015613 0 ustar 00bect bect 0000000 0000000 function dd = vectrans(vector)
%
% VECTRANS: Transformation matrix for a translation.
%
% Calling Sequence:
%
% st = vectrans(tvec)
%
% INPUT:
%
% tvec : A vectors defining the translation along the x,y and
% z axes. i.e. [tx, ty, ty]
%
% OUTPUT:
%
% st : Translation Transformation Matrix
%
% Description:
%
% Returns a (4x4) Transformation matrix for translation.
%
% The matrix is:
%
% [ 1 0 0 tx ]
% [ 0 1 0 ty ]
% [ 0 0 1 tz ]
% [ 0 0 0 1 ]
%
% Examples:
%
% Translate the NURBS line (0.0,0.0,0.0) - (1.0,1.0,1.0) by 3 along
% the x-axis, 2 along the y-axis and 4 along the z-axis.
%
% line = nrbline([0.0 0.0 0.0],[1.0 1.0 1.0]);
% trans = vectrans([3.0 2.0 4.0]);
% tline = nrbtform(line, trans);
%
% See also:
%
% nrbtform
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 1
error('Translation vector required');
end
v = [vector(:);0;0];
dd = [1 0 0 v(1); 0 1 0 v(2); 0 0 1 v(3); 0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbsurfderiveval.m 0000644 0000000 0000000 00000000132 13070134113 017175 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbsurfderiveval.m 0000644 0001750 0001750 00000026314 13070134113 017361 0 ustar 00bect bect 0000000 0000000 function skl = nrbsurfderiveval (srf, uv, d)
%
% NRBSURFDERIVEVAL: Evaluate n-th order derivatives of a NURBS surface
%
% usage: skl = nrbsurfderiveval (srf, [u; v], d)
%
% INPUT:
%
% srf : NURBS surface structure, see nrbmak
%
% u, v : parametric coordinates of the point where we compute the
% derivatives
%
% d : number of partial derivatives to compute
%
%
% OUTPUT:
%
% skl (i, j, k, l) = i-th component derived j-1,k-1 times at the
% l-th point.
%
% Adaptation of algorithm A4.4 from the NURBS book, pg137
%
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
skl = zeros (3, d+1, d+1, size (uv, 2));
for iu = 1:size(uv, 2);
wders = squeeze (surfderiveval (srf.number(1)-1, srf.order(1)-1, ...
srf.knots{1}, srf.number(2)-1, ...
srf.order(2)-1, srf.knots{2}, ...
squeeze (srf.coefs(4, :, :)), uv(1,iu), ...
uv(2,iu), d));
for idim = 1:3
Aders = squeeze (surfderiveval (srf.number(1)-1, srf.order(1)-1, ...
srf.knots{1}, srf.number(2)-1, ...
srf.order(2)-1, srf.knots{2}, ...
squeeze (srf.coefs(idim, :, :)), uv(1,iu),...
uv(2,iu), d));
for k=0:d
for l=0:d-k
v = Aders(k+1, l+1);
for j=1:l
v = v - nchoosek(l,j)*wders(1,j+1)*skl(idim, k+1, l-j+1,iu);
end
for i=1:k
v = v - nchoosek(k,i)*wders(i+1,1)*skl(idim, k-i+1, l+1, iu);
v2 =0;
for j=1:l
v2 = v2 + nchoosek(l,j)*wders(i+1,j+1)*skl(idim, k-i+1, l-j+1, iu);
end
v = v - nchoosek(k,i)*v2;
end
skl(idim, k+1, l+1, iu) = v/wders(1,1);
end
end
end
end
end
%!test
%! k = [0 0 1 1];
%! c = [0 1];
%! [coef(2,:,:), coef(1,:,:)] = meshgrid (c, c);
%! coef(3,:,:) = coef(1,:,:);
%! srf = nrbmak (coef, {k, k});
%! [u, v] = meshgrid (linspace(0,1,11));
%! uv = [u(:)';v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 0);
%! aux = nrbeval(srf,uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!test
%! k = [0 0 1 1];
%! c = [0 1];
%! [coef(2,:,:), coef(1,:,:)] = meshgrid (c, c);
%! coef(3,:,:) = coef(1,:,:);
%! srf = nrbmak (coef, {k, k});
%! srf = nrbkntins (srf, {[], rand(2,1)});
%! [u, v] = meshgrid (linspace(0,1,11));
%! uv = [u(:)';v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 0);
%! aux = nrbeval(srf,uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!shared srf, uv
%!test
%! k = [0 0 0 1 1 1];
%! c = [0 1/2 1];
%! [coef(1,:,:), coef(2,:,:)] = meshgrid (c, c);
%! coef(3,:,:) = coef(1,:,:);
%! srf = nrbmak (coef, {k, k});
%! ders= nrbderiv (srf);
%! [u, v] = meshgrid (linspace(0,1,11));
%! uv = [u(:)';v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 1);
%! [fun, der] = nrbdeval (srf, ders, uv);
%! assert (squeeze (skl (1:2,1,1,:)), fun(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,2,1,:)), der{1}(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,1,2,:)), der{2}(1:2,:), 1e3*eps)
%!
%!test
%! srf = nrbdegelev (srf, [3, 1]);
%! ders= nrbderiv (srf);
%! [fun, der] = nrbdeval (srf, ders, uv);
%! skl = nrbsurfderiveval (srf, uv, 1);
%! assert (squeeze (skl (1:2,1,1,:)), fun(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,2,1,:)), der{1}(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,1,2,:)), der{2}(1:2,:), 1e3*eps)
%!shared uv
%!test
%! k = [0 0 0 1 1 1];
%! c = [0 1/2 1];
%! [coef(2,:,:), coef(1,:,:)] = meshgrid (c, c);
%! coef(3,:,:) = coef(1,:,:);
%! srf = nrbmak (coef, {k, k});
%! ders= nrbderiv (srf);
%! [u, v] = meshgrid (linspace(0,1,11));
%! uv = [u(:)';v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 1);
%! [fun, der] = nrbdeval (srf, ders, uv);
%! assert (squeeze (skl (1:2,1,1,:)), fun(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,2,1,:)), der{1}(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,1,2,:)), der{2}(1:2,:), 1e3*eps)
%!
%!test
%! p = 3; q = 3;
%! mcp = 5; ncp = 5;
%! Lx = 10*rand(1); Ly = Lx;
%! srf = nrbdegelev (nrb4surf ([0 0], [Lx, 0], [0 Ly], [Lx Ly]), [p-1, q-1]);
%! %%srf = nrbkntins (srf, {linspace(0,1,mcp-p+2)(2:end-1), linspace(0,1,ncp-q+2)(2:end-1)});
%! %%srf.coefs = permute (srf.coefs, [1 3 2]);
%! ders= nrbderiv (srf);
%! [fun, der] = nrbdeval (srf, ders, uv);
%! skl = nrbsurfderiveval (srf, uv, 1);
%! assert (squeeze (skl (1:2,1,1,:)), fun(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,2,1,:)), der{1}(1:2,:), 1e3*eps)
%! assert (squeeze (skl (1:2,1,2,:)), der{2}(1:2,:), 1e3*eps)
%!shared srf, uv, P, dPdx, d2Pdx2, c1, c2
%!test
%! [u, v] = meshgrid (linspace(0,1,10));
%! uv = [u(:)';v(:)'];
%! c1 = nrbmak([0 1/2 1; 0 1 0],[0 0 0 1 1 1]);
%! c1 = nrbtform (c1, vecrotx (pi/2));
%! c2 = nrbtform(c1, vectrans([0 1 0]));
%! srf = nrbdegelev (nrbruled (c1, c2), [3, 1]);
%! skl = nrbsurfderiveval (srf, uv, 2);
%! P = squeeze(skl(:,1,1,:));
%! dPdx = squeeze(skl(:,2,1,:));
%! d2Pdx2 = squeeze(skl(:,3,1,:));
%!assert(P(3,:), 2*(P(1,:)-P(1,:).^2),100*eps)
%!assert(dPdx(3,:), 2-4*P(1,:), 100*eps)
%!assert(d2Pdx2(3,:), -4+0*P(1,:), 100*eps)
%! srf = nrbdegelev (nrbruled (c1, c2), [5, 6]);
%! skl = nrbsurfderiveval (srf, uv, 2);
%! P = squeeze(skl(:,1,1,:));
%! dPdx = squeeze(skl(:,2,1,:));
%! d2Pdx2 = squeeze(skl(:,3,1,:));
%! aux = nrbeval(srf,uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!assert(P(3,:), 2*(P(1,:)-P(1,:).^2),100*eps)
%!assert(dPdx(3,:), 2-4*P(1,:), 100*eps)
%!assert(d2Pdx2(3,:), -4+0*P(1,:), 100*eps)
%!
%!test
%! skl = nrbsurfderiveval (srf, uv, 0);
%! aux = nrbeval (srf, uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!shared dPdu, d2Pdu2, P, srf, uv
%!test
%! [u, v] = meshgrid (linspace(0,1,10));
%! uv = [u(:)';v(:)'];
%! c1 = nrbmak([0 1/2 1; 0.1 1.6 1.1; 0 0 0],[0 0 0 1 1 1]);
%! c2 = nrbmak([0 1/2 1; 0.1 1.6 1.1; 1 1 1],[0 0 0 1 1 1]);
%! srf = nrbdegelev (nrbruled (c1, c2), [0, 1]);
%! skl = nrbsurfderiveval (srf, uv, 2);
%! P = squeeze(skl(:,1,1,:));
%! dPdu = squeeze(skl(:,2,1,:));
%! dPdv = squeeze(skl(:,1,2,:));
%! d2Pdu2 = squeeze(skl(:,3,1,:));
%! aux = nrbeval(srf,uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!assert(dPdu(2,:), 3-4*P(1,:),100*eps)
%!assert(d2Pdu2(2,:), -4+0*P(1,:),100*eps)
%!
%!test
%! skl = nrbsurfderiveval (srf, uv, 0);
%! aux = nrbeval(srf,uv);
%! assert (squeeze (skl (1:2,1,1,:)), aux(1:2,:), 1e3*eps)
%!test
%! srf = nrb4surf([0 0], [1 0], [0 1], [1 1]);
%! geo = nrbdegelev (srf, [3 3]);
%1 geo.coefs (4, 2:end-1, 2:end-1) = geo.coefs (4, 2:end-1, 2:end-1) + .1 * rand (1, geo.number(1)-2, geo.number(2)-2);
%! geo = nrbkntins (geo, {[.1:.1:.9], [.2:.2:.8]});
%! [u, v] = meshgrid (linspace(0,1,10));
%! uv = [u(:)';v(:)'];
%! skl = nrbsurfderiveval (geo, uv, 2);
%! dgeo = nrbderiv (geo);
%! [pnts, ders] = nrbdeval (geo, dgeo, uv);
%! assert (ders{1}, squeeze(skl(:,2,1,:)), 1e-9)
%! assert (ders{2}, squeeze(skl(:,1,2,:)), 1e-9)
%!test
%! crv = nrbline ([1 0], [2 0]);
%! srf = nrbrevolve (crv, [0 0 0], [0 0 1], pi/2);
%! srf = nrbtransp (srf);
%! [v, u] = meshgrid (linspace (0, 1, 11));
%! uv = [u(:)'; v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 2);
%! c = sqrt(2);
%! w = @(x, y) (2 - c)*y.^2 + (c-2)*y + 1;
%! dwdy = @(x, y) 2*(2-c)*y + c - 2;
%! d2wdy2 = @(x, y) 2*(2-c);
%! F1 = @(x, y) (x+1) .* ((1-y).^2 + c*y.*(1-y)) ./ w(x,y);
%! F2 = @(x, y) (x+1) .* (y.^2 + c*y.*(1-y)) ./ w(x,y);
%! dF1dx = @(x, y) ((1-y).^2 + c*y.*(1-y)) ./ w(x,y);
%! dF2dx = @(x, y) (y.^2 + c*y.*(1-y)) ./ w(x,y);
%! dF1dy = @(x, y) (x+1) .* ((2 - 2*c)*y + c - 2) ./ w(x,y) - (x+1) .* ((1-y).^2 + c*y.*(1-y)) .* dwdy(x,y) ./ w(x,y).^2;
%! dF2dy = @(x, y) (x+1) .* ((2 - 2*c)*y + c) ./ w(x,y) - (x+1) .* (y.^2 + c*y.*(1-y)) .* dwdy(x,y) ./ w(x,y).^2;
%! d2F1dx2 = @(x, y) zeros (size (x));
%! d2F2dx2 = @(x, y) zeros (size (x));
%! d2F1dxdy = @(x, y) ((2 - 2*c)*y + c - 2) ./ w(x,y) - ((1-y).^2 + c*y.*(1-y)) .* dwdy(x,y) ./ w(x,y).^2;
%! d2F2dxdy = @(x, y) ((2 - 2*c)*y + c) ./ w(x,y) - (y.^2 + c*y.*(1-y)) .* dwdy(x,y) ./ w(x,y).^2;
%! d2F1dy2 = @(x, y) (x+1)*(2 - 2*c) ./ w(x,y) - 2*(x+1) .* ((2 - 2*c)*y + c - 2) .* dwdy(x,y) ./ w(x,y).^2 - ...
%! (x+1) .* ((1-y).^2 + c*y.*(1-y)) * d2wdy2(x,y) ./ w(x,y).^2 + ...
%! 2 * (x+1) .* ((1-y).^2 + c*y.*(1-y)) .* w(x,y) .*dwdy(x,y).^2 ./ w(x,y).^4;
%! d2F2dy2 = @(x, y) (x+1)*(2 - 2*c) ./ w(x,y) - 2*(x+1) .* ((2 - 2*c)*y + c) .* dwdy(x,y) ./ w(x,y).^2 - ...
%! (x+1) .* (y.^2 + c*y.*(1-y)) * d2wdy2(x,y) ./ w(x,y).^2 + ...
%! 2 * (x+1) .* (y.^2 + c*y.*(1-y)) .* w(x,y) .*dwdy(x,y).^2 ./ w(x,y).^4;
%! assert ([F1(u(:),v(:)), F2(u(:),v(:))], squeeze(skl(1:2,1,1,:))', 1e2*eps);
%! assert ([dF1dx(u(:),v(:)), dF2dx(u(:),v(:))], squeeze(skl(1:2,2,1,:))', 1e2*eps);
%! assert ([dF1dy(u(:),v(:)), dF2dy(u(:),v(:))], squeeze(skl(1:2,1,2,:))', 1e2*eps);
%! assert ([d2F1dx2(u(:),v(:)), d2F2dx2(u(:),v(:))], squeeze(skl(1:2,3,1,:))', 1e2*eps);
%! assert ([d2F1dxdy(u(:),v(:)), d2F2dxdy(u(:),v(:))], squeeze(skl(1:2,2,2,:))', 1e2*eps);
%! assert ([d2F1dy2(u(:),v(:)), d2F2dy2(u(:),v(:))], squeeze(skl(1:2,1,3,:))', 1e2*eps);
%!test
%! knots = {[0 0 1 1] [0 0 1 1]};
%! coefs(:,1,1) = [0;0;0;1];
%! coefs(:,2,1) = [1;0;0;1];
%! coefs(:,1,2) = [0;1;0;1];
%! coefs(:,2,2) = [1;1;1;2];
%! srf = nrbmak (coefs, knots);
%! [v, u] = meshgrid (linspace (0, 1, 3));
%! uv = [u(:)'; v(:)'];
%! skl = nrbsurfderiveval (srf, uv, 2);
%! w = @(x, y) x.*y + 1;
%! F1 = @(x, y) x ./ w(x,y);
%! F2 = @(x, y) y ./ w(x,y);
%! F3 = @(x, y) x .* y ./ w(x,y);
%! dF1dx = @(x, y) 1./w(x,y) - x.*y./w(x,y).^2;
%! dF1dy = @(x, y) - x.^2./w(x,y).^2;
%! dF2dx = @(x, y) - y.^2./w(x,y).^2;
%! dF2dy = @(x, y) 1./w(x,y) - x.*y./w(x,y).^2;
%! dF3dx = @(x, y) y./w(x,y) - x.*(y./w(x,y)).^2;
%! dF3dy = @(x, y) x./w(x,y) - y.*(x./w(x,y)).^2;
%! d2F1dx2 = @(x, y) -2*y./w(x,y).^2 + 2*x.*y.^2./w(x,y).^3;
%! d2F1dy2 = @(x, y) 2*x.^3./w(x,y).^3;
%! d2F1dxdy = @(x, y) -x./w(x,y).^2 - x./w(x,y).^2 + 2*x.^2.*y./w(x,y).^3;
%! d2F2dx2 = @(x, y) 2*y.^3./w(x,y).^3;
%! d2F2dy2 = @(x, y) -2*x./w(x,y).^2 + 2*y.*x.^2./w(x,y).^3;
%! d2F2dxdy = @(x, y) -y./w(x,y).^2 - y./w(x,y).^2 + 2*y.^2.*x./w(x,y).^3;
%! d2F3dx2 = @(x, y) -2*y.^2./w(x,y).^2 + 2*x.*y.^3./w(x,y).^3;
%! d2F3dy2 = @(x, y) -2*x.^2./w(x,y).^2 + 2*y.*x.^3./w(x,y).^3;
%! d2F3dxdy = @(x, y) 1./w(x,y) - 3*x.*y./w(x,y).^2 + 2*(x.*y).^2./w(x,y).^3;
%! assert ([F1(u(:),v(:)), F2(u(:),v(:)), F3(u(:),v(:))], squeeze(skl(1:3,1,1,:))', 1e2*eps);
%! assert ([dF1dx(u(:),v(:)), dF2dx(u(:),v(:)), dF3dx(u(:),v(:))], squeeze(skl(1:3,2,1,:))', 1e2*eps);
%! assert ([dF1dy(u(:),v(:)), dF2dy(u(:),v(:)), dF3dy(u(:),v(:))], squeeze(skl(1:3,1,2,:))', 1e2*eps);
%! assert ([d2F1dx2(u(:),v(:)), d2F2dx2(u(:),v(:)), d2F3dx2(u(:),v(:))], squeeze(skl(1:3,3,1,:))', 1e2*eps);
%! assert ([d2F1dy2(u(:),v(:)), d2F2dy2(u(:),v(:)), d2F3dy2(u(:),v(:))], squeeze(skl(1:3,1,3,:))', 1e2*eps);
%! assert ([d2F1dxdy(u(:),v(:)), d2F2dxdy(u(:),v(:)), d2F3dxdy(u(:),v(:))], squeeze(skl(1:3,2,2,:))', 1e2*eps);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbplot.m 0000644 0000000 0000000 00000000132 13070134113 015272 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbplot.m 0000644 0001750 0001750 00000023540 13070134113 015454 0 ustar 00bect bect 0000000 0000000 function nrbplot (nurbs, subd, varargin)
%
% NRBPLOT: Plot a NURBS curve or surface, or the boundary of a NURBS volume.
%
% Calling Sequence:
%
% nrbplot (nrb, subd)
% nrbplot (nrb, subd, p, v)
%
% INPUT:
%
% nrb : NURBS curve, surface or volume, see nrbmak.
%
% npnts : Number of evaluation points, for a surface or volume, a row
% vector with the number of points along each direction.
%
% [p,v] : property/value options
%
% Valid property/value pairs include:
%
% Property Value/{Default}
% -----------------------------------
% light {off} | on
% colormap {'copper'}
%
% Example:
%
% Plot the test surface with 20 points along the U direction
% and 30 along the V direction
%
% nrbplot(nrbtestsrf, [20 30])
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Carlo de Falco, Rafael Vazquez
% Copyright (C) 2012 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
nargs = nargin;
if nargs < 2
error ('Need a NURBS to plot and the number of subdivisions!');
elseif rem(nargs+2,2)
error ('Param value pairs expected')
end
% Default values
light='off';
cmap='summer';
% Recover Param/Value pairs from argument list
for i=1:2:nargs-2
Param = varargin{i};
Value = varargin{i+1};
if (~ischar (Param))
error ('Parameter must be a string')
elseif size(Param,1)~=1
error ('Parameter must be a non-empty single row string.')
end
switch lower (Param)
case 'light'
light = lower (Value);
if (~ischar (light))
error ('light must be a string.')
elseif ~(strcmp(light,'off') | strcmp(light,'on'))
error ('light must be off | on')
end
case 'colormap'
if ischar (Value)
cmap = lower(Value);
elseif size (Value, 2) ~= 3
error ('colormap must be a string or have exactly three columns.')
else
cmap=Value;
end
otherwise
error ('Unknown parameter: %s', Param)
end
end
colormap (cmap);
% convert the number of subdivisions in number of points
subd = subd+1;
% plot the curve or surface
if (iscell (nurbs.knots))
if (size (nurbs.knots,2) == 2) % plot a NURBS surface
knt = nurbs.knots;
order = nurbs.order;
p = nrbeval (nurbs, {linspace(knt{1}(order(1)),knt{1}(end-order(1)+1),subd(1)) ...
linspace(knt{2}(order(2)),knt{2}(end-order(2)+1),subd(2))});
if (strcmp (light,'on'))
% light surface
surfl (squeeze(p(1,:,:)), squeeze(p(2,:,:)), squeeze(p(3,:,:)));
shading interp;
else
surf (squeeze (p(1,:,:)), squeeze (p(2,:,:)), squeeze (p(3,:,:)));
shading faceted;
end
elseif (size (nurbs.knots,2) == 3) % plot the boundaries of a NURBS volume
bnd = nrbextract (nurbs);
hold_flag = ishold;
nrbplot (bnd(1), subd(2:3), varargin{:});
hold on
nrbplot (bnd(2), subd(2:3), varargin{:});
nrbplot (bnd(3), subd([1 3]), varargin{:});
nrbplot (bnd(4), subd([1 3]), varargin{:});
nrbplot (bnd(5), subd(1:2), varargin{:});
nrbplot (bnd(6), subd(1:2), varargin{:});
if (~hold_flag)
hold off
end
else
error ('nrbplot: some argument is not correct')
end
else
% plot a NURBS curve
order = nurbs.order;
p = nrbeval (nurbs, linspace (nurbs.knots(order), nurbs.knots(end-order+1), subd));
if (any (nurbs.coefs(3,:)))
% 3D curve
plot3 (p(1,:), p(2,:), p(3,:));
grid on;
else
% 2D curve
plot (p(1,:), p(2,:));
end
end
axis equal;
end
% plot the control surface
% hold on;
% mesh(squeeze(pnts(1,:,:)),squeeze(pnts(2,:,:)),squeeze(pnts(3,:,:)));
% hold off;
%!demo
%! crv = nrbtestcrv;
%! nrbplot(crv,100)
%! title('Test curve')
%! hold off
%!demo
%! coefs = [0.0 7.5 15.0 25.0 35.0 30.0 27.5 30.0;
%! 0.0 2.5 0.0 -5.0 5.0 15.0 22.5 30.0];
%! knots = [0.0 0.0 0.0 1/6 1/3 1/2 2/3 5/6 1.0 1.0 1.0];
%!
%! geom = [
%! nrbmak(coefs,knots)
%! nrbline([30.0 30.0],[20.0 30.0])
%! nrbline([20.0 30.0],[20.0 20.0])
%! nrbcirc(10.0,[10.0 20.0],1.5*pi,0.0)
%! nrbline([10.0 10.0],[0.0 10.0])
%! nrbline([0.0 10.0],[0.0 0.0])
%! nrbcirc(5.0,[22.5 7.5])
%! ];
%!
%! ng = length(geom);
%! for i = 1:ng
%! nrbplot(geom(i),500);
%! hold on;
%! end
%! hold off;
%! axis equal;
%! title('2D Geometry formed by a series of NURBS curves');
%!demo
%! sphere = nrbrevolve(nrbcirc(1,[],0.0,pi),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbplot(sphere,[40 40],'light','on');
%! title('Ball and torus - surface construction by revolution');
%! hold on;
%! torus = nrbrevolve(nrbcirc(0.2,[0.9 1.0]),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbplot(torus,[40 40],'light','on');
%! hold off
%!demo
%! knots = {[0 0 0 1/2 1 1 1] [0 0 0 1 1 1]...
%! [0 0 0 1/6 2/6 1/2 1/2 4/6 5/6 1 1 1]};
%!
%! coefs = [-1.0000 -0.9734 -0.7071 1.4290 1.0000 3.4172
%! 0 2.4172 0 0.0148 -2.0000 -1.9734
%! 0 2.0000 4.9623 9.4508 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -0.8536 0 -0.6036 1.9571 1.2071 3.5000
%! 0.3536 2.5000 0.2500 0.5429 -1.7071 -1.0000
%! 0 2.0000 4.4900 8.5444 3.4142 2.0000
%! 0.8536 1.0000 0.6036 1.0000 0.8536 1.0000
%! -0.3536 -4.0000 -0.2500 -1.2929 1.7071 1.0000
%! 0.8536 0 0.6036 -2.7071 -1.2071 -5.0000
%! 0 2.0000 4.4900 10.0711 3.4142 2.0000
%! 0.8536 1.0000 0.6036 1.0000 0.8536 1.0000
%! 0 -4.0000 0 0.7071 2.0000 5.0000
%! 1.0000 4.0000 0.7071 -0.7071 -1.0000 -5.0000
%! 0 2.0000 4.9623 14.4142 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -2.5000 -4.0000 -1.7678 0.7071 1.0000 5.0000
%! 0 4.0000 0 -0.7071 -3.5000 -5.0000
%! 0 2.0000 6.0418 14.4142 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -2.4379 0 -1.7238 2.7071 1.9527 5.0000
%! 0.9527 4.0000 0.6737 1.2929 -3.4379 -1.0000
%! 0 2.0000 6.6827 10.0711 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -0.9734 -1.0000 -0.6883 0.7071 3.4172 1.0000
%! 2.4172 0 1.7092 -1.4142 -1.9734 -2.0000
%! 0 4.0000 6.6827 4.9623 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! 0 -0.8536 0 0.8536 3.5000 1.2071
%! 2.5000 0.3536 1.7678 -1.2071 -1.0000 -1.7071
%! 0 3.4142 6.0418 4.4900 4.0000 0
%! 1.0000 0.8536 0.7071 0.6036 1.0000 0.8536
%! -4.0000 -0.3536 -2.8284 1.2071 1.0000 1.7071
%! 0 0.8536 0 -0.8536 -5.0000 -1.2071
%! 0 3.4142 7.1213 4.4900 4.0000 0
%! 1.0000 0.8536 0.7071 0.6036 1.0000 0.8536
%! -4.0000 0 -2.8284 1.4142 5.0000 2.0000
%! 4.0000 1.0000 2.8284 -0.7071 -5.0000 -1.0000
%! 0 4.0000 10.1924 4.9623 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! -4.0000 -2.5000 -2.8284 0.7071 5.0000 1.0000
%! 4.0000 0 2.8284 -2.4749 -5.0000 -3.5000
%! 0 4.0000 10.1924 6.0418 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! 0 -2.4379 0 1.3808 5.0000 1.9527
%! 4.0000 0.9527 2.8284 -2.4309 -1.0000 -3.4379
%! 0 4.0000 7.1213 6.6827 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! -1.0000 -0.9734 0.2071 2.4163 1.0000 3.4172
%! 0 2.4172 -1.2071 -1.3954 -2.0000 -1.9734
%! 2.0000 4.0000 7.0178 6.6827 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -0.8536 0 0.3536 2.4749 1.2071 3.5000
%! 0.3536 2.5000 -0.8536 -0.7071 -1.7071 -1.0000
%! 1.7071 4.0000 6.3498 6.0418 1.7071 0
%! 0.8536 1.0000 0.8536 0.7071 0.8536 1.0000
%! -0.3536 -4.0000 0.8536 0.7071 1.7071 1.0000
%! 0.8536 0 -0.3536 -3.5355 -1.2071 -5.0000
%! 1.7071 4.0000 6.3498 7.1213 1.7071 0
%! 0.8536 1.0000 0.8536 0.7071 0.8536 1.0000
%! 0 -4.0000 1.2071 3.5355 2.0000 5.0000
%! 1.0000 4.0000 -0.2071 -3.5355 -1.0000 -5.0000
%! 2.0000 4.0000 7.0178 10.1924 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -2.5000 -4.0000 -0.5429 3.5355 1.0000 5.0000
%! 0 4.0000 -1.9571 -3.5355 -3.5000 -5.0000
%! 2.0000 4.0000 8.5444 10.1924 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -2.4379 0 -0.0355 3.5355 1.9527 5.0000
%! 0.9527 4.0000 -1.4497 -0.7071 -3.4379 -1.0000
%! 2.0000 4.0000 9.4508 7.1213 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000];
%! coefs = reshape (coefs, 4, 4, 3, 9);
%! horseshoe = nrbmak (coefs, knots);
%! nrbplot (horseshoe, [6, 6, 50], 'light', 'on');
nurbs-1.3.13/inst/PaxHeaders.26136/nrbpermute.m 0000644 0000000 0000000 00000000132 13070134113 015775 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbpermute.m 0000644 0001750 0001750 00000004515 13070134113 016160 0 ustar 00bect bect 0000000 0000000 function tvol = nrbpermute (vol, ord)
%
% NRBPERMUTE: Rearrange the directions of a NURBS volume or surface.
%
% Calling Sequence:
%
% tvol = nrbpermute(vol,order)
%
% INPUT:
%
% vol : NURBS volume or surface, see nrbmak.
% order : the order to rearrange the directions of the NURBS entity.
%
% OUTPUT:
%
% tvol : NURBS volume or surface with rearranged directions.
%
% Description:
%
% Utility function that rearranges the directions of a NURBS volume or
% surface. For surfaces, nrbpermute(srf,[2 1]) is the same as
% nrbtransp(srf). NURBS curves cannot be rearranged.
%
% Example:
%
% nrbpermute (vol, [1 3 2])
%
% Copyright (C) 2013 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (~iscell(vol.knots))
error('A NURBS curve cannot be rearranged.');
end
tvol = nrbmak (permute (vol.coefs, [1, ord+1]), {vol.knots{ord}});
%!demo
%! vol = nrbrevolve (nrb4surf ([1 0], [2 0], [1 1], [2 1]), [0 0 0], [0 1 0], pi/8);
%! nrbplot(vol,[5 10 20]);
%! title('NURBS volume and the same after reordering the directions')
%! hold on
%! vol.coefs(1,:,:) = vol.coefs(1,:,:) + 2;
%! vol = nrbpermute(vol,[2 3 1]);
%! nrbplot(vol,[5 10 20]);
%! hold off
%!test
%! vol = nrbrevolve (nrb4surf ([1 0], [2 0], [1 1], [2 1]), [0 0 0], [0 1 0], pi/8);
%! perm1 = [1 3 2];
%! perm2 = [2 1 3];
%! vol2 = nrbpermute (vol, perm1);
%! vol3 = nrbpermute (vol, perm2);
%! assert (vol.number(perm1), vol2.number)
%! assert (vol.order(perm1), vol2.order)
%! assert ({vol.knots{perm1}}, vol2.knots)
%! assert (permute(vol.coefs, [1, perm1+1]), vol2.coefs)
%! assert (vol.number(perm2), vol3.number)
%! assert (vol.order(perm2), vol3.order)
%! assert ({vol.knots{perm2}}, vol3.knots)
%! assert (permute(vol.coefs, [1, perm2+1]), vol3.coefs)
nurbs-1.3.13/inst/PaxHeaders.26136/kntbrkdegreg.m 0000644 0000000 0000000 00000000126 13070134113 016266 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/kntbrkdegreg.m 0000644 0001750 0001750 00000006443 13070134113 016450 0 ustar 00bect bect 0000000 0000000 % KNTBRKDEGREG: Construct an open knot vector by giving the sequence of
% knots, the degree and the regularity.
%
% knots = kntbrkdegreg (breaks, degree)
% knots = kntbrkdegreg (breaks, degree, regularity)
%
% INPUT:
%
% breaks: sequence of knots.
% degree: polynomial degree of the splines associated to the knot vector.
% regularity: splines regularity.
%
% OUTPUT:
%
% knots: knot vector.
%
% If REGULARITY has as many entries as BREAKS, or as the number of interior
% knots, a different regularity will be assigned to each knot. If
% REGULARITY is not present, it will be taken equal to DEGREE-1.
%
% Copyright (C) 2010 Carlo de Falco, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
function knots = kntbrkdegreg (breaks, degree, reg)
if (iscell (breaks))
if (nargin == 2)
reg = degree - 1;
end
if (numel(breaks)~=numel(degree) || numel(breaks)~=numel(reg))
error('kntbrkdegreg: degree and regularity must have the same length as the number of knot vectors')
end
degree = num2cell (degree);
if (~iscell (reg))
reg = num2cell (reg);
end
knots = cellfun (@do_kntbrkdegreg, breaks, degree, reg, 'uniformoutput', false);
else
if (nargin == 2)
reg = degree - 1;
end
knots = do_kntbrkdegreg (breaks, degree, reg);
end
end
function knots = do_kntbrkdegreg (breaks, degree, reg)
if (numel (breaks) < 2)
error ('kntbrkdegreg: the knots sequence should contain at least two points')
end
if (numel (reg) == 1)
mults = [-1, (degree (ones (1, numel (breaks) - 2)) - reg), -1];
elseif (numel (reg) == numel (breaks))
mults = degree - reg;
elseif (numel (reg) == numel (breaks) - 2)
mults = [-1 degree-reg -1];
else
error('kntbrkdegreg: the length of mult should be equal to one or the number of knots')
end
if (any (reg < -1))
warning ('kntbrkdegreg: for some knots the regularity is lower than -1')
elseif (any (reg > degree-1))
error('kntbrkdegreg: the regularity should be lower than the degree')
end
knots = kntbrkdegmult (breaks, degree, mults);
end
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! knots = kntbrkdegreg (breaks, degree);
%! assert (knots, [0 0 0 0 1 2 3 4 4 4 4])
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! reg = 1;
%! knots = kntbrkdegreg (breaks, degree, reg);
%! assert (knots, [0 0 0 0 1 1 2 2 3 3 4 4 4 4])
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! reg = [0 1 2];
%! knots = kntbrkdegreg (breaks, degree, reg);
%! assert (knots, [0 0 0 0 1 1 1 2 2 3 4 4 4 4])
%!test
%! breaks = {[0 1 2 3 4] [0 1 2 3]};
%! degree = [3 2];
%! reg = {[0 1 2] 0};
%! knots = kntbrkdegreg (breaks, degree, reg);
%! assert (knots, {[0 0 0 0 1 1 1 2 2 3 4 4 4 4] [0 0 0 1 1 2 2 3 3 3]})
nurbs-1.3.13/inst/PaxHeaders.26136/nrb2iges.m 0000644 0000000 0000000 00000000126 13070134113 015330 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrb2iges.m 0000644 0001750 0001750 00000024250 13070134113 015506 0 ustar 00bect bect 0000000 0000000 function nrb2iges (nurbs, filename)
% NRB2IGES : Write a NURBS curve or surface to an IGES file.
%
% Calling Sequence:
%
% nrb2iges (nurbs, filename);
%
% INPUT:
%
% nurbs : NURBS curve or surface, see nrbmak.
% filename : name of the output file.
%
% Description:
%
% The data of the nurbs structure is written in a file following the IGES
% format. For a more in-depth explanation see, for example:
% .
%
% Copyright (C) 2014 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
% This file is based on nurbs2iges.m, (C) 2006 Fu Qiang, originally
% released under the MIT license.
dt = datestr (now, 'yyyy.mm.dd');
dim = numel (nurbs(1).order);
% START SECTION
S{1} = '';
S{2} = 'IGES obtained from Nurbs toolbox.';
S{3} = 'See .';
S{4} = '';
% GLOBAL SECTION
G{1} = '1H,'; % Parameter Deliminator Character
G{2} = '1H;'; % Record Delimiter Character
G{3} = HString ('Nurbs toolbox'); % Product ID from Sender
G{4} = HString (filename); % File Name
G{5} = HString ('Octave Nurbs'); % System ID
G{6} = HString ('nrb2iges'); % Pre-processor Version
G{7} = '32'; % Number of Bits for Integers (No. of bits present in the integer representation of the sending system)
G{8} = '75'; % Single Precision Magnitude (Maximum power of 10 which may be represented as a single precision floating point number from the sending system)
G{9} = '6'; % Single Precision Significance (No. of significant digits of a single precision floating point number on the sending system)
G{10}= '75'; % Double Precision Magnitude (Maximum power of 10 which may be represented as a double precision floating point number from the sending system)
G{11}= '15'; % Double Precision Significance (No. of significant digits of a double precision floating point number on the sending system)
G{12}= HString('Nurbs from Octave'); % Product ID for Receiver
G{13}= '1.0'; % Model Space Scale
G{14}= '6'; % Unit Flag (6 = metres)
G{15}= HString('M'); % Units (metres = "M")
G{16}= '1000'; % Maximum Number of Line Weights
G{17}= '1.0'; % Size of Maximum Line Width
G{18}= HString(dt); % Date and Time of file generation
G{19}= '0.000001'; % Minimum User-intended Resolution
G{20}= '10000.0'; % Approximate Maximum Coordinate
G{21}= HString('Jacopo Corno'); % Name of Author
G{22}= HString('GSCE - TU Darmstadt'); % Author's Organization
G{23}= '3'; % IGES Version Number (3 = IGES version 2.0)
G{24}= '0'; % Drafting Standard Code (0 = no standard)
% Convert section array to lines (maximum lenght 72)
SectionG = make_section (G, 72);
% DIRECTORY ENTRY SECTION
% Each directory entry consists of two, 80 character, fixed formatted lines
D = [];
for ii = 1:length (nurbs)
switch (dim)
case 1 % NURBS curve
D(ii).type = 126;
case 2 % NURBS surface
D(ii).type = 128;
otherwise
error ('Only curves and surfaces can be saved in IGES format.')
end
D(ii).id = 2*ii - 1; % odd counter (see Parameter data section)
D(ii).p_start = 0;
D(ii).p_count = 0;
end
% PARAMETER DATA SECTION
% The structure is a free formatted data entry from columns 1 to 64.
% Each line of free formatted data consists of the entity type number
% followed by the parameter data describing the entity.
% Columns 65 to 72 are reserved for a parameter data index which is an
% odd number counter, right justified in the field, which begins at the
% number 1 and progresses in odd increments for each entity entered.
% Column 73 is reserved for the letter ‘P’ to indicate the data element
% belongs to the parameter data section.
% Columns 74 to 80 are reserved for the sequence number. Each line of
% data corresponds to the entity type as specified in the global section.
SectionP = {};
for ii = 1:length (nurbs)
P = make_section_array (nurbs(ii)); % finish one entity
% Convert section array to lines
SP = make_section (P, 64);
D(ii).p_count = length (SP);
if (ii == 1)
D(ii).p_start = 1;
else
D(ii).p_start = D(ii-1).p_start + D(ii-1).p_count;
end
SectionP{ii} = SP;
end
% SAVE
fid = fopen (filename, 'w');
% Save Start Section
for ii = 1:length (S)
fprintf (fid, '%-72sS%7d\n', S{ii}, ii);
end
% Save Global Section
for ii = 1:length (SectionG)
fprintf (fid, '%-72sG%7d\n', SectionG{ii}, ii);
end
% Save Directory Entry Section
for i = 1:length (D)
fprintf (fid, '%8d%8d%8d%8d%8d%8d%8d%8d%8dD%7d\n', ...
D(i).type, D(i).p_start, 0, 0 ,0, 0, 0, 0, 0, i*2-1);
fprintf (fid, '%8d%8d%8d%8d%8d%8s%8s%8s%8dD%7d\n', ...
D(i).type, 0, 0, D(i).p_count, 0, ' ', ' ', ' ', 0, i*2);
end
% Save Parameter Data Section
lines_p = 0;
for jj = 1:length (D)
sec = SectionP{jj};
for ii = 1:length (sec)
lines_p = lines_p + 1;
fprintf (fid, '%-64s %7dP%7d\n', sec{ii}, D(jj).id, lines_p);
end
end
% Save Terminate Section
sec_t = sprintf ('%7dS%7dG%7dD%7dP%7d', length (S), length(SectionG), 2*length(D), lines_p);
fprintf (fid, '%-72sT%7d\n', sec_t, 1);
fclose(fid);
end
function P = make_section_array (nurbs)
dim = numel (nurbs.order);
% in IGES the control points are stored in the format [x, y, z, w]
% instead of [w*x, w*y, w*z, w]
for idim = 1:3
nurbs.coefs(idim,:) = nurbs.coefs(idim,:) ./ nurbs.coefs(4,:);
end
P = {};
switch dim
case 1
% Rational B-Spline Curve Entity
cp = nurbs.coefs;
deg = nurbs.order - 1;
knots = nurbs.knots;
uspan = [0 1];
isplanar = ~any(cp(3,:));
P{1} = '126'; % NURBS curve
P{2} = int2str (size (cp, 2) - 1); % Number of control points
P{3} = int2str (deg); % Degree
P{4} = int2str (isplanar); % Curve on xy plane
P{5} = '0';
P{6} = '0';
P{7} = '0';
index = 8;
for ii = 1:length (knots)
P{index} = sprintf ('%f', knots(ii));
index = index + 1;
end
for ii = 1:size (cp, 2)
P{index} = sprintf ('%f', cp(4,ii));
index = index + 1;
end
for ii = 1:size (cp, 2)
P{index} = sprintf ('%f', cp(1,ii));
index = index + 1;
P{index} = sprintf ('%f', cp(2,ii));
index = index + 1;
P{index} = sprintf ('%f', cp(3,ii));
index = index + 1;
end
P{index} = sprintf ('%f', uspan(1));
index = index +1;
P{index} = sprintf ('%f', uspan(2));
index = index +1;
P{index} = '0.0';
index = index +1;
P{index} = '0.0';
index = index +1;
if isplanar
P{index} = '1.0';
else
P{index} = '0.0';
end
index = index + 1;
P{index} = '0';
index = index + 1;
P{index} = '0';
case 2
% Rational B-Spline Surface Entity
cp = nurbs.coefs;
degU = nurbs.order(1) - 1;
degV = nurbs.order(2) - 1;
knotsU = nurbs.knots{1};
knotsV = nurbs.knots{2};
uspan = [0 1];
vspan = [0 1];
P{1} = '128'; % NURBS surface
P{2} = int2str (size (cp, 2) - 1); % Number of control points in U
P{3} = int2str (size (cp, 3) - 1); % Number of control points in V
P{4} = int2str (degU); % Degree in U
P{5} = int2str (degV); % Degree in V
P{6} = '0';
P{7} = '0';
P{8} = '0';
P{9} = '0';
P{10} = '0';
index = 11;
for ii = 1:length (knotsU)
P{index} = sprintf ('%f', knotsU(ii));
index = index + 1;
end
for ii = 1:length (knotsV)
P{index} = sprintf ('%f', knotsV(ii));
index = index + 1;
end
for jj = 1:size (cp, 3)
for ii = 1:size (cp, 2)
P{index} = sprintf ('%f', cp(4,ii,jj));
index = index + 1;
end
end
for jj = 1:size (cp, 3)
for ii = 1:size (cp, 2)
P{index} = sprintf ('%f',cp(1,ii,jj));
index = index + 1;
P{index} = sprintf ('%f',cp(2,ii,jj));
index = index + 1;
P{index} = sprintf ('%f',cp(3,ii,jj));
index = index + 1;
end
end
P{index} = sprintf('%f',uspan(1));
index = index +1;
P{index} = sprintf('%f',uspan(2));
index = index +1;
P{index} = sprintf('%f',vspan(1));
index = index +1;
P{index} = sprintf('%f',vspan(2));
index = index +1;
P{index} = '0';
index = index + 1;
P{index} = '0';
otherwise
end
end
function hs = HString (str)
% HString : Convert the string STR to the Hollerith format.
hs = sprintf ('%dH%s', length(str), str);
end
function sec = make_section (fields, linewidth)
sec = {};
index = 1;
line = '';
num = length (fields);
for i = 1:num
if (i < num)
newitem = [fields{i} ','];
else
newitem = [fields{i} ';'];
end
len = length (line) + length (newitem);
if ( len > linewidth )
% new line
sec{index} = line;
index = index + 1;
line = '';
end
line = [line newitem];
end
sec{index} = line;
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbmultipatch.m 0000644 0000000 0000000 00000000132 13070134113 016466 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbmultipatch.m 0000644 0001750 0001750 00000022726 13070134113 016655 0 ustar 00bect bect 0000000 0000000 function [interfaces, boundary] = nrbmultipatch (nurbs)
%
% NRBMULTIPATCH: construct the information for gluing conforming NURBS patches, using the same format as in GeoPDEs.
%
% Calling Sequence:
%
% [interfaces, boundary] = nrbmultipatch (nurbs);
%
% INPUT:
%
% nurbs : an array of NURBS surfaces or volumes (not both), see nrbmak.
%
% OUTPUT:
%
% interfaces: array with the information for each interface, that is:
% - number of the first patch (patch1), and the local side number (side1)
% - number of the second patch (patch2), and the local side number (side2)
% - flag (faces and volumes), ornt1, ornt2 (only volumes): information
% on how the two patches match, see below.
% boundary: array with the boundary faces that do not belong to any interface
% - nsides: total number of sides on the boundary array (numel(boundary))
% - patches: number of the patch to which the boundary belongs
% - sides: number of the local side on the patch
%
% The faces of two patches must match conformingly: the control points must be the same,
% with the knot vectors (in each direction) related by an affine transformation.
%
% The boundary faces are stored separately, that is, nsides=1 for each boundary.
% To join several faces under the same condition, the user should do it by hand.
%
% Copyright (C) 2014, 2015, 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
npatch = numel (nurbs);
if (~iscell (nurbs(1).knots))
ndim = 1;
tol = 1e-15;
compare_sides = @(nrb1, nrb2) max(abs(nrb1.coefs - nrb2.coefs)) < tol;
elseif (size(nurbs(1).knots,2) == 2)
ndim = 2;
compare_sides = @(nrb1, nrb2) compare_sides_univariate (nrb1, nrb2);
elseif (size(nurbs(1).knots,2) == 3)
ndim = 3;
compare_sides = @(nrb1, nrb2) compare_sides_bivariate (nrb1, nrb2);
end
non_set_faces = cell (npatch, 1);
for ii = 1:npatch
if (~iscell (nurbs(ii).knots))
if (ndim ~= 1)
error ('All the patches must have the same dimension (at least for now)')
end
elseif (ndim ~= size(nurbs(ii).knots,2))
error ('All the patches must have the same dimension (at least for now)')
end
non_set_faces{ii} = 1:2*ndim;
end
num_interfaces = 0;
num_boundaries = 0;
boundary = struct ('nsides', 0, 'patches', [], 'faces', []);
for i1 = 1:npatch
nrb_faces1 = nrbextract (nurbs(i1));
for j1 = non_set_faces{i1}
% This is to fix a bug when two faces of the same patch form an interface
% (for instance, in a ring or a torus)
if (isempty (intersect (non_set_faces{i1}, j1))); continue; end
nrb1 = nrb_faces1(j1);
% corners1 = face_corners (nrb1);
non_set_faces{i1} = setdiff (non_set_faces{i1}, j1);
flag = 0;
i2 = i1 - 1;
while (~flag && i2 < npatch)
i2 = i2 + 1;
nrb_faces2 = nrbextract (nurbs(i2));
j2 = 0;
while (~flag && j2 < numel (non_set_faces{i2}))
j2 = j2 + 1;
nrb2 = nrb_faces2(non_set_faces{i2}(j2));
if (ndim == 1)
flag = compare_sides (nrb1, nrb2);
MsgFlag = false;
elseif (ndim == 2)
[flag, MsgFlag] = compare_sides (nrb1, nrb2);
elseif (ndim == 3)
[flag, ornt1, ornt2, MsgFlag] = compare_sides (nrb1, nrb2);
end
if (MsgFlag)
display_warning (MsgFlag, i1, j1, i2, j2);
end
end
end
if (flag)
intrfc.patch1 = i1;
intrfc.side1 = j1;
intrfc.patch2 = i2;
intrfc.side2 = non_set_faces{i2}(j2);
if (ndim ==3)
intrfc.flag = flag;
intrfc.ornt1 = ornt1;
intrfc.ornt2 = ornt2;
elseif (ndim == 2)
intrfc.ornt = flag;
end
non_set_faces{i2} = setdiff (non_set_faces{i2}, non_set_faces{i2}(j2));
num_interfaces = num_interfaces + 1;
interfaces(num_interfaces) = intrfc;
else
bndry.nsides = 1;
bndry.patches = i1;
bndry.faces = j1;
num_boundaries = num_boundaries + 1;
boundary(num_boundaries) = bndry;
end
end
end
if (num_interfaces == 0)
interfaces = [];
end
if (num_boundaries == 0)
boundary = [];
end
end
% Compare the sides of two volumes
function [flag, ornt1, ornt2, MsgFlag] = compare_sides_bivariate (nrb1, nrb2)
MsgFlag = 0;
tol = 1e-13;
face_corners = @(x) reshape (x.coefs(:, [1 end], [1 end]), 4, []);
coefs1 = face_corners (nrb1);
coefs2 = face_corners (nrb2);
% Sort of relative error
tol = 1e-13 * max(abs(coefs1(1:3,1) - coefs1(1:3,end)));
tolknt = 1e-12;
% Should use some sort of relative error
if (max (max (abs (coefs1 - coefs2))) < tol)
flag = 1; ornt1 = 1; ornt2 = 1;
elseif (max (max (abs (coefs1 - coefs2(:,[1 3 2 4])))) < tol)
flag = -1; ornt1 = 1; ornt2 = 1;
elseif (max (max (abs (coefs1 - coefs2(:,[3 1 4 2])))) < tol)
flag = -1; ornt1 = -1; ornt2 = 1;
elseif (max (max (abs (coefs1 - coefs2(:,[2 1 4 3])))) < tol)
flag = 1; ornt1 = -1; ornt2 = 1;
elseif (max (max (abs (coefs1 - coefs2(:,[4 3 2 1])))) < tol)
flag = 1; ornt1 = -1; ornt2 = -1;
elseif (max (max (abs (coefs1 - coefs2(:,[4 2 3 1])))) < tol)
flag = -1; ornt1 = -1; ornt2 = -1;
elseif (max (max (abs (coefs1 - coefs2(:,[2 4 1 3])))) < tol)
flag = -1; ornt1 = 1; ornt2 = -1;
elseif (max (max (abs (coefs1 - coefs2(:,[3 4 1 2])))) < tol)
flag = 1; ornt1 = 1; ornt2 = -1;
else
flag = 0; ornt1 = 0; ornt2 = 0;
end
% Reorder control points and knot vectors, to make comparisons easier
if (flag)
if (flag == -1)
nrb2 = nrbtransp (nrb2);
end
if (ornt1 == -1)
nrb2 = nrbreverse (nrb2, 1);
end
if (ornt2 == -1)
nrb2 = nrbreverse (nrb2, 2);
end
if (nrb1.order ~= nrb2.order)
flag = 0;
MsgFlag = -3;
elseif (nrb1.number ~= nrb2.number)
flag = 0;
MsgFlag = -1;
elseif (any (cellfun (@numel, nrb1.knots) ~= cellfun (@numel, nrb2.knots))) % This is redundant
flag = 0;
MsgFlag = -4;
else
% Pass the knots to the [0 1] interval to compare
pass_to_01 = @(x) (x - x(1)) / (x(end) - x(1));
knt1 = cellfun (pass_to_01, nrb1.knots, 'UniformOutput', false);
knt2 = cellfun (pass_to_01, nrb2.knots, 'UniformOutput', false);
if (max (abs (nrb1.coefs(:) - nrb2.coefs(:))) > tol)
flag = 0;
MsgFlag = -2;
elseif ((max (abs (knt1{1} - knt2{1})) > tolknt) || (max (abs (knt1{2} - knt2{2})) > tolknt))
flag = 0;
MsgFlag = -5;
end
end
end
end
% Compare the sides of two surfaces
function [flag, MsgFlag] = compare_sides_univariate (nrb1, nrb2)
MsgFlag = 0;
face_corners = @(x) reshape (x.coefs(:, [1 end]), 4, []);
coefs1 = face_corners (nrb1);
coefs2 = face_corners (nrb2);
% Sort of relative error
tol = 1e-13 * max(abs(coefs1(1:3,1) - coefs1(1:3,end)));
tolknt = 1e-12;
if (max (max (abs (coefs1 - coefs2))) < tol)
flag = 1;
elseif (max (max (abs (coefs1 - coefs2(:,[end 1])))) < tol)
flag = -1;
else
flag = 0;
end
if (flag)
% Reorder control points and knot vectors, to make comparisons easier
if (flag == -1)
nrb2 = nrbreverse (nrb2);
end
if (nrb1.order ~= nrb2.order)
flag = 0;
MsgFlag = -3;
elseif (nrb1.number ~= nrb2.number)
flag = 0;
MsgFlag = -1;
elseif (numel(nrb1.knots) ~= numel(nrb2.knots)) % This is redundant
flag = 0;
MsgFlag = -4;
else
% Pass the knots to the [0 1] interval to compare
knt1 = (nrb1.knots - nrb1.knots(1)) / (nrb1.knots(end) - nrb1.knots(1));
knt2 = (nrb2.knots - nrb2.knots(1)) / (nrb2.knots(end) - nrb2.knots(1));
if (max (abs (nrb1.coefs(:) - nrb2.coefs(:))) > tol)
flag = 0;
MsgFlag = -2;
elseif (max (abs (knt1 - knt2)) > tolknt)
flag = 0;
MsgFlag = -5;
end
end
end
end
function display_warning (MsgFlag, patch1, face1, patch2, face2)
switch MsgFlag
case {-1}
warning (['The corners of PATCH %d FACE %d, and PATCH %d FACE %d coincide, but the number ' ...
'of control points is different. No information is saved in this case'], patch1, face1, patch2, face2)
case {-2}
warning (['The corners of PATCH %d FACE %d, and PATCH %d FACE %d coincide, but the internal ' ...
'control points do not. No information is saved in this case'], patch1, face1, patch2, face2)
case {-3}
warning (['The corners of PATCH %d FACE %d, and PATCH %d FACE %d coincide, but the degree ' ...
'is different. No information is saved in this case'], patch1, face1, patch2, face2)
case {-4}
warning (['The corners of PATCH %d FACE %d, and PATCH %d FACE %d coincide, but the number ' ...
'of knots is different. No information is saved in this case'], patch1, face1, patch2, face2)
case {-5}
warning (['The corners of PATCH %d FACE %d, and PATCH %d FACE %d coincide, but the ' ...
'knot vectors are different. No information is saved in this case'], patch1, face1, patch2, face2)
end
end nurbs-1.3.13/inst/PaxHeaders.26136/nrbtransp.m 0000644 0000000 0000000 00000000132 13070134113 015623 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbtransp.m 0000644 0001750 0001750 00000003611 13070134113 016002 0 ustar 00bect bect 0000000 0000000 function tsrf = nrbtransp(srf)
%
% NRBTRANSP: Transpose a NURBS surface, by swapping U and V directions.
%
% Calling Sequence:
%
% tsrf = nrbtransp(srf)
%
% INPUT:
%
% srf : NURBS surface, see nrbmak.
%
% OUTPUT:
%
% tsrf : NURBS surface with U and V diretions transposed.
%
% Description:
%
% Utility function that transposes a NURBS surface, by swapping U and
% V directions. NURBS curves cannot be transposed.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if ~iscell(srf.knots)
error(' A NURBS curve cannot be transposed.');
elseif size(srf.knots,2) == 3
error('The transposition of NURBS volumes has not been implemented.');
end
tsrf = nrbmak(permute(srf.coefs,[1 3 2]), fliplr(srf.knots));
end
%!demo
%! srf = nrb4surf([0 0 0], [1 0 1], [0 1 1], [1 1 2]);
%! nrbplot(srf,[20 5]);
%! title('Plane surface and its transposed (translated)')
%! hold on
%! srf.coefs(3,:,:) = srf.coefs(3,:,:) + 10;
%! srf = nrbtransp(srf);
%! nrbplot(srf,[20 5]);
%! hold off
%!test
%! srf = nrbrevolve(nrbline([1 0],[2 0]), [0 0 0], [0 0 1], pi/2);
%! srft = nrbtransp(srf);
%! assert (srf.number, fliplr(srft.number));
%! assert (srf.order, fliplr(srft.order));
%! assert (srf.knots, fliplr(srft.knots));
%! assert (srf.coefs, permute(srft.coefs, [1 3 2])); nurbs-1.3.13/inst/PaxHeaders.26136/basiskntins.m 0000644 0000000 0000000 00000000132 13070134113 016142 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/basiskntins.m 0000644 0001750 0001750 00000006007 13070134113 016323 0 ustar 00bect bect 0000000 0000000 function C = basiskntins (deg, kc, kf)
% Compute the coefficient matrix for non-uniform B-splines subdivision.
%
% This represents the B-spline basis given by a coarse knot vector
% in terms of the B-spline basis of a finer knot vector.
%
% The function is implemented for the univariate case, based on
% Algorithm A5.4 from 'The NURBS BOOK' pg164.
%
%
% Calling Sequence:
%
% S = basiskntins (deg, kc, kf);
%
% INPUT:
%
% deg - degree of the first knot vector
% kc - coarse knot vector
% kf - fine knot vector
%
% OUTPUT:
%
% S - The matrix relating the two spaces, of size (deg-nu, deg-nt)
% with nu = numel(u)-deg-1, nt = numel(t)-deg-1
%
% Copyright (C) 2015, 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
nk = numel(kc);
nc = nk - (deg+1);
u = new_knots(kc, kf);
nu = numel(u);
nf = nc + nu;
C = sparse (nf, nc);
ik = zeros(1,nk+nu);
n = nc - 1;
r = nu - 1;
m = nc + deg;
a = findspan(n, deg, u(1), kc);
b = findspan(n, deg, u(end), kc);
b = b+1;
C(1:a-deg+1,1:a-deg+1) = speye(a-deg+1);
C(b+nu:nc+nu,b:nc) = speye(nc-b+1);
ik(1:a+1) = kc(1:a+1);
ik(b+deg+nu+1:m+nu+1) = kc(b+deg+1:m+1);
ii = b + deg - 1;
ss = ii + nu;
for jj=r:-1:0
ind = (a+1):ii;
ind = ind(u(jj+1)<=kc(ind+1));
C(ind+ss-ii-deg,:) = 0;
C(ind+ss-ii-deg,ind-deg) = speye(numel(ind));
ik(ind+(ss-ii)+1) = kc(ind+1);
ii = ii - numel(ind);
ss = ss - numel(ind);
C(ss-deg,:) = C(ss-deg+1,:);
for l=1:deg
ind = ss - deg + l;
alfa = ik(ss+l+1) - u(jj+1);
if abs(alfa) == 0
C(ind,:) = C(ind+1,:);
else
alfa = alfa/(ik(ss+l+1) - kc(ii-deg+l+1));
C(ind,:) = C(ind,:)*alfa + C(ind+1,:)*(1-alfa);
end
end
ik(ss+1) = u(jj+1);
ss = ss - 1;
end
end
function u = new_knots (kc, kf)
% Find the new knots, with the correct multiplicity
[valc, multc] = unique (kc, 'last');
multc = diff ([0 multc(:)']);
[valf, multf] = unique (kf, 'last');
multf = diff ([0 multf(:)']);
unew = setdiff (kf, kc);
[~,posf] = ismember (unew, valf);
mult_new = multf(posf);
[urep, indc, indf] = intersect (valc, valf);
mult_rep = multf(indf) - multc(indc);
urep = urep(mult_rep>0);
mult_rep = mult_rep(mult_rep>0);
mult = [mult_new mult_rep];
u = [unew, urep];
ind = zeros (numel(kf)-numel(kc), 1);
ind(cumsum([1 mult(:)'])) = 1;
u = sort (u(cumsum(ind(1:end-1))));
end nurbs-1.3.13/inst/PaxHeaders.26136/nrbunclamp.m 0000644 0000000 0000000 00000000132 13070134113 015753 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbunclamp.m 0000644 0001750 0001750 00000006726 13070134113 016144 0 ustar 00bect bect 0000000 0000000 function ucrv = nrbunclamp (crv, k, xdim)
% NRBUNCLAMP: Compute the knot vector and control points of the unclamped curve or surface.
%
% Calling Sequence:
%
% ucrv = nrbrunclamp (crv, k)
% ucrv = nrbrunclamp (crv, k, dim)
%
% INPUT:
%
% crv : NURBS curve or surface, see nrbmak.
% k : continuity for the unclamping (from 0 up to p-1)
% dim : dimension in which to unclamp (all by default).
%
% OUTPUT:
%
% ucrv: NURBS curve with unclamped knot vector, see nrbmak
%
% Description:
%
% Unclamps a curve, removing the open knot vector. Computes the new
% knot vector and control points of the unclamped curve.
%
% Adapted from Algorithm A12.1 from 'The NURBS BOOK' pg577.
%
% Copyright (C) 2013, 2014 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (iscell (crv.knots))
knt = crv.knots;
curve = false;
else
knt = {crv.knots};
curve = true;
end
ndim = numel (knt);
if (nargin < 3)
xdim = 1:ndim;
end
%if (iscell (crv.knots))
if (numel(k) ~= ndim)
k = k * ones(1, ndim);
end
Pw = crv.coefs;
for idim = xdim
p = crv.order(idim) - 1;
U = knt{idim};
n = crv.number(idim);
m = n + p + 1;
kk = k(idim);
if (kk >= p)
warning ('Taking the maximum k allowed, degree - 1')
kk = p - 1;
end
% Unclamp at left end
for ii=0:kk
U(kk-ii+1) = U(kk-ii+2) - (U(n+1-ii) - U(n-ii));
end
Pw = permute (Pw, [1, circshift([2 3 4], [0, 1-idim])]);
for ii = p-kk-1:p-2
for jj = ii:-1:0
alpha = (U(p+1) - U(p+jj-ii)) / (U(p+jj+2) - U(p+jj-ii));
Pw(:,jj+1,:,:) = (Pw(:,jj+1,:,:) - alpha*Pw(:,jj+2,:,:))/(1-alpha);
end
end
% Unclamp at right end
for ii=0:kk
U(m-kk+ii) = U(m-kk+ii-1) + U(p+ii+1+1) - U(p+ii+1);
end
for ii = p-kk-1:p-2
for jj = ii:-1:0
alpha = (U(n+1)-U(n-jj))/(U(n+2-jj+ii)-U(n-jj));
Pw(:,n-jj,:,:) = (Pw(:,n-jj,:,:) - (1-alpha)*Pw(:,n-jj-1,:,:))/alpha;
end
end
Pw = permute (Pw, [1, circshift([2 3 4], [0, idim-1])]);
knt{idim} = U;
end
if (~curve)
ucrv = nrbmak (Pw, knt);
else
ucrv = nrbmak (Pw, knt{:});
end
%!demo
%! crv = nrbcirc (1,[],0,2*pi/3);
%! crv = nrbdegelev (crv, 2);
%! figure
%! nrbctrlplot (crv); hold on
%! nrbctrlplot (nrbtform (nrbunclamp (crv, 1), vectrans([-0.4, -0.4])));
%! nrbctrlplot (nrbtform (nrbunclamp (crv, 2), vectrans([-0.8, -0.8])));
%! nrbctrlplot (nrbtform (nrbunclamp (crv, 3), vectrans([-1.6, -1.6])));
%! title ('Original curve and unclamped versions')
%!test
%! crv = nrbdegelev (nrbtestcrv,2);
%! x = linspace (0, 1, 100);
%! F = nrbeval (crv, x);
%! ucrv = nrbunclamp (crv, 0);
%! assert (F, nrbeval(ucrv, x));
%! ucrv = nrbunclamp (crv, 1);
%! assert (F, nrbeval(ucrv, x), 1e-14);
%! ucrv = nrbunclamp (crv, 2);
%! assert (F, nrbeval(ucrv, x), 1e-14);
%! ucrv = nrbunclamp (crv, 3);
%! assert (F, nrbeval(ucrv, x), 1e-14);
nurbs-1.3.13/inst/PaxHeaders.26136/kntrefine.m 0000644 0000000 0000000 00000000126 13070134113 015602 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/kntrefine.m 0000644 0001750 0001750 00000013724 13070134113 015764 0 ustar 00bect bect 0000000 0000000 % KNTREFINE: Refine a given knot vector by dividing each interval uniformly,
% maintaining the continuity in previously existing knots.
%
% [rknots] = kntrefine (knots, n_sub, degree, regularity)
% [rknots, zeta] = kntrefine (knots, n_sub, degree, regularity)
% [rknots, zeta, new_knots] = kntrefine (knots, n_sub, degree, regularity)
%
% INPUT:
%
% knots: initial knot vector.
% n_sub: number of new knots to be added in each interval.
% degree: polynomial degree of the refined knot vector
% regularity: maximum global regularity
%
% OUTPUT:
%
% rknots: refined knot vector
% zeta: refined knot vector without repetitions
% new_knots: new knots, to apply the knot insertion
%
% The regularity at the new inserted knots is the one given by the user.
% At previously existing knots, the regularity is the minimum
% between the previous regularity, and the one given by the user.
% This ensures optimal convergence rates in the context of IGA.
%
% Copyright (C) 2010 Carlo de Falco, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
function varargout = kntrefine (knots, n_sub, degree, regularity)
if (iscell(knots))
if (numel(n_sub)~=numel(degree) || numel(n_sub)~=numel(regularity) || ...
numel(n_sub)~=numel(knots))
error('kntrefine: n_sub, degree and regularity must have the same length as the number of knot vectors')
end
aux_knots = knots;
else
if (numel(n_sub)~=numel(degree) || numel(n_sub)~=numel(regularity) || ...
numel(n_sub)~=1)
error('kntrefine: n_sub, degree and regularity must have the same length as the number of knot vectors')
end
aux_knots = {knots};
end
if (nargout == 3)
for idim = 1:numel(n_sub)
if (degree(idim)+1 ~= sum (aux_knots{idim}==aux_knots{idim}(1)))
error ('kntrefine: new_knots is only computed when the degree is maintained');
end
end
for idim = 1:numel(n_sub)
min_mult = degree(idim) - regularity(idim);
z = unique (aux_knots{idim});
nz = numel (z);
deg = sum (aux_knots{idim} == z(1)) - 1;
rknots{idim} = z(ones(1, degree(idim)+1));
new_knots{idim} = [];
for ik = 2:nz
insk = linspace (z(ik-1), z(ik), n_sub(idim) + 2);
insk = vec (repmat (insk(2:end-1), min_mult, 1))';
old_mult = sum (aux_knots{idim} == z(ik));
mult = max (min_mult, degree(idim) - deg + old_mult);
rknots{idim} = [rknots{idim}, insk, z(ik*ones(1, mult))];
new_knots{idim} = [new_knots{idim}, insk, z(ik*ones(1, mult-old_mult))];
end
zeta{idim} = unique (rknots{idim});
end
if (~iscell(knots))
rknots = rknots{1};
zeta = zeta{1};
new_knots = new_knots{1};
end
varargout{1} = rknots;
varargout{2} = zeta;
varargout{3} = new_knots;
else
for idim = 1:numel(n_sub)
min_mult = degree(idim) - regularity(idim);
z = unique (aux_knots{idim});
nz = numel (z);
deg = sum (aux_knots{idim} == z(1)) - 1;
rknots{idim} = z(ones(1, degree(idim)+1));
for ik = 2:nz
insk = linspace (z(ik-1), z(ik), n_sub(idim) + 2);
insk = vec (repmat (insk(2:end-1), min_mult, 1))';
old_mult = sum (aux_knots{idim} == z(ik));
mult = max (min_mult, degree(idim) - deg + old_mult);
rknots{idim} = [rknots{idim}, insk, z(ik*ones(1, mult))];
end
zeta{idim} = unique (rknots{idim});
end
if (~iscell(knots))
rknots = rknots{1};
zeta = zeta{1};
end
varargout{1} = rknots;
if (nargout == 2)
varargout{2} = zeta;
end
end
end
function v = vec (in)
v = in(:);
end
%!shared nrbs
%!test
%! knots = {[0 0 1 1] [0 0 0 1 1 1]};
%! coefs(1,:,:) = [1 sqrt(2)/2 0; 2 sqrt(2) 0];
%! coefs(2,:,:) = [0 sqrt(2)/2 1; 0 sqrt(2) 2];
%! coefs(4,:,:) = [1 sqrt(2)/2 1; 1 sqrt(2)/2 1];
%! nrbs = nrbmak (coefs, knots);
%! nrbs = nrbkntins (nrbs, {[] [0.5 0.6 0.6]});
%! nrbs = nrbdegelev (nrbs, [0 1]);
%! nrbs = nrbkntins (nrbs, {[] [0.4]});
%! rknots = kntrefine (nrbs.knots, [1 1], [1 1], [0 0]);
%! assert (rknots{1} == [0 0 0.5 1 1]);
%! assert (rknots{2} == [0 0 0.2 0.4 0.45 0.5 0.55 0.6 0.8 1 1]);
%!
%!test
%! rknots = kntrefine (nrbs.knots, [1 1], [3 3], [0 0]);
%! assert (rknots{1}, [0 0 0 0 0.5 0.5 0.5 1 1 1 1]);
%! assert (rknots{2}, [0 0 0 0 0.2 0.2 0.2 0.4 0.4 0.4 0.45 0.45 0.45 0.5 0.5 0.5 0.55 0.55 0.55 0.6 0.6 0.6 0.8 0.8 0.8 1 1 1 1]);
%!
%!test
%! rknots = kntrefine (nrbs.knots, [1 1], [3 3], [2 2]);
%! assert (rknots{1}, [0 0 0 0 0.5 1 1 1 1]);
%! assert (rknots{2}, [0 0 0 0 0.2 0.4 0.45 0.5 0.5 0.55 0.6 0.6 0.6 0.8 1 1 1 1]);
%!
%!test
%! rknots = kntrefine (nrbs.knots, [1 1], [4 4], [0 0]);
%! assert (rknots{1}, [0 0 0 0 0 0.5 0.5 0.5 0.5 1 1 1 1 1]);
%! assert (rknots{2}, [0 0 0 0 0 0.2 0.2 0.2 0.2 0.4 0.4 0.4 0.4 0.45 0.45 0.45 0.45 0.5 0.5 0.5 0.5 0.55 0.55 0.55 0.55 0.6 0.6 0.6 0.6 0.8 0.8 0.8 0.8 1 1 1 1 1]);
%!
%!test
%! rknots = kntrefine (nrbs.knots, [1 1], [4 4], [3 3]);
%! assert (rknots{1}, [0 0 0 0 0 0.5 1 1 1 1 1]);
%! assert (rknots{2}, [0 0 0 0 0 0.2 0.4 0.4 0.45 0.5 0.5 0.5 0.55 0.6 0.6 0.6 0.6 0.8 1 1 1 1 1]);
%!
%!test
%! knots = [0 0 0 0 0.4 0.5 0.5 0.6 0.6 0.6 1 1 1 1];
%! rknots = kntrefine (knots, 1, 4, 3);
%! assert (rknots, [0 0 0 0 0 0.2 0.4 0.4 0.45 0.5 0.5 0.5 0.55 0.6 0.6 0.6 0.6 0.8 1 1 1 1 1]);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbderiv.m 0000644 0000000 0000000 00000000132 13070134113 015425 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbderiv.m 0000644 0001750 0001750 00000142424 13070134113 015612 0 ustar 00bect bect 0000000 0000000 function varargout = nrbderiv (nurbs)
%
% NRBDERIV: Construct the first and second derivative representation of a
% NURBS curve, surface or volume.
%
% Calling Sequence:
%
% ders = nrbderiv (nrb);
% [ders, ders2] = nrbderiv (nrb);
%
% INPUT:
%
% nrb : NURBS data structure, see nrbmak.
%
% OUTPUT:
%
% ders: A data structure that represents the first
% derivatives of a NURBS curve, surface or volume.
% ders2: A data structure that represents the second
% derivatives of a NURBS curve, surface or volume.
%
% Description:
%
% The derivatives of a B-Spline are themselves a B-Spline of lower degree,
% giving an efficient means of evaluating multiple derivatives. However,
% although the same approach can be applied to NURBS, the situation for
% NURBS is more complex. We have followed in this function the same idea
% that was already used for the first derivative in the function nrbderiv.
% The second derivative data structure can be evaluated later with the
% function nrbdeval.
%
% See also:
%
% nrbdeval
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Carlo de Falco
% Copyright (C) 2010, 2011 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (~isstruct(nurbs))
error('NURBS representation is not structure!');
end
if (~strcmp(nurbs.form,'B-NURBS'))
error('Not a recognised NURBS representation');
end
% We raise the degree to avoid errors in the computation of the second
% derivative
if (iscell (nurbs.knots))
ndim = size(nurbs.knots, 2);
else
ndim = 1;
end
if (nargout == 2)
degelev = max (2*ones(1, ndim) - (nurbs.order-1), 0);
nurbs = nrbdegelev (nurbs, degelev);
end
degree = nurbs.order - 1;
if (ndim == 3)
% NURBS structure represents a volume
num1 = nurbs.number(1);
num2 = nurbs.number(2);
num3 = nurbs.number(3);
% taking derivatives along the u direction
dknots = nurbs.knots;
dcoefs = permute (nurbs.coefs,[1 3 4 2]);
dcoefs = reshape (dcoefs,4*num2*num3,num1);
[dcoefs,dknots{1}] = bspderiv (degree(1),dcoefs,nurbs.knots{1});
dcoefs = permute (reshape (dcoefs,[4 num2 num3 size(dcoefs,2)]),[1 4 2 3]);
dnurbs{1} = nrbmak (dcoefs, dknots);
if (nargout == 2)
% taking second derivative along the u direction (duu)
dknots2 = dknots;
dcoefs2 = permute (dcoefs, [1 3 4 2]);
dcoefs2 = reshape (dcoefs2, 4*num2*num3, []);
[dcoefs2, dknots2{1}] = bspderiv (degree(1)-1, dcoefs2, dknots{1});
dcoefs2 = permute (reshape (dcoefs2, 4, num2, num3, []), [1 4 2 3]);
dnurbs2{1,1} = nrbmak (dcoefs2, dknots2);
% taking second derivative along the v direction (duv and dvu)
dknots2 = dknots;
dcoefs2 = permute (dcoefs,[1 2 4 3]);
dcoefs2 = reshape (dcoefs2, 4*(num1-1)*num3, num2);
[dcoefs2, dknots2{2}] = bspderiv (degree(2), dcoefs2, dknots{2});
dcoefs2 = permute (reshape (dcoefs2, 4, num1-1, num3, []), [1 2 4 3]);
dnurbs2{1,2} = nrbmak (dcoefs2, dknots2);
dnurbs2{2,1} = dnurbs2{1,2};
% taking second derivative along the w direction (duw and dwu)
dknots2 = dknots;
dcoefs2 = reshape (dcoefs, 4*(num1-1)*num2, num3);
[dcoefs2, dknots2{3}] = bspderiv (degree(3), dcoefs2, dknots{3});
dcoefs2 = reshape (dcoefs2, 4, num1-1, num2, []);
dnurbs2{1,3} = nrbmak (dcoefs2, dknots2);
dnurbs2{3,1} = dnurbs2{1,3};
end
% taking derivatives along the v direction
dknots = nurbs.knots;
dcoefs = permute (nurbs.coefs,[1 2 4 3]);
dcoefs = reshape (dcoefs,4*num1*num3,num2);
[dcoefs,dknots{2}] = bspderiv (degree(2),dcoefs,nurbs.knots{2});
dcoefs = permute (reshape (dcoefs,[4 num1 num3 size(dcoefs,2)]),[1 2 4 3]);
dnurbs{2} = nrbmak (dcoefs, dknots);
if (nargout == 2)
% taking second derivative along the v direction (dvv)
dknots2 = dknots;
dcoefs2 = permute (dcoefs,[1 2 4 3]);
dcoefs2 = reshape (dcoefs2, 4*num1*num3, num2-1);
[dcoefs2, dknots2{2}] = bspderiv (degree(2)-1, dcoefs2, dknots{2});
dcoefs2 = permute (reshape (dcoefs2, 4, num1, num3, []), [1 2 4 3]);
dnurbs2{2,2} = nrbmak (dcoefs2, dknots2);
% taking second derivative along the w direction (dvw and dwv)
dknots2 = dknots;
dcoefs2 = reshape (dcoefs, 4*num1*(num2-1), num3);
[dcoefs2, dknots2{3}] = bspderiv (degree(3), dcoefs2, dknots{3});
dcoefs2 = reshape (dcoefs2, 4, num1, num2-1, []);
dnurbs2{2,3} = nrbmak (dcoefs2, dknots2);
dnurbs2{3,2} = dnurbs2{2,3};
end
% taking derivatives along the w direction
dknots = nurbs.knots;
dcoefs = reshape (nurbs.coefs,4*num1*num2,num3);
[dcoefs,dknots{3}] = bspderiv (degree(3),dcoefs,nurbs.knots{3});
dcoefs = reshape (dcoefs,[4 num1 num2 size(dcoefs,2)]);
dnurbs{3} = nrbmak (dcoefs, dknots);
if (nargout == 2)
% taking second derivative along the w direction (dww)
dknots2 = dknots;
dcoefs2 = reshape (dcoefs, 4*num1*num2, num3-1);
[dcoefs2, dknots2{3}] = bspderiv (degree(3)-1, dcoefs2, dknots{3});
dcoefs2 = reshape (dcoefs2, 4, num1, num2, []);
dnurbs2{3,3} = nrbmak (dcoefs2, dknots2);
end
elseif (ndim == 2)
% NURBS structure represents a surface
num1 = nurbs.number(1);
num2 = nurbs.number(2);
% taking first derivative along the u direction
dknots = nurbs.knots;
dcoefs = permute (nurbs.coefs,[1 3 2]);
dcoefs = reshape (dcoefs,4*num2,num1);
[dcoefs,dknots{1}] = bspderiv (degree(1),dcoefs,nurbs.knots{1});
dcoefs = permute (reshape (dcoefs,[4 num2 size(dcoefs,2)]),[1 3 2]);
dnurbs{1} = nrbmak (dcoefs, dknots);
if (nargout == 2)
% taking second derivative along the u direction (duu)
dknots2 = dknots;
dcoefs2 = permute (dcoefs, [1 3 2]);
dcoefs2 = reshape (dcoefs2, 4*num2, []);
[dcoefs2, dknots2{1}] = bspderiv (degree(1)-1, dcoefs2, dknots{1});
dcoefs2 = permute (reshape (dcoefs2, 4, num2, []), [1 3 2]);
dnurbs2{1,1} = nrbmak (dcoefs2, dknots2);
% taking second derivative along the v direction (duv and dvu)
dknots2 = dknots;
dcoefs2 = reshape (dcoefs, 4*(num1-1), num2);
[dcoefs2, dknots2{2}] = bspderiv (degree(2), dcoefs2, dknots{2});
dcoefs2 = reshape (dcoefs2, 4, num1-1, []);
dnurbs2{1,2} = nrbmak (dcoefs2, dknots2);
dnurbs2{2,1} = dnurbs2{1,2};
end
% taking first derivative along the v direction
dknots = nurbs.knots;
dcoefs = reshape (nurbs.coefs,4*num1,num2);
[dcoefs,dknots{2}] = bspderiv (degree(2),dcoefs,nurbs.knots{2});
dcoefs = reshape (dcoefs,[4 num1 size(dcoefs,2)]);
dnurbs{2} = nrbmak (dcoefs, dknots);
if (nargout == 2)
% taking second derivative along the v direction (dvv)
dknots2 = dknots;
dcoefs2 = reshape (dcoefs, 4*num1, num2-1);
[dcoefs2, dknots2{2}] = bspderiv (degree(2)-1, dcoefs2, dknots{2});
dcoefs2 = reshape (dcoefs2, 4, num1, []);
dnurbs2{2,2} = nrbmak (dcoefs2, dknots2);
end
else
% NURBS structure represents a curve
[dcoefs,dknots] = bspderiv (degree, nurbs.coefs, nurbs.knots);
dnurbs = nrbmak (dcoefs, dknots);
if (nargout == 2)
[dcoefs2,dknots2] = bspderiv (degree-1, dcoefs, dknots);
dnurbs2 = nrbmak (dcoefs2, dknots2);
end
end
varargout{1} = dnurbs;
if (nargout == 2)
varargout{2} = dnurbs2;
if (iscell (dnurbs2))
dnurbs2 = [dnurbs2{:}];
end
if (any (arrayfun(@(x) any(isnan(x.coefs(:)) | isinf(x.coefs(:))), dnurbs2)))
warning ('nrbderiv:SecondDerivative', ...
['The structure for the second derivative contains Inf and/or NaN coefficients, ' ...
'probably due to low continuity at repeated knots. This should not affect the ' ...
'computation of the second derivatives, except at those knots.'])
end
end
end
%!demo
%! crv = nrbtestcrv;
%! nrbplot(crv,48);
%! title('First derivatives along a test curve.');
%!
%! tt = linspace(0.0,1.0,9);
%!
%! dcrv = nrbderiv(crv);
%!
%! [p1, dp] = nrbdeval(crv,dcrv,tt);
%!
%! p2 = vecnorm(dp);
%!
%! hold on;
%! plot(p1(1,:),p1(2,:),'ro');
%! h = quiver(p1(1,:),p1(2,:),p2(1,:),p2(2,:),0);
%! set(h,'Color','black');
%! hold off;
%!demo
%! srf = nrbtestsrf;
%! p = nrbeval(srf,{linspace(0.0,1.0,20) linspace(0.0,1.0,20)});
%! h = surf(squeeze(p(1,:,:)),squeeze(p(2,:,:)),squeeze(p(3,:,:)));
%! set(h,'FaceColor','blue','EdgeColor','blue');
%! title('First derivatives over a test surface.');
%!
%! npts = 5;
%! tt = linspace(0.0,1.0,npts);
%! dsrf = nrbderiv(srf);
%!
%! [p1, dp] = nrbdeval(srf, dsrf, {tt, tt});
%!
%! up2 = vecnorm(dp{1});
%! vp2 = vecnorm(dp{2});
%!
%! hold on;
%! plot3(p1(1,:),p1(2,:),p1(3,:),'ro');
%! h1 = quiver3(p1(1,:),p1(2,:),p1(3,:),up2(1,:),up2(2,:),up2(3,:));
%! h2 = quiver3(p1(1,:),p1(2,:),p1(3,:),vp2(1,:),vp2(2,:),vp2(3,:));
%! set(h1,'Color','black');
%! set(h2,'Color','black');
%!
%! hold off;
%!test
%! knots = [0 0 0 0.5 1 1 1];
%! coefs(1,:) = [0 2 4 2];
%! coefs(2,:) = [0 2 2 0];
%! coefs(3,:) = [0 4 2 0];
%! coefs(4,:) = [1 2 2 1];
%! nrb = nrbmak (coefs, knots);
%! [dnrb, dnrb2] = nrbderiv (nrb);
%! x = linspace (0, 1, 10);
%! [pnt, jac, hess] = nrbdeval (nrb, dnrb, dnrb2, x);
%! w = -4*x.^2 + 4*x + 1;
%! F = zeros (3,numel(x)); DF = zeros (3, numel(x)); D2F = zeros (3, numel(x));
%! F(1,:) = (-4*x.*(x-2)./w) .* (x<0.5) + ((4*x - 5)./w + 3) .* (x>0.5);
%! F(2,:) = (2-2./w);
%! F(3,:) = (-4*x.*(5*x-4)./w) .* (x<0.5) + (-4*(x.^2 - 1)./w) .* (x>0.5);
%! DF(1,:) = (8*(2*x.^2-x+1)./w.^2) .* (x<0.5) + (8*(2*x-3).*(x-1)./w.^2) .* (x>0.5);
%! DF(2,:) = -8*(2*x-1)./w.^2;
%! DF(3,:) = -(8*(2*x.^2+5*x-2)./w.^2) .* (x<0.5) - (8*(2*x.^2-3*x+2)./w.^2) .* (x>0.5);
%! D2F(1,:) = 8*(16*x.^3-12*x.^2+24*x-9)./w.^3 .* (x<0.5) + 8*(16*x.^3-60*x.^2+72*x-29)./w.^3 .* (x>0.5);
%! D2F(2,:) = -16*(12*x.^2-12*x+5)./w.^3;
%! D2F(3,:) = -8*(16*x.^3+60*x.^2-48*x+21)./w.^3 .* (x<0.5) -8*(16*x.^3-36*x.^2+48*x-19)./w.^3 .* (x>0.5);
%! assert (F, pnt, 1e3*eps)
%! assert (DF, jac, 1e3*eps)
%! assert (D2F, hess, 1e3*eps)
%!test
%! knots = {[0 0 0 1 1 1], [0 0 0 0.5 1 1 1]};
%! coefs = ones (4,3,4);
%! coefs(1,:,:) = reshape ([0 0 0 0; 1 1 1 1; 2 2 4 2], 1, 3, 4);
%! coefs(2,:,:) = reshape ([0 1 2 3; 0 1 2 3; 0 1 4 3], 1, 3, 4);
%! coefs(3,:,:) = reshape ([0 1 0 0; 0 0 0 0; 0 0 0 0], 1, 3, 4);
%! coefs(4,:,:) = reshape ([1 1 1 1; 1 1 1 1; 1 1 2 1], 1, 3, 4);
%! nrb = nrbmak (coefs, knots);
%! [dnrb, dnrb2] = nrbderiv (nrb);
%! X = linspace (0, 1, 4); Y = linspace (0, 1, 4);
%! [pnt, jac, hess] = nrbdeval (nrb, dnrb, dnrb2, {X Y});
%! [y, x] = meshgrid (X, Y);
%! w = (2*x.^2.*y.^2 + 1) .* (y < 0.5) + (-6*x.^2.*y.^2 + 8*x.^2.*y - 2*x.^2 + 1) .* (y > 0.5);
%! F = zeros ([3,size(x)]);
%! F(1,:,:) = ((2*x - 2) ./w + 2) .* (y<0.5) + (2 + (2*x-2)./w) .* (y > 0.5);
%! F(2,:,:) = (2 - (2*(y-1).^2)./w).*(y<0.5) + ...
%! ((-12*x.^2.*y.^2 + 16*x.^2.*y - 4*x.^2 + 2*y.^2 + 1)./w).*(y>0.5);
%! F(3,:,:) = (-2*y.*(3*y - 2).*(x - 1).^2./w) .* (y<0.5) + ...
%! (2*(x - 1).^2.*(y - 1).^2./w) .* (y>0.5);
%! dFdu = zeros ([3,size(x)]);
%! dFdu(1,:,:) = (((8*x - 4*x.^2).*y.^2 + 2)./w.^2).*(y<0.5) + ...
%! (((12*y.^2 - 16*y + 4).*x.^2 + (-24*y.^2 + 32*y - 8).*x + 2)./w.^2).*(y>0.5);
%! dFdu(2,:,:) = (8*x.*y.^2.*(y - 1).^2./w.^2).*(y<0.5) + ...
%! ((4*x.*(3*y - 1).*(2*y.^2 - 1).*(y - 1))./w.^2).*(y>0.5);
%! dFdu(3,:,:) = (-4*y.*(2.*x.*y.^2 + 1).*(3*y - 2).*(x - 1)./w.^2).*(y<0.5) + ...
%! ((-4*(x - 1).*(y - 1).^2.*(6*x.*y.^2 - 8*x.*y + 2*x - 1))./w.^2).*(y>0.5);
%! dFdv = zeros ([3,size(x)]);
%! dFdv(1,:,:) = (-8*x.^2.*y.*(x - 1)./w.^2).*(y<0.5) + ...
%! (8*x.^2.*(3*y - 2).*(x - 1)./w.^2).*(y>0.5);
%! dFdv(2,:,:) = (-4*(2*y.*x.^2 + 1).*(y - 1)./w.^2).*(y<0.5) + ...
%! (((16*y.^2 - 20*y + 8).*x.^2 + 4*y)./w.^2).*(y>0.5);
%! dFdv(3,:,:) = (-4*(x - 1).^2.*(2*x.^2.*y.^2 + 3*y - 1)./w.^2).*(y<0.5) + ...
%! (4*(x - 1).^2.*(y - 1).*(2*x.^2 - 2*x.^2.*y + 1)./w.^2).*(y>0.5);
%! d2Fduu = zeros ([3, size(x)]);
%! d2Fduu(1,:,:) = (-((48*x.^2 - 16*x.^3).*y.^4 + (24*x - 8).*y.^2)./w.^3).*(y<0.5) + ...
%! (((32*(3*y - 1).*(x - 1).*(y - 1))-(8*(3*y - 1).*(x - 3).*(y - 1).*w))./w.^3).*(y>0.5);
%! d2Fduu(2,:,:) = (-(8*y.^2.*(6*x.^2.*y.^2 - 1).*(y - 1).^2)./w.^3).*(y<0.5) + ...
%! ((4*(3*y - 1).*(2*y.^2 - 1).*(y - 1).*(18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 + 1))./w.^3).*(y>0.5);
%! d2Fduu(3,:,:) = ((4*y.*(3*y - 2).*(8*x.^3.*y.^4 - 12*x.^2.*y.^4 + 6*x.^2.*y.^2 - 12*x.*y.^2 + 2*y.^2 - 1))./w.^3).*(y<0.5) + ...
%! ((4*(y - 1).^2.*(6*y.^2 - 8*y + 3) - 4*x.^3.*(y - 1).^2.*(72*y.^4 - 192*y.^3 + 176*y.^2 - 64*y + 8) + 4*x.^2.*(y - 1).^2.*(108*y.^4 - 288*y.^3 + 282*y.^2 - 120*y + 18) - 4*x.*(y - 1).^2.*(36*y.^2 - 48*y + 12))./w.^3) .* (y>0.5);
%! d2Fdvv = zeros ([3, size(x)]);
%! d2Fdvv(1,:,:) = (8*x.^2.*(6*x.^2.*y.^2 - 1).*(x - 1)./w.^3) .* (y<0.5) + ...
%! (8*x.^2.*(x - 1).*(54*x.^2.*y.^2 - 72*x.^2.*y + 26*x.^2 + 3)./w.^3) .* (y>0.5);
%! d2Fdvv(2,:,:) = (-((48*y.^2 - 32*y.^3).*x.^4 + (- 24*y.^2 + 48*y - 8).*x.^2 + 4)./w.^3) .*(y<0.5) + ...
%! (((192*y.^3 - 360*y.^2 + 288*y - 88).*x.^4 + (72*y.^2 - 28).*x.^2 + 4)./w.^3) .* (y>0.5);
%! d2Fdvv(3,:,:) = (4*(x - 1).^2.*(8*x.^4.*y.^3 + 18*x.^2.*y.^2 - 12*x.^2.*y - 3))./w.^3 .* (y<0.5) + ...
%! ((4*(x - 1).^2.*(24*x.^4 + 18*x.^2 + 1) + 4*y.^2.*(72*x.^4 + 18*x.^2).*(x - 1).^2 - 96*x.^4.*y.^3.*(x - 1).^2 - 4*y.*(72*x.^4 + 36*x.^2).*(x - 1).^2)./w.^3) .* (y>0.5);
%! d2Fduv = zeros ([3, size(x)]);
%! d2Fduv(1,:,:) = (-(y.^3.*(32*x.^3 - 16*x.^4) - y.*(16*x - 24*x.^2))./w.^3) .* (y<0.5) + ...
%! (-(-8*(3*y - 2).*(6*y.^2 - 8*y + 2).*x.^4 + 8*(3*y - 2).*(12*y.^2 - 16*y + 4).*x.^3 + (48 - 72*y).*x.^2 + (48*y - 32).*x)./w.^3) .* (y>0.5);
%! d2Fduv(2,:,:) = (16*x.*y.*(y - 1).*(2*x.^2.*y.^2 + 2*y - 1)./w.^3) .* (y<0.5) + ...
%! (-(8*x.*(4*y.^2 - 5*y + 2))./w.^2 + (16*x.*(3*y - 2).*(2*y.^2 - 1))./w.^3) .* (y>0.5);
%! d2Fduv(3,:,:) = (-(8*(x - 1).*(4*x.^3.*y.^4 - 6*x.^2.*y.^3 + 6*x.^2.*y.^2 + 12*x.*y.^3 - 6*x.*y.^2 + 3*y - 1))./w.^3) .* (y<0.5) + ...
%! ((8*(x - 1).*(y - 1).*(12*x.^3.*y.^3 - 28*x.^3.*y.^2 + 20*x.^3.*y - 4*x.^3 + 6*x.^2.*y.^2 - 12*x.^2.*y + 6*x.^2 - 12*x.*y.^2 + 18*x.*y - 6*x + 1))./w.^3) .* (y>0.5);
%! assert (F, pnt, 1e3*eps)
%! assert (dFdu, jac{1}, 1e3*eps)
%! assert (dFdv, jac{2}, 1e3*eps)
%! assert (d2Fduu, hess{1,1}, 1e3*eps)
%! assert (d2Fduv, hess{1,2}, 1e3*eps)
%! assert (d2Fduv, hess{2,1}, 1e3*eps)
%! assert (d2Fdvv, hess{2,2}, 1e3*eps)
%!test
%! knots = {[0 0 0 1 1 1], [0 0 0 0.5 1 1 1]};
%! coefs = ones (4,3,4);
%! coefs(1,:,:) = reshape ([0 0 0 0; 1 1 1 1; 2 2 4 2], 1, 3, 4);
%! coefs(2,:,:) = reshape ([0 1 2 3; 0 1 2 3; 0 1 4 3], 1, 3, 4);
%! coefs(3,:,:) = reshape ([0 1 0 0; 0 0 0 0; 0 0 0 0], 1, 3, 4);
%! coefs(4,:,:) = reshape ([1 1 1 1; 1 1 1 1; 1 1 2 1], 1, 3, 4);
%! nrb = nrbmak (coefs, knots);
%! nrb = nrbdegelev (nrbextrude (nrb, [0.4 0.6 2]), [0 0 1]);
%! nrb.coefs(4,2,3,3) = 1.5;
%! [dnrb, dnrb2] = nrbderiv (nrb);
%! X = linspace (0, 1, 4); Y = linspace (0, 1, 4); Z = linspace (0, 1, 4);
%! [pnt, jac, hess] = nrbdeval (nrb, dnrb, dnrb2, {X Y Z});
%! [y, x, z] = meshgrid (X, Y, Z);
%! w = (-2*x.^2.*y.^2.*z.^2 + 2*x.^2.*y.^2 + 2*x.*y.^2.*z.^2 + 1) .* (y < 0.5) + ...
%! (6*x.^2.*y.^2.*z.^2 - 6*x.^2.*y.^2 - 8*x.^2.*y.*z.^2 + 8*x.^2.*y + 2*x.^2.*z.^2 - 2*x.^2 - 6*x.*y.^2.*z.^2 + 8*x.*y.*z.^2 - 2*x.*z.^2 + 1) .* (y > 0.5);
%! F = zeros ([3,size(x)]);
%! F(1,:,:,:) = ((10*x + 20*x.^2.*y.^2 + z.*(4*x.^2.*y.^2 + 2))./(5*w)) .* (y<0.5) + ...
%! (60*x.^2.*y.^2 - 10*x + z.*(12*x.^2.*y.^2 - 16*x.^2.*y + 4*x.^2 - 2) - 80*x.^2.*y + 20*x.^2)./(-5*w) .* (y > 0.5);
%! F(2,:,:,:) = ((20*y + 20*x.^2.*y.^2 + z.*(6*x.^2.*y.^2 + 3) - 10*y.^2)./(5*w)).*(y<0.5) + ...
%! ((60*x.^2.*y.^2 + z.*(18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 - 3) - 80*x.^2.*y + 20*x.^2 - 10*y.^2 - 5)./(-5*w)).*(y>0.5);
%! F(3,:,:,:) = ((4*y - 6*x.^2.*y.^2 + z.*(4*x.^2.*y.^2 + 2) - 8*x.*y + 12*x.*y.^2 + 4*x.^2.*y - 6*y.^2)./w) .* (y<0.5) + ...
%! ((2*z - 4*y - 4*x + 2*x.^2.*y.^2 + 8*x.*y - 4*x.*y.^2 - 4*x.^2.*y - 4*x.^2.*z + 2*x.^2 + 2*y.^2 + 16*x.^2.*y.*z - 12*x.^2.*y.^2.*z + 2)./w) .* (y>0.5);
%! dFdu = zeros ([3,size(x)]);
%! dFdu(1,:,:,:) = ((x.*((8*y.^2.*z.^3)/5 + 8*y.^2) - (4*y.^2.*z.^3)/5 + x.^2.*(z.^2.*(8*y.^4 + 4*y.^2) + (8*y.^4.*z.^3)/5 - 4*y.^2) + 2)./w.^2).*(y<0.5) + ...
%! ((z.^3.*(x.^2.*((72*y.^4)/5 - (192*y.^3)/5 + (176*y.^2)/5 - (64*y)/5 + 8/5) - (16*y)/5 - x.*((24*y.^2)/5 - (32*y)/5 + 8/5) + (12*y.^2)/5 + 4/5) - x.*(24*y.^2 - 32*y + 8) + x.^2.*(12*y.^2 - 16*y + 4) + x.^2.*z.^2.*(72*y.^4 - 192*y.^3 + 164*y.^2 - 48*y + 4) + 2)./w.^2).*(y>0.5);
%! dFdu(2,:,:,:) = ((z.^2.*(8*x.^2.*y.^4 - y.^2.*(8*y - 4*y.^2) + (2*x.*y.^2.*(40*y - 20*y.^2))/5) + z.^3.*((12*x.^2.*y.^4)/5 + (12*x.*y.^2)/5 - (6*y.^2)/5) + (2*x.*y.^2.*(20*y.^2 - 40*y + 20))/5)./w.^2).*(y<0.5) + ...
%! (((2*(3*y.^2 - 4*y + 1).*(18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 - 6*x + 3).*z.^3)/5 + (2*(3*y.^2 - 4*y + 1).*(60*x.^2.*y.^2 - 80*x.^2.*y + 20*x.^2 - 20*x.*y.^2 - 10*x + 10*y.^2 + 5).*z.^2)/5 - (2*(10*x - 20*x.*y.^2).*(3*y.^2 - 4*y + 1))/5)./w.^2).*(y>0.5);
%! dFdu(3,:,:,:) = ((4*y.*(3*y - 2) + z.^3.*(8*x.^2.*y.^4 + 8*x.*y.^2 - 4*y.^2) - z.^2.*(4*y.*(2*y.^2 - 3*y.^3).*x.^2 - 4*y.*(4*y.^2 - 6*y.^3).*x + 4*y.*(2*y.^2 - 3*y.^3)) + 4*x.^2.*y.*(4*y.^2 - 6*y.^3) - 4*x.*y.*(- 6*y.^3 + 4*y.^2 + 3*y - 2)) ./w.^2).*(y<0.5) + ...
%! ((z.^2.*(4*(y - 1).*(3*y.^3 - 7*y.^2 + 5*y - 1).*x.^2 - 4*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2).*x + 4*(y - 1).*(3*y.^3 - 7*y.^2 + 5*y - 1)) - 4*(y - 1).^2 + z.^3.*(4*(y - 1).*(18*y.^3 - 30*y.^2 + 14*y - 2).*x.^2 - 4*(6*y - 2).*(y - 1).*x + 4*(3*y - 1).*(y - 1)) + 4*x.*(y - 1).*(6*y.^3 - 14*y.^2 + 11*y - 3) - 4*x.^2.*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2))./w.^2) .* (y > 0.5);
%! dFdv = zeros ([3,size(x)]);
%! dFdv(1,:,:,:) = ((8*x.*y.*(x - 1).*(z.^3 + 5*x.*z.^2 - 5*x))/5./w.^2).*(y<0.5) + ...
%! (-(8*x.*(3*y - 2).*(x - 1).*(z.^3 + 5*x.*z.^2 - 5*x))/5./w.^2).*(y>0.5);
%! dFdv(2,:,:,:) = (-((8*x.*z.^2 - x.^2.*(8*z.^2 - 8)).*y.^2 + ((12*x.*z.^3)/5 - x.^2.*((12*z.^3)/5 + 8) + 4).*y - 4)./w.^2).*(y<0.5) + ...
%! ((4*y + z.^3.*(x.*((36*y)/5 - 24/5) - x.^2.*((36*y)/5 - 24/5)) + z.^2.*(x.*(16*y.^2 + 4*y - 8) - x.^2.*(16*y.^2 + 4*y - 8)) + x.^2.*(16*y.^2 - 20*y + 8))./w.^2).*(y>0.5);
%! dFdv(3,:,:,:) = ((4*(x - 1).^2 - y.*(4*(3*x - 3).*(x - 1) - 8*x.*z.^3.*(x - 1)) + y.^2.*(4*(x - 1).*(2*x.^3 - 4*x.^2 + 2*x).*z.^2 + 4*(2*x.^2 - 2*x.^3).*(x - 1)))./w.^2).*(y<0.5) + ...
%! ((y.^2.*(4*(x - 1).*(2*x.^3 - 4*x.^2 + 2*x).*z.^2 + 4*(2*x.^2 - 2*x.^3).*(x - 1)) - 4*(x - 1).*(2*x.^3 - 2*x.^2 + x - 1) - y.*(24*x.*(x - 1).*z.^3 + 4*(x - 1).*(4*x.^3 - 8*x.^2 + 4*x).*z.^2 - 4*(x - 1).*(4*x.^3 - 4*x.^2 + x - 1)) + 16*x.*z.^3.*(x - 1) + 4*z.^2.*(x - 1).*(2*x.^3 - 4*x.^2 + 2*x))./w.^2).*(y>0.5);
%! dFdw = zeros ([3,size(x)]);
%! dFdw(1,:,:,:) = ((4*x.^2.*y.^2 + 2)./(- 10*x.^2.*y.^2.*z.^2 + 10*x.^2.*y.^2 + 10*x.*y.^2.*z.^2 + 5) - ((20*x.*y.^2.*z - 20*x.^2.*y.^2.*z).*(10*x + 20*x.^2.*y.^2 + z.*(4*x.^2.*y.^2 + 2)))./(5*w).^2).*(y<0.5) + ...
%! ((12*x.^2.*y.^2 - 16*x.^2.*y + 4*x.^2 - 2)./(- 30*x.^2.*y.^2.*z.^2 + 30*x.^2.*y.^2 + 40*x.^2.*y.*z.^2 - 40*x.^2.*y - 10*x.^2.*z.^2 + 10*x.^2 + 30*x.*y.^2.*z.^2 - 40*x.*y.*z.^2 + 10*x.*z.^2 - 5) - ((60*x.^2.*y.^2 - 10*x + z.*(12*x.^2.*y.^2 - 16*x.^2.*y + 4*x.^2 - 2) - 80*x.^2.*y + 20*x.^2).*(- 60*z.*x.^2.*y.^2 + 80*z.*x.^2.*y - 20*z.*x.^2 + 60*z.*x.*y.^2 - 80*z.*x.*y + 20*z.*x))./(5*w).^2).*(y>0.5);
%! dFdw(2,:,:,:) = ((6*x.^2.*y.^2 + 3)./(- 10*x.^2.*y.^2.*z.^2 + 10*x.^2.*y.^2 + 10*x.*y.^2.*z.^2 + 5) - ((20*x.*y.^2.*z - 20*x.^2.*y.^2.*z).*(20*y + 20*x.^2.*y.^2 + z.*(6*x.^2.*y.^2 + 3) - 10*y.^2))./(5*w).^2).*(y<0.5) + ...
%! ((18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 - 3)./(- 30*x.^2.*y.^2.*z.^2 + 30*x.^2.*y.^2 + 40*x.^2.*y.*z.^2 - 40*x.^2.*y - 10*x.^2.*z.^2 + 10*x.^2 + 30*x.*y.^2.*z.^2 - 40*x.*y.*z.^2 + 10*x.*z.^2 - 5) - ((- 60*z.*x.^2.*y.^2 + 80*z.*x.^2.*y - 20*z.*x.^2 + 60*z.*x.*y.^2 - 80*z.*x.*y + 20*z.*x).*(60*x.^2.*y.^2 + z.*(18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 - 3) - 80*x.^2.*y + 20*x.^2 - 10*y.^2 - 5))./(5*w).^2).*(y>0.5);
%! dFdw(3,:,:,:) = ((4*x.^2.*y.^2 + 2)./(2*x.^2.*y.^2 - z.^2.*(2*x.^2.*y.^2 - 2*x.*y.^2) + 1) + (2*z.*(2*x.^2.*y.^2 - 2*x.*y.^2).*(4*y - 6*x.^2.*y.^2 + z.*(4*x.^2.*y.^2 + 2) - 8*x.*y + 12*x.*y.^2 + 4*x.^2.*y - 6*y.^2))./w.^2).*(y<0.5) + ...
%! ((12*x.^2.*y.^2 - 16*x.^2.*y + 4*x.^2 - 2)./(6*x.^2.*y.^2 + z.^2.*(- 6*x.^2.*y.^2 + 8*x.^2.*y - 2*x.^2 + 6*x.*y.^2 - 8*x.*y + 2*x) - 8*x.^2.*y + 2*x.^2 - 1) + (2*z.*(- 6*x.^2.*y.^2 + 8*x.^2.*y - 2*x.^2 + 6*x.*y.^2 - 8*x.*y + 2*x).*(2*z - 4*y - 4*x + 2*x.^2.*y.^2 + 8*x.*y - 4*x.*y.^2 - 4*x.^2.*y - 4*x.^2.*z + 2*x.^2 + 2*y.^2 + 16*x.^2.*y.*z - 12*x.^2.*y.^2.*z + 2))./w.^2).*(y>0.5);
%! d2Fduu = zeros ([3, size(x)]);
%! d2Fduu(1,:,:,:) = (((8*y.^2.*z.^3)/5 + 2*x.*(z.^2.*(8*y.^4 + 4*y.^2) + (8*y.^4.*z.^3)/5 - 4*y.^2) + 8*y.^2)./w.^2 - (2*(2*y.^2.*z.^2 + 4*x.*y.^2 - 4*x.*y.^2.*z.^2).*(x.*((8*y.^2.*z.^3)/5 + 8*y.^2) - (4*y.^2.*z.^3)/5 + x.^2.*(z.^2.*(8*y.^4 + 4*y.^2) + (8*y.^4.*z.^3)/5 - 4*y.^2) + 2))./w.^3).*(y<0.5) + ...
%! ((32*y + 2*x.*(12*y.^2 - 16*y + 4) + z.^3.*((32*y)/5 + 2*x.*((72*y.^4)/5 - (192*y.^3)/5 + (176*y.^2)/5 - (64*y)/5 + 8/5) - (24*y.^2)/5 - 8/5) - 24*y.^2 + 2*x.*z.^2.*(72*y.^4 - 192*y.^3 + 164*y.^2 - 48*y + 4) - 8)./w.^2 - (2*(z.^3.*(x.^2.*((72*y.^4)/5 - (192*y.^3)/5 + (176*y.^2)/5 - (64*y)/5 + 8/5) - (16*y)/5 - x.*((24*y.^2)/5 - (32*y)/5 + 8/5) + (12*y.^2)/5 + 4/5) - x.*(24*y.^2 - 32*y + 8) + x.^2.*(12*y.^2 - 16*y + 4) + x.^2.*z.^2.*(72*y.^4 - 192*y.^3 + 164*y.^2 - 48*y + 4) + 2).*(4*x + 6*y.^2.*z.^2 - 16*x.*y + 12*x.*y.^2 - 4*x.*z.^2 - 8*y.*z.^2 + 2*z.^2 + 16*x.*y.*z.^2 - 12*x.*y.^2.*z.^2))./(-w).^3).*(y>0.5);
%! d2Fduu(2,:,:,:) = ((z.^3.*((24*x.*y.^4)/5 + (12*y.^2)/5) + (2*y.^2.*(20*y.^2 - 40*y + 20))/5 + z.^2.*((2*y.^2.*(40*y - 20*y.^2))/5 + 16*x.*y.^4))./w.^2 - (2*(z.^2.*(8*x.^2.*y.^4 - y.^2.*(8*y - 4*y.^2) + (2*x.*y.^2.*(40*y - 20*y.^2))/5) + z.^3.*((12*x.^2.*y.^4)/5 + (12*x.*y.^2)/5 - (6*y.^2)/5) + (2*x.*y.^2.*(20*y.^2 - 40*y + 20))/5).*(2*y.^2.*z.^2 + 4*x.*y.^2 - 4*x.*y.^2.*z.^2))./w.^3).*(y<0.5) + ...
%! (((2*(3*y.^2 - 4*y + 1).*(36*x.*y.^2 - 48*x.*y + 12*x - 6).*z.^3)/5 - (2*(3*y.^2 - 4*y + 1).*(160*x.*y - 40*x - 120*x.*y.^2 + 20*y.^2 + 10).*z.^2)/5 + (2*(20*y.^2 - 10).*(3*y.^2 - 4*y + 1))/5)./w.^2 - (2*((2*(3*y.^2 - 4*y + 1).*(18*x.^2.*y.^2 - 24*x.^2.*y + 6*x.^2 - 6*x + 3).*z.^3)/5 + (2*(3*y.^2 - 4*y + 1).*(60*x.^2.*y.^2 - 80*x.^2.*y + 20*x.^2 - 20*x.*y.^2 - 10*x + 10*y.^2 + 5).*z.^2)/5 - (2*(10*x - 20*x.*y.^2).*(3*y.^2 - 4*y + 1))/5).*(4*x + 6*y.^2.*z.^2 - 16*x.*y + 12*x.*y.^2 - 4*x.*z.^2 - 8*y.*z.^2 + 2*z.^2 + 16*x.*y.*z.^2 - 12*x.*y.^2.*z.^2))./(-w).^3).*(y>0.5);
%! d2Fduu(3,:,:,:) = (((16*x.*y.^4 + 8*y.^2).*z.^3 + (4*y.*(4*y.^2 - 6*y.^3) - 8*x.*y.*(2*y.^2 - 3*y.^3)).*z.^2 - 4*y.*(- 6*y.^3 + 4*y.^2 + 3*y - 2) + 8*x.*y.*(4*y.^2 - 6*y.^3))./w.^2 - (2*(2*y.^2.*z.^2 + 4*x.*y.^2 - 4*x.*y.^2.*z.^2).*(4*y.*(3*y - 2) + z.^3.*(8*x.^2.*y.^4 + 8*x.*y.^2 - 4*y.^2) - z.^2.*(4*y.*(2*y.^2 - 3*y.^3).*x.^2 - 4*y.*(4*y.^2 - 6*y.^3).*x + 4*y.*(2*y.^2 - 3*y.^3)) + 4*x.^2.*y.*(4*y.^2 - 6*y.^3) - 4*x.*y.*(- 6*y.^3 + 4*y.^2 + 3*y - 2)))./w.^3).*(y<0.5) + ...
%! (-((4*(6*y - 2).*(y - 1) - 8*x.*(y - 1).*(18*y.^3 - 30*y.^2 + 14*y - 2)).*z.^3 + (4*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2) - 8*x.*(y - 1).*(3*y.^3 - 7*y.^2 + 5*y - 1)).*z.^2 - 4*(y - 1).*(6*y.^3 - 14*y.^2 + 11*y - 3) + 8*x.*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2))./w.^2 - (2*(z.^2.*(4*(y - 1).*(3*y.^3 - 7*y.^2 + 5*y - 1).*x.^2 - 4*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2).*x + 4*(y - 1).*(3*y.^3 - 7*y.^2 + 5*y - 1)) - 4*(y - 1).^2 + z.^3.*(4*(y - 1).*(18*y.^3 - 30*y.^2 + 14*y - 2).*x.^2 - 4*(6*y - 2).*(y - 1).*x + 4*(3*y - 1).*(y - 1)) + 4*x.*(y - 1).*(6*y.^3 - 14*y.^2 + 11*y - 3) - 4*x.^2.*(y - 1).*(6*y.^3 - 14*y.^2 + 10*y - 2)).*(4*x + 6*y.^2.*z.^2 - 16*x.*y + 12*x.*y.^2 - 4*x.*z.^2 - 8*y.*z.^2 + 2*z.^2 + 16*x.*y.*z.^2 - 12*x.*y.^2.*z.^2))./(-w).^3) .* (y>0.5);
%! d2Fduv = zeros ([3, size(x)]);
%! d2Fduv(1,:,:,:) = ((((8.*x.^2.*(6.*z.^3 - 6.*z.^5))/5 + (8.*x.^4.*(10.*z.^4 - 20.*z.^2 + 10))/5 - (8.*x.^3.*(- 4.*z.^5 + 10.*z.^4 + 4.*z.^3 - 30.*z.^2 + 20))/5 + (16.*x.*z.^5)/5).*y.^3 + ((8.*x.*(2.*z.^3 - 10.*z.^2 + 10))/5 + (8.*x.^2.*(15.*z.^2 - 15))/5 - (8.*z.^3)/5).*y)./w.^3) .* (y<0.5) + ...
%! (-(x.^4.*((8.*(3.*y - 2).*(30.*y.^2 - 40.*y + 10).*z.^4)/5 - (8.*(3.*y - 2).*(60.*y.^2 - 80.*y + 20).*z.^2)/5 + (8.*(3.*y - 2).*(30.*y.^2 - 40.*y + 10))/5) - x.^3.*(- (8.*(3.*y - 2).*(12.*y.^2 - 16.*y + 4).*z.^5)/5 + (8.*(3.*y - 2).*(30.*y.^2 - 40.*y + 10).*z.^4)/5 + (8.*(3.*y - 2).*(12.*y.^2 - 16.*y + 4).*z.^3)/5 - (8.*(3.*y - 2).*(90.*y.^2 - 120.*y + 30).*z.^2)/5 + (8.*(3.*y - 2).*(60.*y.^2 - 80.*y + 20))/5) + z.^3.*((24.*y)/5 - 16/5) - x.^2.*((8.*(3.*y - 2).*(18.*y.^2 - 24.*y + 6).*z.^5)/5 - (8.*(3.*y - 2).*(18.*y.^2 - 24.*y + 6).*z.^3)/5 + (72.*y - 48).*z.^2 - 72.*y + 48) + x.*((8.*(3.*y - 2).*(6.*y.^2 - 8.*y + 2).*z.^5)/5 + (32/5 - (48.*y)/5).*z.^3 + (48.*y - 32).*z.^2 - 48.*y + 32))./(-w).^3) .* (y>0.5);
%! d2Fduv(2,:,:,:) = ((((4.*x.^2.*(60.*z.^2 - 60.*z.^4))/5 + (4.*x.^3.*(40.*z.^4 - 80.*z.^2 + 40))/5 + 16.*x.*z.^4).*y.^4 + ((4.*x.^2.*(18.*z.^3 - 18.*z.^5))/5 + (4.*x.^3.*(12.*z.^5 - 12.*z.^3 + 40.*z.^2 - 40))/5 + (4.*x.*(6.*z.^5 - 40.*z.^2 + 40))/5 + 16.*z.^2).*y.^3 + ((4.*x.*(60.*z.^2 - 60))/5 - 24.*z.^2).*y.^2 + ((4.*x.*(6.*z.^3 + 20))/5 - (12.*z.^3)/5).*y)./w.^3) .* (y<0.5) + ...
%! ((z.^3.*(((432.*y.^3)/5 - (864.*y.^2)/5 + (528.*y)/5 - 96/5).*x.^3 + (- (648.*y.^3)/5 + (1296.*y.^2)/5 - (792.*y)/5 + 144/5).*x.^2 + ((72.*y)/5 - 48/5).*x - (36.*y)/5 + 24/5) - x.^3.*(192.*y.^4 - 496.*y.^3 + 480.*y.^2 - 208.*y + 32) + z.^4.*((- 192.*y.^4 + 208.*y.^3 + 96.*y.^2 - 144.*y + 32).*x.^3 + (288.*y.^4 - 312.*y.^3 - 144.*y.^2 + 216.*y - 48).*x.^2 + (- 96.*y.^4 + 104.*y.^3 + 48.*y.^2 - 72.*y + 16).*x) + x.*(- 96.*y.^3 + 96.*y.^2 + 8.*y - 16) + z.^2.*(x.^2.*(- 288.*y.^4 + 312.*y.^3 + 144.*y.^2 - 216.*y + 48) - 20.*y - x.^3.*(- 384.*y.^4 + 704.*y.^3 - 384.*y.^2 + 64.*y) + x.*(96.*y.^3 - 96.*y.^2 + 40.*y - 16) + 48.*y.^2 - 48.*y.^3 + 8) - z.^5.*(((432.*y.^3)/5 - (864.*y.^2)/5 + (528.*y)/5 - 96/5).*x.^3 + (- (648.*y.^3)/5 + (1296.*y.^2)/5 - (792.*y)/5 + 144/5).*x.^2 + ((216.*y.^3)/5 - (432.*y.^2)/5 + (264.*y)/5 - 48/5).*x))./(-w).^3) .* (y>0.5);
%! d2Fduv(3,:,:,:) = (((x.^2.*(48.*z.^2 - 48.*z.^4) - x.^4.*(16.*z.^4 - 48.*z.^2 + 32) + x.^3.*(48.*z.^4 - 96.*z.^2 + 32) + 16.*x.*z.^4).*y.^4 + (x.^2.*(- 48.*z.^5 + 48.*z.^3 + 144.*z.^2 - 144) - x.^3.*(- 32.*z.^5 + 32.*z.^3 + 48.*z.^2 - 48) + x.*(16.*z.^5 - 144.*z.^2 + 96) + 48.*z.^2).*y.^3 + (x.*(96.*z.^2 - 48) + x.^3.*(48.*z.^2 - 48) - x.^2.*(120.*z.^2 - 96) - 24.*z.^2).*y.^2 + (x.*(16.*z.^3 - 24) - 8.*z.^3 + 24).*y + 8.*x - 8)./w.^3) .* (y<0.5) + ...
%! ((8.*y - x.^4.*(96.*y.^4 - 320.*y.^3 + 384.*y.^2 - 192.*y + 32) + x.^3.*(96.*y.^4 - 368.*y.^3 + 528.*y.^2 - 336.*y + 80) + z.^3.*((288.*y.^3 - 576.*y.^2 + 352.*y - 64).*x.^3 + (- 432.*y.^3 + 864.*y.^2 - 528.*y + 96).*x.^2 + (48.*y - 32).*x - 24.*y + 16) - x.*(96.*y.^3 - 240.*y.^2 + 200.*y - 56) - z.^4.*((48.*y.^4 - 160.*y.^3 + 192.*y.^2 - 96.*y + 16).*x.^4 + (- 144.*y.^4 + 480.*y.^3 - 576.*y.^2 + 288.*y - 48).*x.^3 + (144.*y.^4 - 480.*y.^3 + 576.*y.^2 - 288.*y + 48).*x.^2 + (- 48.*y.^4 + 160.*y.^3 - 192.*y.^2 + 96.*y - 16).*x) + z.^2.*(x.^4.*(144.*y.^4 - 480.*y.^3 + 576.*y.^2 - 288.*y + 48) - 96.*y + x.^2.*(144.*y.^4 - 624.*y.^3 + 984.*y.^2 - 672.*y + 168) - x.^3.*(288.*y.^4 - 1008.*y.^3 + 1296.*y.^2 - 720.*y + 144) + x.*(144.*y.^3 - 384.*y.^2 + 336.*y - 96) + 120.*y.^2 - 48.*y.^3 + 24) - z.^5.*((288.*y.^3 - 576.*y.^2 + 352.*y - 64).*x.^3 + (- 432.*y.^3 + 864.*y.^2 - 528.*y + 96).*x.^2 + (144.*y.^3 - 288.*y.^2 + 176.*y - 32).*x) + x.^2.*(144.*y.^3 - 384.*y.^2 + 336.*y - 96) - 8)./(-w).^3) .* (y>0.5);
%! d2Fduw = zeros ([3, size(x)]);
%! d2Fduw(1,:,:,:) = ((x.^2.*((24.*y.^4.*z.^2)/5 + 2.*z.*(8.*y.^4 + 4.*y.^2)) - (12.*y.^2.*z.^2)/5 + (24.*x.*y.^2.*z.^2)/5)./w.^2 - (2.*(4.*x.*y.^2.*z - 4.*x.^2.*y.^2.*z).*(x.*((8.*y.^2.*z.^3)/5 + 8.*y.^2) - (4.*y.^2.*z.^3)/5 + x.^2.*(z.^2.*(8.*y.^4 + 4.*y.^2) + (8.*y.^4.*z.^3)/5 - 4.*y.^2) + 2))./w.^3) .* (y<0.5) + ...
%! (-((- (4.*(3.*y - 1).*(y - 1).*(36.*y.^4 - 96.*y.^3 + 88.*y.^2 - 32.*y + 4).*x.^4)/5 + (4.*(3.*y - 1).*(y - 1).*(36.*y.^4 - 96.*y.^3 + 100.*y.^2 - 48.*y + 8).*x.^3)/5 - (4.*(3.*y - 1).*(y - 1).*(18.*y.^2 - 24.*y + 6).*x.^2)/5 + (4.*(3.*y - 1).*(y - 1).*(6.*y.^2 - 8.*y + 2).*x)/5).*z.^4 + ((4.*x.^3.*(3.*y - 1).*(y - 1).*(360.*y.^4 - 960.*y.^3 + 820.*y.^2 - 240.*y + 20))/5 - (4.*x.^4.*(3.*y - 1).*(y - 1).*(360.*y.^4 - 960.*y.^3 + 820.*y.^2 - 240.*y + 20))/5).*z.^3 + (- (4.*(3.*y - 1).*(y - 1).*(108.*y.^4 - 288.*y.^3 + 264.*y.^2 - 96.*y + 12).*x.^4)/5 + (4.*(3.*y - 1).*(y - 1).*(36.*y.^2 - 48.*y + 12).*x.^3)/5 - (24.*(3.*y - 1).*(y - 1).*x)/5 + (12.*(3.*y - 1).*(y - 1))/5).*z.^2 + (- (4.*(3.*y - 1).*(y - 1).*(360.*y.^4 - 960.*y.^3 + 940.*y.^2 - 400.*y + 60).*x.^4)/5 + (4.*(3.*y - 1).*(y - 1).*(360.*y.^2 - 480.*y + 120).*x.^3)/5 - (4.*(3.*y - 1).*(y - 1).*(180.*y.^2 - 240.*y + 90).*x.^2)/5 + 16.*(3.*y - 1).*(y - 1).*x).*z)./(-w).^3) .* (y>0.5);
%! d2Fduw(2,:,:,:) = ((2.*z.*(8.*x.^2.*y.^4 - y.^2.*(8.*y - 4.*y.^2) + (2.*x.*y.^2.*(40.*y - 20.*y.^2))/5) + 3.*z.^2.*((12.*x.^2.*y.^4)/5 + (12.*x.*y.^2)/5 - (6.*y.^2)/5))./w.^2 - (2.*(4.*x.*y.^2.*z - 4.*x.^2.*y.^2.*z).*(z.^2.*(8.*x.^2.*y.^4 - y.^2.*(8.*y - 4.*y.^2) + (2.*x.*y.^2.*(40.*y - 20.*y.^2))/5) + z.^3.*((12.*x.^2.*y.^4)/5 + (12.*x.*y.^2)/5 - (6.*y.^2)/5) + (2.*x.*y.^2.*(20.*y.^2 - 40.*y + 20))/5))./w.^3) .* (y<0.5) + ...
%! (((6.*(3.*y.^2 - 4.*y + 1).*(18.*x.^2.*y.^2 - 24.*x.^2.*y + 6.*x.^2 - 6.*x + 3).*z.^2)/5 + (4.*(3.*y.^2 - 4.*y + 1).*(60.*x.^2.*y.^2 - 80.*x.^2.*y + 20.*x.^2 - 20.*x.*y.^2 - 10.*x + 10.*y.^2 + 5).*z)/5)./w.^2 - (2.*((2.*(3.*y.^2 - 4.*y + 1).*(18.*x.^2.*y.^2 - 24.*x.^2.*y + 6.*x.^2 - 6.*x + 3).*z.^3)/5 + (2.*(3.*y.^2 - 4.*y + 1).*(60.*x.^2.*y.^2 - 80.*x.^2.*y + 20.*x.^2 - 20.*x.*y.^2 - 10.*x + 10.*y.^2 + 5).*z.^2)/5 - (2.*(10.*x - 20.*x.*y.^2).*(3.*y.^2 - 4.*y + 1))/5).*(- 12.*z.*x.^2.*y.^2 + 16.*z.*x.^2.*y - 4.*z.*x.^2 + 12.*z.*x.*y.^2 - 16.*z.*x.*y + 4.*z.*x))./(-w).^3) .* (y>0.5);
%! d2Fduw(3,:,:,:) = (- (2.*z.*(4.*y.*(2.*y.^2 - 3.*y.^3).*x.^2 - 4.*y.*(4.*y.^2 - 6.*y.^3).*x + 4.*y.*(2.*y.^2 - 3.*y.^3)) - 3.*z.^2.*(8.*x.^2.*y.^4 + 8.*x.*y.^2 - 4.*y.^2))./w.^2 - (2.*(4.*x.*y.^2.*z - 4.*x.^2.*y.^2.*z).*(4.*y.*(3.*y - 2) + z.^3.*(8.*x.^2.*y.^4 + 8.*x.*y.^2 - 4.*y.^2) - z.^2.*(4.*y.*(2.*y.^2 - 3.*y.^3).*x.^2 - 4.*y.*(4.*y.^2 - 6.*y.^3).*x + 4.*y.*(2.*y.^2 - 3.*y.^3)) + 4.*x.^2.*y.*(4.*y.^2 - 6.*y.^3) - 4.*x.*y.*(- 6.*y.^3 + 4.*y.^2 + 3.*y - 2)))./w.^3) .* (y<0.5) + ...
%! ((2.*z.*(4.*(y - 1).*(3.*y.^3 - 7.*y.^2 + 5.*y - 1).*x.^2 - 4.*(y - 1).*(6.*y.^3 - 14.*y.^2 + 10.*y - 2).*x + 4.*(y - 1).*(3.*y.^3 - 7.*y.^2 + 5.*y - 1)) + 3.*z.^2.*(4.*(y - 1).*(18.*y.^3 - 30.*y.^2 + 14.*y - 2).*x.^2 - 4.*(6.*y - 2).*(y - 1).*x + 4.*(3.*y - 1).*(y - 1)))./w.^2 - (2.*(z.^2.*(4.*(y - 1).*(3.*y.^3 - 7.*y.^2 + 5.*y - 1).*x.^2 - 4.*(y - 1).*(6.*y.^3 - 14.*y.^2 + 10.*y - 2).*x + 4.*(y - 1).*(3.*y.^3 - 7.*y.^2 + 5.*y - 1)) - 4.*(y - 1).^2 + z.^3.*(4.*(y - 1).*(18.*y.^3 - 30.*y.^2 + 14.*y - 2).*x.^2 - 4.*(6.*y - 2).*(y - 1).*x + 4.*(3.*y - 1).*(y - 1)) + 4.*x.*(y - 1).*(6.*y.^3 - 14.*y.^2 + 11.*y - 3) - 4.*x.^2.*(y - 1).*(6.*y.^3 - 14.*y.^2 + 10.*y - 2)).*(- 12.*z.*x.^2.*y.^2 + 16.*z.*x.^2.*y - 4.*z.*x.^2 + 12.*z.*x.*y.^2 - 16.*z.*x.*y + 4.*z.*x))./(-w).^3) .* (y>0.5);
%! d2Fdvv = zeros ([3, size(x)]);
%! d2Fdvv(1,:,:,:) = (-(8.*x.*(x - 1).*(z.^3 + 5.*x.*z.^2 - 5.*x).*(- 6.*x.^2.*y.^2.*z.^2 + 6.*x.^2.*y.^2 + 6.*x.*y.^2.*z.^2 - 1))/5./w.^3) .* (y<0.5) + ...
%! ((8.*x.*(x - 1).*(z.^3 + 5.*x.*z.^2 - 5.*x).*(- 54.*x.^2.*y.^2.*z.^2 + 54.*x.^2.*y.^2 + 72.*x.^2.*y.*z.^2 - 72.*x.^2.*y - 26.*x.^2.*z.^2 + 26.*x.^2 + 54.*x.*y.^2.*z.^2 - 72.*x.*y.*z.^2 + 26.*x.*z.^2 + 3))/5./(-w).^3) .* (y>0.5);
%! d2Fdvv(2,:,:,:) = ((2.*((8.*x.*z.^2 - x.^2.*(8.*z.^2 - 8)).*y.^2 + ((12.*x.*z.^3)/5 - x.^2.*((12.*z.^3)/5 + 8) + 4).*y - 4).*(- 4.*y.*x.^2.*z.^2 + 4.*y.*x.^2 + 4.*y.*x.*z.^2))./w.^3 - ((12.*x.*z.^3)/5 + 2.*y.*(8.*x.*z.^2 - x.^2.*(8.*z.^2 - 8)) - x.^2.*((12.*z.^3)/5 + 8) + 4)./w.^2) .* (y<0.5) + ...
%! ((z.^2.*(x.*(32.*y + 4) - x.^2.*(32.*y + 4)) + x.^2.*(32.*y - 20) + z.^3.*((36.*x)/5 - (36.*x.^2)/5) + 4)./w.^2 - (2.*(4.*y + z.^3.*(x.*((36.*y)/5 - 24/5) - x.^2.*((36.*y)/5 - 24/5)) + z.^2.*(x.*(16.*y.^2 + 4.*y - 8) - x.^2.*(16.*y.^2 + 4.*y - 8)) + x.^2.*(16.*y.^2 - 20.*y + 8)).*(8.*x.^2.*z.^2 + 12.*x.^2.*y - 8.*x.*z.^2 - 8.*x.^2 + 12.*x.*y.*z.^2 - 12.*x.^2.*y.*z.^2))./(-w).^3) .* (y>0.5);
%! d2Fdvv(3,:,:,:) = ((2.*y.*(4.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x).*z.^2 + 4.*(2.*x.^2 - 2.*x.^3).*(x - 1)) - 4.*(3.*x - 3).*(x - 1) + 8.*x.*z.^3.*(x - 1))./w.^2 - (2.*(4.*(x - 1).^2 - y.*(4.*(3.*x - 3).*(x - 1) - 8.*x.*z.^3.*(x - 1)) + y.^2.*(4.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x).*z.^2 + 4.*(2.*x.^2 - 2.*x.^3).*(x - 1))).*(- 4.*y.*x.^2.*z.^2 + 4.*y.*x.^2 + 4.*y.*x.*z.^2))./w.^3) .* (y<0.5) + ...
%! ((4.*(x - 1).*(4.*x.^3 - 4.*x.^2 + x - 1) + 2.*y.*(4.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x).*z.^2 + 4.*(2.*x.^2 - 2.*x.^3).*(x - 1)) - 24.*x.*z.^3.*(x - 1) - 4.*z.^2.*(x - 1).*(4.*x.^3 - 8.*x.^2 + 4.*x))./w.^2 - (2.*(y.^2.*(4.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x).*z.^2 + 4.*(2.*x.^2 - 2.*x.^3).*(x - 1)) - 4.*(x - 1).*(2.*x.^3 - 2.*x.^2 + x - 1) - y.*(24.*x.*(x - 1).*z.^3 + 4.*(x - 1).*(4.*x.^3 - 8.*x.^2 + 4.*x).*z.^2 - 4.*(x - 1).*(4.*x.^3 - 4.*x.^2 + x - 1)) + 16.*x.*z.^3.*(x - 1) + 4.*z.^2.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x)).*(8.*x.^2.*z.^2 + 12.*x.^2.*y - 8.*x.*z.^2 - 8.*x.^2 + 12.*x.*y.*z.^2 - 12.*x.^2.*y.*z.^2))./(-w).^3) .* (y>0.5);
%! d2Fdvw = zeros ([3, size(x)]);
%! d2Fdvw(1,:,:,:) = (((8.*x.*z.*(x - 1).*(20.*x.^3.*z.^2 - 20.*x.^3 + 2.*x.^2.*z.^3 - 20.*x.^2.*z.^2 + 6.*x.^2.*z + 40.*x.^2 - 2.*x.*z.^3).*y.^3)/5 + (8.*x.*z.*(10.*x + 3.*z).*(x - 1).*y)/5)./w.^3) .* (y<0.5) + ...
%! (((8.*x.*(3.*y - 2).*(x - 1).*(- 6.*x.^2.*y.^2 + 8.*x.^2.*y - 2.*x.^2 + 6.*x.*y.^2 - 8.*x.*y + 2.*x).*z.^4)/5 + (8.*x.*(3.*y - 2).*(x - 1).*(- 60.*x.^3.*y.^2 + 80.*x.^3.*y - 20.*x.^3 + 60.*x.^2.*y.^2 - 80.*x.^2.*y + 20.*x.^2).*z.^3)/5 - (8.*x.*(3.*y - 2).*(x - 1).*(18.*x.^2.*y.^2 - 24.*x.^2.*y + 6.*x.^2 - 3).*z.^2)/5 + (8.*x.*(3.*y - 2).*(x - 1).*(60.*x.^3.*y.^2 - 80.*x.^3.*y + 20.*x.^3 - 120.*x.^2.*y.^2 + 160.*x.^2.*y - 40.*x.^2 + 10.*x).*z)/5)./(-w).^3) .* (y>0.5);
%! d2Fdvw(2,:,:,:) = ((4.*x.*y.*z.*(x - 1).*(40.*x.^2.*y.^3.*z.^2 - 40.*x.^2.*y.^3 + 6.*x.^2.*y.^2.*z.^3 + 18.*x.^2.*y.^2.*z + 80.*x.^2.*y.^2 - 40.*x.*y.^3.*z.^2 - 6.*x.*y.^2.*z.^3 - 40.*y.^2 + 60.*y + 9.*z))/5./w.^3) .* (y<0.5) + ...
%! (-((4.*x.*(x - 1).*(54.*x.^2.*y.^3 - 108.*x.^2.*y.^2 + 66.*x.^2.*y - 12.*x.^2 - 54.*x.*y.^3 + 108.*x.*y.^2 - 66.*x.*y + 12.*x).*z.^4)/5 + (4.*x.*(x - 1).*(240.*x.^2.*y.^4 - 260.*x.^2.*y.^3 - 120.*x.^2.*y.^2 + 180.*x.^2.*y - 40.*x.^2 - 240.*x.*y.^4 + 260.*x.*y.^3 + 120.*x.*y.^2 - 180.*x.*y + 40.*x).*z.^3)/5 - (4.*x.*(x - 1).*(- 162.*x.^2.*y.^3 + 324.*x.^2.*y.^2 - 198.*x.^2.*y + 36.*x.^2 + 27.*y - 18).*z.^2)/5 - (4.*x.*(x - 1).*(240.*x.^2.*y.^4 - 980.*x.^2.*y.^3 + 1320.*x.^2.*y.^2 - 700.*x.^2.*y + 120.*x.^2 + 120.*y.^3 - 120.*y.^2 + 50.*y - 20).*z)/5)./(-w).^3) .* (y>0.5);
%! d2Fdvw(3,:,:,:) = (-(y.^3.*(8.*x.*z.*(x - 1).*(12.*x.^2 - 24.*x + 12) - 48.*x.^3.*z.^2.*(x - 1) + 8.*x.*z.^4.*(2.*x - 2.*x.^2).*(x - 1)) + y.^4.*(8.*x.*(x - 1).*(- 4.*x.^4 + 12.*x.^3 - 12.*x.^2 + 4.*x).*z.^3 + 8.*x.*(x - 1).*(4.*x.^4 - 8.*x.^3 + 4.*x.^2).*z) - 24.*x.*y.*z.^2.*(x - 1) - 8.*x.*y.^2.*z.*(x - 1).*(6.*x.^2 - 12.*x + 6))./w.^3) .* (y<0.5) + ...
%! ((8.*z.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x) - y.*(72.*x.*(x - 1).*z.^2 + 8.*(x - 1).*(4.*x.^3 - 8.*x.^2 + 4.*x).*z) + 48.*x.*z.^2.*(x - 1) + 8.*y.^2.*z.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x))./w.^2 - (2.*(y.^2.*(4.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x).*z.^2 + 4.*(2.*x.^2 - 2.*x.^3).*(x - 1)) - 4.*(x - 1).*(2.*x.^3 - 2.*x.^2 + x - 1) - y.*(24.*x.*(x - 1).*z.^3 + 4.*(x - 1).*(4.*x.^3 - 8.*x.^2 + 4.*x).*z.^2 - 4.*(x - 1).*(4.*x.^3 - 4.*x.^2 + x - 1)) + 16.*x.*z.^3.*(x - 1) + 4.*z.^2.*(x - 1).*(2.*x.^3 - 4.*x.^2 + 2.*x)).*(- 12.*z.*x.^2.*y.^2 + 16.*z.*x.^2.*y - 4.*z.*x.^2 + 12.*z.*x.*y.^2 - 16.*z.*x.*y + 4.*z.*x))./(-w).^3) .* (y>0.5);
%! d2Fdww = zeros ([3, size(x)]);
%! d2Fdww(1,:,:,:) = ((32.*x.*y.^2.*(2.*x.^2.*y.^2 + 1).*(x - 1).*(5.*x + z + 10.*x.^2.*y.^2 + 2.*x.^2.*y.^2.*z))./(5.*w.^3) - (8.*x.*y.^2.*(x - 1).*(15.*x + z + 30.*x.^2.*y.^2 + 2.*x.^2.*y.^2.*z))/5./w.^2) .* (y<0.5) + ...
%! (((8.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(36.*x.^4.*y.^4 - 96.*x.^4.*y.^3 + 88.*x.^4.*y.^2 - 32.*x.^4.*y + 4.*x.^4 - 36.*x.^3.*y.^4 + 96.*x.^3.*y.^3 - 88.*x.^3.*y.^2 + 32.*x.^3.*y - 4.*x.^3 - 6.*x.^2.*y.^2 + 8.*x.^2.*y - 2.*x.^2 + 6.*x.*y.^2 - 8.*x.*y + 2.*x).*z.^3)/5 + (8.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(540.*x.^4.*y.^4 - 1440.*x.^4.*y.^3 + 1320.*x.^4.*y.^2 - 480.*x.^4.*y + 60.*x.^4 - 540.*x.^3.*y.^4 + 1440.*x.^3.*y.^3 - 1410.*x.^3.*y.^2 + 600.*x.^3.*y - 90.*x.^3 + 90.*x.^2.*y.^2 - 120.*x.^2.*y + 30.*x.^2).*z.^2)/5 + (8.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(108.*x.^4.*y.^4 - 288.*x.^4.*y.^3 + 264.*x.^4.*y.^2 - 96.*x.^4.*y + 12.*x.^4 - 36.*x.^2.*y.^2 + 48.*x.^2.*y - 12.*x.^2 + 3).*z)/5 + (8.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(180.*x.^4.*y.^4 - 480.*x.^4.*y.^3 + 440.*x.^4.*y.^2 - 160.*x.^4.*y + 20.*x.^4 - 30.*x.^3.*y.^2 + 40.*x.^3.*y - 10.*x.^3 - 30.*x.^2.*y.^2 + 40.*x.^2.*y - 10.*x.^2 + 5.*x))/5)./(-w).^3) .* (y>0.5);
%! d2Fdww(2,:,:,:) = ((16.*x.*y.^2.*(2.*x.^2.*y.^2 + 1).*(x - 1).*(20.*y + 3.*z + 20.*x.^2.*y.^2 - 10.*y.^2 + 6.*x.^2.*y.^2.*z))./(5.*w.^3) - (12.*x.*y.^2.*(x - 1).*(20.*y + z + 20.*x.^2.*y.^2 - 10.*y.^2 + 2.*x.^2.*y.^2.*z))/5./w.^2) .* (y<0.5) + ...
%! (((4.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(108.*x.^4.*y.^4 - 288.*x.^4.*y.^3 + 264.*x.^4.*y.^2 - 96.*x.^4.*y + 12.*x.^4 - 108.*x.^3.*y.^4 + 288.*x.^3.*y.^3 - 264.*x.^3.*y.^2 + 96.*x.^3.*y - 12.*x.^3 - 18.*x.^2.*y.^2 + 24.*x.^2.*y - 6.*x.^2 + 18.*x.*y.^2 - 24.*x.*y + 6.*x).*z.^3)/5 + (4.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(1080.*x.^4.*y.^4 - 2880.*x.^4.*y.^3 + 2640.*x.^4.*y.^2 - 960.*x.^4.*y + 120.*x.^4 - 1080.*x.^3.*y.^4 + 2880.*x.^3.*y.^3 - 2640.*x.^3.*y.^2 + 960.*x.^3.*y - 120.*x.^3 - 180.*x.^2.*y.^4 + 240.*x.^2.*y.^3 - 150.*x.^2.*y.^2 + 120.*x.^2.*y - 30.*x.^2 + 180.*x.*y.^4 - 240.*x.*y.^3 + 150.*x.*y.^2 - 120.*x.*y + 30.*x).*z.^2)/5 + (4.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(324.*x.^4.*y.^4 - 864.*x.^4.*y.^3 + 792.*x.^4.*y.^2 - 288.*x.^4.*y + 36.*x.^4 - 108.*x.^2.*y.^2 + 144.*x.^2.*y - 36.*x.^2 + 9).*z)/5 + (4.*x.*(3.*y - 1).*(x - 1).*(y - 1).*(360.*x.^4.*y.^4 - 960.*x.^4.*y.^3 + 880.*x.^4.*y.^2 - 320.*x.^4.*y + 40.*x.^4 - 60.*x.^2.*y.^4 + 80.*x.^2.*y.^3 - 110.*x.^2.*y.^2 + 120.*x.^2.*y - 30.*x.^2 + 10.*y.^2 + 5))/5)./(-w).^3) .* (y>0.5);
%! d2Fdww(3,:,:,:) = ((32.*x.*y.^2.*(2.*x.^2.*y.^2 + 1).*(x - 1).*(2.*y + z - 3.*x.^2.*y.^2 - 4.*x.*y + 6.*x.*y.^2 + 2.*x.^2.*y - 3.*y.^2 + 2.*x.^2.*y.^2.*z))./w.^3 - (8.*x.*y.^2.*(x - 1).*(6.*y + z - 9.*x.^2.*y.^2 - 12.*x.*y + 18.*x.*y.^2 + 6.*x.^2.*y - 9.*y.^2 + 2.*x.^2.*y.^2.*z))./w.^2) .* (y<0.5) + ...
%! ((2.*(- 6.*x.^2.*y.^2 + 8.*x.^2.*y - 2.*x.^2 + 6.*x.*y.^2 - 8.*x.*y + 2.*x).*(2.*z - 4.*y - 4.*x + 2.*x.^2.*y.^2 + 8.*x.*y - 4.*x.*y.^2 - 4.*x.^2.*y - 4.*x.^2.*z + 2.*x.^2 + 2.*y.^2 + 16.*x.^2.*y.*z - 12.*x.^2.*y.^2.*z + 2))./w.^2 - (8.*z.^2.*(- 6.*x.^2.*y.^2 + 8.*x.^2.*y - 2.*x.^2 + 6.*x.*y.^2 - 8.*x.*y + 2.*x).^2.*(2.*z - 4.*y - 4.*x + 2.*x.^2.*y.^2 + 8.*x.*y - 4.*x.*y.^2 - 4.*x.^2.*y - 4.*x.^2.*z + 2.*x.^2 + 2.*y.^2 + 16.*x.^2.*y.*z - 12.*x.^2.*y.^2.*z + 2))./(-w).^3 - (4.*z.*(12.*x.^2.*y.^2 - 16.*x.^2.*y + 4.*x.^2 - 2).*(- 6.*x.^2.*y.^2 + 8.*x.^2.*y - 2.*x.^2 + 6.*x.*y.^2 - 8.*x.*y + 2.*x))./w.^2) .* (y>0.5);
%! assert (F, pnt, 1e3*eps)
%! assert (dFdu, jac{1}, 1e3*eps)
%! assert (dFdv, jac{2}, 1e3*eps)
%! assert (dFdw, jac{3}, 1e3*eps)
%! assert (d2Fduu, hess{1,1}, 1e3*eps)
%! assert (d2Fduv, hess{1,2}, 1e3*eps)
%! assert (d2Fduw, hess{1,3}, 1e3*eps)
%! assert (d2Fduv, hess{2,1}, 1e3*eps)
%! assert (d2Fdvv, hess{2,2}, 1e3*eps)
%! assert (d2Fdvw, hess{2,3}, 1e3*eps)
%! assert (d2Fduw, hess{3,1}, 1e3*eps)
%! assert (d2Fdvw, hess{3,2}, 1e3*eps)
%! assert (d2Fdww, hess{3,3}, 1e3*eps)
%!test
%! nrb = nrbextrude (nrb4surf ([0 0], [1 0], [0 1], [1 1]), [0 0 1]);
%! nrb = nrbdegelev (nrb, [1 1 1]);
%! nrb.coefs (4,2,2,2) = 1.1;
%! [dnrb, dnrb2] = nrbderiv (nrb);
%! X = linspace (0, 1, 24); Y = linspace (0, 1, 24); Z = linspace (0, 1, 24);
%! [pnt, jac, hess] = nrbdeval (nrb, dnrb, dnrb2, {X Y Z});
%! [y, x, z] = meshgrid (X, Y, Z);
%! F = zeros ([3, size(x)]);
%! F(1,:,:,:) = (5.*x)./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5);
%! F(2,:,:,:) = (5.*y)./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5);
%! F(3,:,:,:) = (5.*z)./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5);
%! dFdu = zeros ([3, size(x)]);
%! dFdu(1,:,:,:) = ((z.*(20.*y - 20.*y.^2) - z.^2.*(20.*y - 20.*y.^2)).*x.^2 + 25)./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^2;
%! dFdu(2,:,:,:) = (y.^2.*(5.*z.*(8.*x - 4) - 5.*z.^2.*(8.*x - 4)) - y.^3.*(5.*z.*(8.*x - 4) - 5.*z.^2.*(8.*x - 4)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdu(3,:,:,:) = (z.^2.*(5.*y.*(8.*x - 4) - 5.*y.^2.*(8.*x - 4)) - z.^3.*(5.*y.*(8.*x - 4) - 5.*y.^2.*(8.*x - 4)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdv = zeros ([3, size(x)]);
%! dFdv(1,:,:,:) = (x.^2.*(5.*z.*(8.*y - 4) - 5.*z.^2.*(8.*y - 4)) - x.^3.*(5.*z.*(8.*y - 4) - 5.*z.^2.*(8.*y - 4)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdv(2,:,:,:) = ((z.*(20.*x - 20.*x.^2) - z.^2.*(20.*x - 20.*x.^2)).*y.^2 + 25)./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^2;
%! dFdv(3,:,:,:) = (z.^2.*(5.*x.*(8.*y - 4) - 5.*x.^2.*(8.*y - 4)) - z.^3.*(5.*x.*(8.*y - 4) - 5.*x.^2.*(8.*y - 4)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdw = zeros ([3, size(x)]);
%! dFdw(1,:,:,:) = (x.^2.*(y.*(40.*z - 20) - y.^2.*(40.*z - 20)) - x.^3.*(y.*(40.*z - 20) - y.^2.*(40.*z - 20)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdw(2,:,:,:) = (y.^2.*(x.*(40.*z - 20) - x.^2.*(40.*z - 20)) - y.^3.*(x.*(40.*z - 20) - x.^2.*(40.*z - 20)))./((- 4.*x.^2.*y.^2 + 4.*x.^2.*y + 4.*x.*y.^2 - 4.*x.*y).*z.^2 + (4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y).*z + 5).^2;
%! dFdw(3,:,:,:) = ((y.*(20.*x - 20.*x.^2) - y.^2.*(20.*x - 20.*x.^2)).*z.^2 + 25)./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^2;
%! d2Fduu = zeros ([3, size(x)]);
%! d2Fduu(1,:,:,:) = (40.*y.*z.*(y - 1).*(z - 1).*(4.*x.^3.*y.^2.*z.^2 - 4.*x.^3.*y.^2.*z - 4.*x.^3.*y.*z.^2 + 4.*x.^3.*y.*z + 15.*x - 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduu(2,:,:,:) = (40.*y.^2.*z.*(y - 1).*(z - 1).*(4.*y.^2.*z.^2 - 4.*y.^2.*z - 4.*y.*z.^2 + 4.*y.*z + 5) - 40.*x.*y.^2.*z.*(y - 1).*(z - 1).*(12.*y.^2.*z.^2 - 12.*y.^2.*z - 12.*y.*z.^2 + 12.*y.*z) + 40.*x.^2.*y.^2.*z.*(y - 1).*(z - 1).*(12.*y.^2.*z.^2 - 12.*y.^2.*z - 12.*y.*z.^2 + 12.*y.*z))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduu(3,:,:,:) = (40.*y.*z.^2.*(y - 1).*(z - 1).*(4.*y.^2.*z.^2 - 4.*y.^2.*z - 4.*y.*z.^2 + 4.*y.*z + 5) - 40.*x.*y.*z.^2.*(y - 1).*(z - 1).*(12.*y.^2.*z.^2 - 12.*y.^2.*z - 12.*y.*z.^2 + 12.*y.*z) + 40.*x.^2.*y.*z.^2.*(y - 1).*(z - 1).*(12.*y.^2.*z.^2 - 12.*y.^2.*z - 12.*y.*z.^2 + 12.*y.*z))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduv = zeros ([3, size(x)]);
%! d2Fduv(1,:,:,:) = (20.*x.*z.*(2.*y - 1).*(z - 1).*(4.*x.^3.*y.^2.*z.^2 - 4.*x.^3.*y.^2.*z - 4.*x.^3.*y.*z.^2 + 4.*x.^3.*y.*z - 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 15.*x - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduv(2,:,:,:) = (20.*y.*z.*(2.*x - 1).*(z - 1).*(4.*x.^2.*y.^3.*z.^2 - 4.*x.^2.*y.^3.*z - 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z - 4.*x.*y.^3.*z.^2 + 4.*x.*y.^3.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z + 15.*y - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduv(3,:,:,:) = (20.*z.^2.*(2.*x - 1).*(2.*y - 1).*(z - 1).*(4.*x.^2.*y.^2.*z.^2 - 4.*x.^2.*y.^2.*z - 4.*x.^2.*y.*z.^2 + 4.*x.^2.*y.*z - 4.*x.*y.^2.*z.^2 + 4.*x.*y.^2.*z + 4.*x.*y.*z.^2 - 4.*x.*y.*z + 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduw = zeros ([3, size(x)]);
%! d2Fduw(1,:,:,:) = (20.*x.*y.*(2.*z - 1).*(y - 1).*(4.*x.^3.*y.^2.*z.^2 - 4.*x.^3.*y.^2.*z - 4.*x.^3.*y.*z.^2 + 4.*x.^3.*y.*z - 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 15.*x - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduw(2,:,:,:) = (20.*y.^2.*(2.*x - 1).*(2.*z - 1).*(y - 1).*(4.*x.^2.*y.^2.*z.^2 - 4.*x.^2.*y.^2.*z - 4.*x.^2.*y.*z.^2 + 4.*x.^2.*y.*z - 4.*x.*y.^2.*z.^2 + 4.*x.*y.^2.*z + 4.*x.*y.*z.^2 - 4.*x.*y.*z + 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fduw(3,:,:,:) = (20.*y.*z.*(2.*x - 1).*(y - 1).*(4.*x.^2.*y.^2.*z.^3 - 4.*x.^2.*y.^2.*z.^2 - 4.*x.^2.*y.*z.^3 + 4.*x.^2.*y.*z.^2 - 4.*x.*y.^2.*z.^3 + 4.*x.*y.^2.*z.^2 + 4.*x.*y.*z.^3 - 4.*x.*y.*z.^2 + 15.*z - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvv = zeros ([3, size(x)]);
%! d2Fdvv(1,:,:,:) = (40.*x.^2.*z.*(x - 1).*(z - 1).*(4.*x.^2.*z.^2 - 4.*x.^2.*z - 4.*x.*z.^2 + 4.*x.*z + 5) + 40.*x.^2.*y.^2.*z.*(x - 1).*(z - 1).*(12.*x.^2.*z.^2 - 12.*x.^2.*z - 12.*x.*z.^2 + 12.*x.*z) - 40.*x.^2.*y.*z.*(x - 1).*(z - 1).*(12.*x.^2.*z.^2 - 12.*x.^2.*z - 12.*x.*z.^2 + 12.*x.*z))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvv(2,:,:,:) = (40.*x.*z.*(x - 1).*(z - 1).*(4.*x.^2.*y.^3.*z.^2 - 4.*x.^2.*y.^3.*z - 4.*x.*y.^3.*z.^2 + 4.*x.*y.^3.*z + 15.*y - 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvv(3,:,:,:) = (40.*x.*z.^2.*(x - 1).*(z - 1).*(4.*x.^2.*z.^2 - 4.*x.^2.*z - 4.*x.*z.^2 + 4.*x.*z + 5) + 40.*x.*y.^2.*z.^2.*(x - 1).*(z - 1).*(12.*x.^2.*z.^2 - 12.*x.^2.*z - 12.*x.*z.^2 + 12.*x.*z) - 40.*x.*y.*z.^2.*(x - 1).*(z - 1).*(12.*x.^2.*z.^2 - 12.*x.^2.*z - 12.*x.*z.^2 + 12.*x.*z))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvw = zeros ([3, size(x)]);
%! d2Fdvw(1,:,:,:) = (20.*x.^2.*(2.*y - 1).*(2.*z - 1).*(x - 1).*(4.*x.^2.*y.^2.*z.^2 - 4.*x.^2.*y.^2.*z - 4.*x.^2.*y.*z.^2 + 4.*x.^2.*y.*z - 4.*x.*y.^2.*z.^2 + 4.*x.*y.^2.*z + 4.*x.*y.*z.^2 - 4.*x.*y.*z + 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvw(2,:,:,:) = (20.*x.*y.*(2.*z - 1).*(x - 1).*(4.*x.^2.*y.^3.*z.^2 - 4.*x.^2.*y.^3.*z - 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z - 4.*x.*y.^3.*z.^2 + 4.*x.*y.^3.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z + 15.*y - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdvw(3,:,:,:) = (20.*x.*z.*(2.*y - 1).*(x - 1).*(4.*x.^2.*y.^2.*z.^3 - 4.*x.^2.*y.^2.*z.^2 - 4.*x.^2.*y.*z.^3 + 4.*x.^2.*y.*z.^2 - 4.*x.*y.^2.*z.^3 + 4.*x.*y.^2.*z.^2 + 4.*x.*y.*z.^3 - 4.*x.*y.*z.^2 + 15.*z - 10))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdww = zeros ([3, size(x)]);
%! d2Fdww(1,:,:,:) = (40.*x.^2.*y.*(x - 1).*(y - 1).*(4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y + 5) + 40.*x.^2.*y.*z.^2.*(x - 1).*(y - 1).*(12.*x.^2.*y.^2 - 12.*x.^2.*y - 12.*x.*y.^2 + 12.*x.*y) - 40.*x.^2.*y.*z.*(x - 1).*(y - 1).*(12.*x.^2.*y.^2 - 12.*x.^2.*y - 12.*x.*y.^2 + 12.*x.*y))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdww(2,:,:,:) = (40.*x.*y.^2.*(x - 1).*(y - 1).*(4.*x.^2.*y.^2 - 4.*x.^2.*y - 4.*x.*y.^2 + 4.*x.*y + 5) + 40.*x.*y.^2.*z.^2.*(x - 1).*(y - 1).*(12.*x.^2.*y.^2 - 12.*x.^2.*y - 12.*x.*y.^2 + 12.*x.*y) - 40.*x.*y.^2.*z.*(x - 1).*(y - 1).*(12.*x.^2.*y.^2 - 12.*x.^2.*y - 12.*x.*y.^2 + 12.*x.*y))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
%! d2Fdww(3,:,:,:) = (40.*x.*y.*(x - 1).*(y - 1).*(4.*x.^2.*y.^2.*z.^3 - 4.*x.^2.*y.*z.^3 - 4.*x.*y.^2.*z.^3 + 4.*x.*y.*z.^3 + 15.*z - 5))./(- 4.*x.^2.*y.^2.*z.^2 + 4.*x.^2.*y.^2.*z + 4.*x.^2.*y.*z.^2 - 4.*x.^2.*y.*z + 4.*x.*y.^2.*z.^2 - 4.*x.*y.^2.*z - 4.*x.*y.*z.^2 + 4.*x.*y.*z + 5).^3;
nurbs-1.3.13/inst/PaxHeaders.26136/nrbcoons.m 0000644 0000000 0000000 00000000132 13070134113 015435 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbcoons.m 0000644 0001750 0001750 00000013021 13070134113 015610 0 ustar 00bect bect 0000000 0000000 function srf = nrbcoons(u1, u2, v1, v2)
%
% NRBCOONS: Construction of a Coons patch.
%
% Calling Sequence:
%
% srf = nrbcoons(ucrv1, ucrv2, vcrv1, vcrv2)
%
% INPUT:
%
% ucrv1 : NURBS curve defining the bottom U direction boundary of
% the constructed NURBS surface.
%
% ucrv2 : NURBS curve defining the top U direction boundary of
% the constructed NURBS surface.
%
% vcrv1 : NURBS curve defining the bottom V direction boundary of
% the constructed NURBS surface.
%
% vcrv2 : NURBS curve defining the top V direction boundary of
% the constructed NURBS surface.
%
% OUTPUT:
%
% srf : Coons NURBS surface patch.
%
% Description:
%
% Construction of a bilinearly blended Coons surface patch from four NURBS
% curves that define the boundary.
%
% The orientation of the four NURBS boundary curves.
%
% ^ V direction
% |
% | ucrv2
% ------->--------
% | |
% | |
% vcrv1 ^ Surface ^ vcrv2
% | |
% | |
% ------->-----------> U direction
% ucrv1
%
%
% Examples:
%
% // Define four NURBS curves and construct a Coons surface patch.
% pnts = [ 0.0 3.0 4.5 6.5 8.0 10.0;
% 0.0 0.0 0.0 0.0 0.0 0.0;
% 2.0 2.0 7.0 4.0 7.0 9.0];
% crv1 = nrbmak(pnts, [0 0 0 1/3 0.5 2/3 1 1 1]);
%
% pnts= [ 0.0 3.0 5.0 8.0 10.0;
% 10.0 10.0 10.0 10.0 10.0;
% 3.0 5.0 8.0 6.0 10.0];
% crv2 = nrbmak(pnts, [0 0 0 1/3 2/3 1 1 1]);
%
% pnts= [ 0.0 0.0 0.0 0.0;
% 0.0 3.0 8.0 10.0;
% 2.0 0.0 5.0 3.0];
% crv3 = nrbmak(pnts, [0 0 0 0.5 1 1 1]);
%
% pnts= [ 10.0 10.0 10.0 10.0 10.0;
% 0.0 3.0 5.0 8.0 10.0;
% 9.0 7.0 7.0 10.0 10.0];
% crv4 = nrbmak(pnts, [0 0 0 0.25 0.75 1 1 1]);
%
% srf = nrbcoons(crv1, crv2, crv3, crv4);
% nrbplot(srf,[20 20],220,45);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin ~= 4
error('Incorrect number of input arguments');
end
if (max (abs (nrbeval (u1, u1.knots(1)) - nrbeval (v1, v1.knots(1)))) > 1e-10 || ...
max (abs (nrbeval (u1, u1.knots(end)) - nrbeval (v2, v2.knots(1)))) > 1e-10 || ...
max (abs (nrbeval (u2, u2.knots(1)) - nrbeval (v1, v1.knots(end)))) > 1e-10 || ...
max (abs (nrbeval (u2, u2.knots(end)) - nrbeval (v2, v2.knots(end)))) > 1e-10)
error ('The four curves do not define a closed boundary')
end
r1 = nrbruled(u1, u2);
r2 = nrbtransp(nrbruled(v1, v2));
t = nrb4surf(u1.coefs(:,1), u1.coefs(:,end), u2.coefs(:,1), u2.coefs(:,end));
% raise all surfaces to a common degree
du = max([r1.order(1), r2.order(1), t.order(1)]);
dv = max([r1.order(2), r2.order(2), t.order(2)]);
r1 = nrbdegelev(r1, [du - r1.order(1), dv - r1.order(2)]);
r2 = nrbdegelev(r2, [du - r2.order(1), dv - r2.order(2)]);
t = nrbdegelev(t, [du - t.order(1), dv - t.order(2)]);
% merge the knot vectors, to obtain a common knot vector
% U knots
k1 = r1.knots{1};
k2 = r2.knots{1};
k3 = t.knots{1};
k = unique([k1 k2 k3]);
n = length(k);
kua = [];
kub = [];
kuc = [];
for i = 1:n
i1 = length(find(k1 == k(i)));
i2 = length(find(k2 == k(i)));
i3 = length(find(k3 == k(i)));
m = max([i1, i2, i3]);
kua = [kua k(i)*ones(1,m-i1)];
kub = [kub k(i)*ones(1,m-i2)];
kuc = [kuc k(i)*ones(1,m-i3)];
end
% V knots
k1 = r1.knots{2};
k2 = r2.knots{2};
k3 = t.knots{2};
k = unique([k1 k2 k3]);
n = length(k);
kva = [];
kvb = [];
kvc = [];
for i = 1:n
i1 = length(find(k1 == k(i)));
i2 = length(find(k2 == k(i)));
i3 = length(find(k3 == k(i)));
m = max([i1, i2, i3]);
kva = [kva k(i)*ones(1,m-i1)];
kvb = [kvb k(i)*ones(1,m-i2)];
kvc = [kvc k(i)*ones(1,m-i3)];
end
r1 = nrbkntins(r1, {kua, kva});
r2 = nrbkntins(r2, {kub, kvb});
t = nrbkntins(t, {kuc, kvc});
% combine coefficient to construct Coons surface
coefs(1,:,:) = r1.coefs(1,:,:) + r2.coefs(1,:,:) - t.coefs(1,:,:);
coefs(2,:,:) = r1.coefs(2,:,:) + r2.coefs(2,:,:) - t.coefs(2,:,:);
coefs(3,:,:) = r1.coefs(3,:,:) + r2.coefs(3,:,:) - t.coefs(3,:,:);
coefs(4,:,:) = r1.coefs(4,:,:) + r2.coefs(4,:,:) - t.coefs(4,:,:);
srf = nrbmak(coefs, r1.knots);
end
%!demo
%! pnts = [ 0.0 3.0 4.5 6.5 8.0 10.0;
%! 0.0 0.0 0.0 0.0 0.0 0.0;
%! 2.0 2.0 7.0 4.0 7.0 9.0];
%! crv1 = nrbmak(pnts, [0 0 0 1/3 0.5 2/3 1 1 1]);
%!
%! pnts= [ 0.0 3.0 5.0 8.0 10.0;
%! 10.0 10.0 10.0 10.0 10.0;
%! 3.0 5.0 8.0 6.0 10.0];
%! crv2 = nrbmak(pnts, [0 0 0 1/3 2/3 1 1 1]);
%!
%! pnts= [ 0.0 0.0 0.0 0.0;
%! 0.0 3.0 8.0 10.0;
%! 2.0 0.0 5.0 3.0];
%! crv3 = nrbmak(pnts, [0 0 0 0.5 1 1 1]);
%!
%! pnts= [ 10.0 10.0 10.0 10.0 10.0;
%! 0.0 3.0 5.0 8.0 10.0;
%! 9.0 7.0 7.0 10.0 10.0];
%! crv4 = nrbmak(pnts, [0 0 0 0.25 0.75 1 1 1]);
%!
%! srf = nrbcoons(crv1, crv2, crv3, crv4);
%!
%! nrbplot(srf,[20 20]);
%! title('Construction of a bilinearly blended Coons surface.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/nrbnumbasisfun.m 0000644 0000000 0000000 00000000132 13070134113 016646 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbnumbasisfun.m 0000644 0001750 0001750 00000010666 13070134113 017035 0 ustar 00bect bect 0000000 0000000 function idx = nrbnumbasisfun (points, nrb)
%
% NRBNUMBASISFUN: Numbering of basis functions for NURBS
%
% Calling Sequence:
%
% N = nrbnumbasisfun (u, crv)
% N = nrbnumbasisfun ({u, v}, srf)
% N = nrbnumbasisfun (p, srf)
% N = nrbnumbasisfun ({u, v, w}, vol)
% N = nrbnumbasisfun (p, vol)
%
% INPUT:
%
% u or p(1,:,:) - parametric points along u direction
% v or p(2,:,:) - parametric points along v direction
% w or p(3,:,:) - parametric points along w direction
% crv - NURBS curve
% srf - NURBS surface
% vol - NURBS volume
%
% OUTPUT:
%
% N - Indices of the basis functions that are nonvanishing at each
% point. size(N) == [npts, prod(nrb.order)]
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if ( (nargin<2) ...
|| (nargout>1) ...
|| (~isstruct(nrb)) ...
|| (iscell(points) && ~iscell(nrb.knots)) ...
|| (~iscell(points) && iscell(nrb.knots) && (size(points,1)~=numel(nrb.number))) ...
)
error('Incorrect input arguments in nrbnumbasisfun');
end
if (~iscell(nrb.knots)) %% NURBS curve
iv = findspan (nrb.number-1, nrb.order-1, points, nrb.knots);
idx = numbasisfun (iv, points, nrb.order-1, nrb.knots);
else
ndim = numel (nrb.number);
if (iscell (points))
for idim = 1:ndim
pts_dim = points{idim};
sp{idim} = findspan (nrb.number(idim)-1, nrb.order(idim)-1, pts_dim, nrb.knots{idim});
% N{idim} = basisfun(sp{idim}, pts_dim, nrb.order(idim)-1, nrb.knots{idim});
num{idim} = numbasisfun (sp{idim}, pts_dim, nrb.order(idim)-1, nrb.knots{idim}) + 1;
end
npts_dim = cellfun (@numel, points);
cumnpts = cumprod([1 npts_dim]);
npts = prod (npts_dim);
numaux = 1;
cumorder = cumprod ([1 nrb.order]);
cumnumber = cumprod ([1 nrb.number]);
for idim = 1:ndim
num_dim = reshape (num{idim}, 1, npts_dim(idim), 1, nrb.order(idim));
num_dim = repmat (num_dim, cumnpts(idim), 1, cumorder(idim), 1);
num_prev = reshape (numaux, cumnpts(idim), 1, cumorder(idim), 1);
num_prev = repmat (num_prev, 1, npts_dim(idim), 1, nrb.order(idim));
numaux = sub2ind ([cumnumber(idim) nrb.number(idim)], num_prev, num_dim);
numaux = reshape (numaux, cumnpts(idim+1), cumorder(idim+1));
end
idx = reshape (numaux, npts, prod (nrb.order));
else
for idim = 1:ndim
pts_dim = points(idim,:);
sp{idim} = findspan (nrb.number(idim)-1, nrb.order(idim)-1, pts_dim, nrb.knots{idim});
% N{idim} = basisfun(sp{idim}, pts_dim, nrb.order(idim)-1, nrb.knots{idim});
num{idim} = numbasisfun (sp{idim}, pts_dim, nrb.order(idim)-1, nrb.knots{idim}) + 1;
end
npts = numel (points(1,:));
idx = zeros (npts, prod(nrb.order));
local_num = cell (ndim, 1);
for ipt = 1:npts
for idim = 1:ndim
local_num{idim} = num{idim}(ipt,:);
end
[local_num{:}] = ndgrid (local_num{:});
idx(ipt,:) = reshape (sub2ind (nrb.number, local_num{:}), 1, size(idx, 2));
end
end
end
end
%!test
%! p = 2; q = 3; m = 4; n = 5;
%! Lx = 1; Ly = 1;
%! nrb = nrb4surf ([0 0], [1 0], [0 1], [1 1]);
%! nrb = nrbdegelev (nrb, [p-1, q-1]);
%! ikx = linspace(0,1,m); iky = linspace(0,1,n);
%! nrb = nrbkntins (nrb, {ikx(2:end-1), iky(2:end-1)});
%! nrb.coefs (4,:,:) = nrb.coefs (4,:,:) + rand (size (nrb.coefs (4,:,:)));
%! u = rand (1, 30); v = rand (1, 10);
%! u = (u-min (u))/max (u-min (u));
%! v = (v-min (v))/max (v-min (v));
%! N = nrbnumbasisfun ({u, v}, nrb);
%! assert (all (all (N>0)), true)
%! assert (all (all (N <= prod (nrb.number))), true)
%! assert (max (max (N)), prod (nrb.number))
%! assert (min (min (N)), 1) nurbs-1.3.13/inst/PaxHeaders.26136/findspan.m 0000644 0000000 0000000 00000000126 13070134113 015417 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/findspan.m 0000644 0001750 0001750 00000003476 13070134113 015604 0 ustar 00bect bect 0000000 0000000 function s = findspan(n,p,u,U)
% FINDSPAN Find the span of a B-Spline knot vector at a parametric point
%
% Calling Sequence:
%
% s = findspan(n,p,u,U)
%
% INPUT:
%
% n - number of control points - 1
% p - spline degree
% u - parametric point
% U - knot sequence
%
% OUTPUT:
%
% s - knot span index
%
% Modification of Algorithm A2.1 from 'The NURBS BOOK' pg68
%
% Copyright (C) 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (max(u(:))>U(end) || min(u(:))= U,1,'last')-1;
end
end
%!test
%! n = 3;
%! U = [0 0 0 1/2 1 1 1];
%! p = 2;
%! u = linspace(0, 1, 10);
%! s = findspan (n, p, u, U);
%! assert (s, [2*ones(1, 5) 3*ones(1, 5)]);
%!test
%! p = 2; m = 7; n = m - p - 1;
%! U = [zeros(1,p) linspace(0,1,m+1-2*p) ones(1,p)];
%! u = [ 0 0.11880 0.55118 0.93141 0.40068 0.35492 0.44392 0.88360 0.35414 0.92186 0.83085 1];
%! s = [2 2 3 4 3 3 3 4 3 4 4 4];
%! assert (findspan (n, p, u, U), s, 1e-10);
nurbs-1.3.13/inst/PaxHeaders.26136/surfderivcpts.m 0000644 0000000 0000000 00000000132 13070134113 016515 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/surfderivcpts.m 0000644 0001750 0001750 00000004540 13070134113 016676 0 ustar 00bect bect 0000000 0000000 function pkl = surfderivcpts (n, p, U, m, q, V, P, d, r1, r2, s1, s2)
%
% SURFDERIVCPTS: Compute control points of n-th derivatives of a NURBS surface.
%
% usage: pkl = surfderivcpts (n, p, U, m, q, V, P, d)
%
% INPUT:
%
% n+1, m+1 = number of control points
% p, q = spline order
% U, V = knots
% P = control points
% d = derivative order
%
% OUTPUT:
%
% pkl (k+1, l+1, i+1, j+1) = i,jth control point
% of the surface differentiated k
% times in the u direction and l
% times in the v direction
%
% Adaptation of algorithm A3.7 from the NURBS book, pg114
%
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin <= 8)
r1 = 0; r2 = n;
s1 = 0; s2 = m;
end
r = r2-r1;
s = s2-s1;
du = min (d, p); dv = min (d, q);
for j=s1:s2
temp = curvederivcpts (n, p, U, P(:,j+1:end), du, r1, r2);
for k=0:du
for i=0:r-k
pkl (k+1, 1, i+1, j-s1+1) = temp (k+1, i+1);
end
end
end
for k=0:du
for i=0:r-k
dd = min (d-k, dv);
temp = curvederivcpts (m, q, V(s1+1:end), pkl(k+1, 1, i+1, :), ...
dd, 0, s);
for l=1:dd
for j=0:s-l
pkl (k+1, l+1, i+1, j+1) = temp (l+1, j+1);
end
end
end
end
end
%!test
%! coefs = cat(3,[0 0; 0 1],[1 1; 0 1]);
%! knots = {[0 0 1 1] [0 0 1 1]};
%! plane = nrbmak(coefs,knots);
%! pkl = surfderivcpts (plane.number(1)-1, plane.order(1)-1,...
%! plane.knots{1}, plane.number(2)-1,...
%! plane.order(2)-1, plane.knots{2}, ...
%! squeeze (plane.coefs(1,:,:)), 1);
nurbs-1.3.13/inst/PaxHeaders.26136/vecangle.m 0000644 0000000 0000000 00000000132 13070134113 015376 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecangle.m 0000644 0001750 0001750 00000002702 13070134113 015555 0 ustar 00bect bect 0000000 0000000 function ang = vecangle(num,den)
%
% VECANGLE: An alternative to atan, returning an arctangent in the
% range 0 to 2*pi.
%
% Calling Sequence:
%
% ang = vecmag2(num,dum)
%
% INPUT:
%
% num : Numerator, vector of size (1,nv).
% dem : Denominator, vector of size (1,nv).
%
% OUTPUT:
% ang : Arctangents, row vector of angles.
%
% Description:
%
% The components of the vector ang are the arctangent of the corresponding
% enties of num./dem. This function is an alternative for
% atan, returning an angle in the range 0 to 2*pi.
%
% Examples:
%
% Find the atan(1.2,2.0) and atan(1.5,3.4) using vecangle
%
% ang = vecangle([1.2 1.5], [2.0 3.4]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
ang = atan2(num,den);
index = find(ang < 0.0);
ang(index) = 2*pi+ang(index);
end
nurbs-1.3.13/inst/PaxHeaders.26136/vecroty.m 0000644 0000000 0000000 00000000132 13070134113 015305 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecroty.m 0000644 0001750 0001750 00000003251 13070134113 015464 0 ustar 00bect bect 0000000 0000000 function ry = vecroty(angle)
%
% VECROTY: Transformation matrix for a rotation around the y axis.
%
% Calling Sequence:
%
% ry = vecroty(angle);
%
% INPUT:
%
% angle : rotation angle defined in radians
%
% OUTPUT:
%
% ry : (4x4) Transformation matrix.
%
%
% Description:
%
% Return the (4x4) Transformation matrix for a rotation about the y axis
% by the defined angle.
%
% The matrix is:
%
% [ cos(angle) 0 sin(angle) 0]
% [ 0 1 0 0]
% [ -sin(angle) 0 cos(angle) 0]
% [ 0 0 0 1]
%
% Examples:
%
% Rotate the NURBS line (0.0 0.0 0.0) - (3.0 3.0 3.0) by 45 degrees
% around the y-axis
%
% line = nrbline([0.0 0.0 0.0],[3.0 3.0 3.0]);
% trans = vecroty(%pi/4);
% rline = nrbtform(line, trans);
%
% See also:
%
% nrbtform
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
sn = sin(angle);
cn = cos(angle);
ry = [cn 0 sn 0; 0 1 0 0; -sn 0 cn 0; 0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/surfderiveval.m 0000644 0000000 0000000 00000000132 13070134113 016473 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/surfderiveval.m 0000644 0001750 0001750 00000005576 13070134113 016666 0 ustar 00bect bect 0000000 0000000 function skl = surfderiveval (n, p, U, m, q, V, P, u, v, d)
%
% SURFDERIVEVAL: Compute the derivatives of a B-spline surface.
%
% usage: skl = surfderiveval (n, p, U, m, q, V, P, u, v, d)
%
% INPUT:
%
% n+1, m+1 = number of control points
% p, q = spline order
% U, V = knots
% P = control points
% u,v = evaluation points
% d = derivative order
%
% OUTPUT:
%
% skl (k+1, l+1) = surface differentiated k
% times in the u direction and l
% times in the v direction
%
% Adaptation of algorithm A3.8 from the NURBS book, pg115
%
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
skl = zeros (d+1, d+1);
du = min (d, p);
dv = min (d, q);
uspan = findspan (n, p, u, U);
for ip=0:p
Nu(1:ip+1,ip+1) = basisfun (uspan, u, ip, U)';
end
vspan = findspan (m, q, v, V);
for ip=0:q
Nv(1:ip+1,ip+1) = basisfun (vspan, v, ip, V)';
end
pkl = surfderivcpts (n, p, U, m, q, V, P, d, uspan-p, uspan, ...
vspan-q, vspan);
for k = 0:du
dd = min (d-k, dv);
for l = 0:dd
skl(k+1,l+1) =0;
for i=0:q-l
tmp = 0;
for j = 0:p-k
tmp = tmp + Nu(j+1,p-k+1) * pkl(k+1,l+1,j+1,i+1);
end
skl(k+1,l+1) = skl(k+1,l+1) + Nv(i+1,q-l+1)*tmp;
end
end
end
end
%!shared srf
%!test
%! k = [0 0 0 1 1 1];
%! c = [0 1/2 1];
%! [coef(2,:,:), coef(1,:,:)] = meshgrid (c, c);
%! srf = nrbmak (coef, {k, k});
%! skl = surfderiveval (srf.number(1)-1, ...
%! srf.order(1)-1, ...
%! srf.knots{1}, ...
%! srf.number(2)-1, ...
%! srf.order(2)-1, ...
%! srf.knots{2},...
%! squeeze(srf.coefs(1,:,:)), .5, .5, 1) ;
%! assert (skl, [.5 0; 1 0])
%!test
%! srf = nrbkntins (srf, {[], rand(1,2)});
%! skl = surfderiveval (srf.number(1)-1,...
%! srf.order(1)-1, ...
%! srf.knots{1},...
%! srf.number(2)-1,...
%! srf.order(2)-1, ...
%! srf.knots{2},...
%! squeeze(srf.coefs(1,:,:)), .5, .5, 1) ;
%! assert (skl, [.5 0; 1 0], 100*eps)
nurbs-1.3.13/inst/PaxHeaders.26136/curvederivcpts.m 0000644 0000000 0000000 00000000126 13070134113 016665 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/curvederivcpts.m 0000644 0001750 0001750 00000003627 13070134113 017050 0 ustar 00bect bect 0000000 0000000 function pk = curvederivcpts (n, p, U, P, d, r1, r2)
% Compute control points of n-th derivatives of a B-spline curve.
%
% usage: pk = curvederivcpts (n, p, U, P, d)
% pk = curvederivcpts (n, p, U, P, d, r1, r2)
%
% If r1, r2 are not given, all the control points are computed.
%
% INPUT:
% n+1 = number of control points
% p = degree of the spline
% d = maximum derivative order (d<=p)
% U = knots
% P = control points
% r1 = first control point to compute
% r2 = auxiliary index for the last control point to compute
% OUTPUT:
% pk(k,i) = i-th control point of (k-1)-th derivative, r1 <= i <= r2-k
%
% Adaptation of algorithm A3.3 from the NURBS book, pg98.
%
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin <= 5)
r1 = 0;
r2 = n;
end
r = r2 - r1;
for i=0:r
pk(1, i+1) = P(r1+i+1);
end
for k=1:d
tmp = p - k + 1;
for i=0:r-k
pk (k+1, i+1) = tmp * (pk(k,i+2)-pk(k,i+1)) / ...
(U(r1+i+p+2)-U(r1+i+k+1));
end
end
end
%!test
%! line = nrbmak([0.0 1.5; 0.0 3.0],[0.0 0.0 1.0 1.0]);
%! pk = curvederivcpts (line.number-1, line.order-1, line.knots,...
%! line.coefs(1,:), 2);
%! assert (pk, [0 3/2; 3/2 0], 100*eps);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbctrlplot.m 0000644 0000000 0000000 00000000132 13070134113 016157 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbctrlplot.m 0000644 0001750 0001750 00000007505 13070134113 016344 0 ustar 00bect bect 0000000 0000000 function nrbctrlplot (nurbs)
% NRBCTRLPLOT: Plot a NURBS entity along with its control points.
%
% Calling Sequence:
%
% nrbctrlplot (nurbs)
%
% INPUT:
%
% nurbs: NURBS curve, surface or volume, see nrbmak.
%
% Example:
%
% Plot the test curve and test surface with their control polygon and
% control net, respectively
%
% nrbctrlplot(nrbtestcrv)
% nrbctrlplot(nrbtestsrf)
%
% See also:
%
% nrbkntplot
%
% Copyright (C) 2011, 2012 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin < 1)
error ('nrbctrlplot: Need a NURBS to plot!');
end
% Default values
light='on';
cmap='summer';
colormap (cmap);
hold_flag = ishold;
if (iscell (nurbs.knots))
if (size (nurbs.knots,2) == 3)
nsub = 100;
nrbplot (nurbs, [nsub nsub nsub], 'light', light, 'colormap', cmap);
hold on
% Plot the control points
coefs = bsxfun (@rdivide, nurbs.coefs(1:3,:,:,:), nurbs.coefs(4,:,:,:));
coefs = reshape (coefs, 3, []);
plot3 (coefs(1,:), coefs(2,:), coefs(3,:), 'r.','MarkerSize',20);
% Plot the control net
for ii = 1:size (nurbs.coefs, 2)
for jj = 1:size (nurbs.coefs, 3)
coefs = reshape (nurbs.coefs(1:3,ii,jj,:), 3, []);
weights = reshape (nurbs.coefs(4,ii,jj,:), 1, []);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
end
for kk = 1:size (nurbs.coefs, 4)
coefs = reshape (nurbs.coefs(1:3,ii,:,kk), 3, []);
weights = reshape (nurbs.coefs(4,ii,:,kk), 1, []);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
end
end
for jj = 1:size (nurbs.coefs, 3)
for kk = 1:size (nurbs.coefs, 4)
coefs = reshape (nurbs.coefs(1:3,:,jj,kk), 3, []);
weights = reshape (nurbs.coefs(4,:,jj,kk), 1, []);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
end
end
elseif (size (nurbs.knots,2) == 2) % plot a NURBS surface
nsub = 100;
nrbplot (nurbs, [nsub nsub], 'light', light, 'colormap', cmap);
hold on
% And plot the control net
for ii = 1:size (nurbs.coefs, 2)
coefs = reshape (nurbs.coefs(1:3,ii,:), 3, []);
weights = reshape (nurbs.coefs(4,ii,:), 1, []);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'r.','MarkerSize',20)
end
for jj = 1:size (nurbs.coefs, 3)
coefs = reshape (nurbs.coefs(1:3,:,jj), 3, []);
weights = reshape (nurbs.coefs(4,:,jj), 1, []);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'r.','MarkerSize',20)
end
end
else % plot a NURBS curve
nsub = 1000;
nrbplot (nurbs, nsub);
hold on
% And plot the control polygon
coefs = nurbs.coefs(1:3,:);
weights = nurbs.coefs(4,:);
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'k--')
plot3 (coefs(1,:)./weights, coefs(2,:)./weights, coefs(3,:)./weights,'r.','MarkerSize',20)
end
if (~hold_flag)
hold off
end
end
%!demo
%! crv = nrbtestcrv;
%! nrbctrlplot(crv)
%! title('Test curve')
%! hold off
%!demo
%! srf = nrbtestsrf;
%! nrbctrlplot(srf)
%! title('Test surface')
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/bspkntins.m 0000644 0000000 0000000 00000000126 13070134113 015630 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspkntins.m 0000644 0001750 0001750 00000013556 13070134113 016015 0 ustar 00bect bect 0000000 0000000 function [ic,ik,C] = bspkntins(d,c,k,u)
% BSPKNTINS: Insert knots into a B-Spline
%
% Calling Sequence:
%
% [ic,ik] = bspkntins(d,c,k,u)
%
% INPUT:
%
% d - spline degree integer
% c - control points double matrix(mc,nc)
% k - knot sequence double vector(nk)
% u - new knots double vector(nu)
%
% OUTPUT:
%
% ic - new control points double matrix(mc,nc+nu)
% ik - new knot sequence double vector(nk+nu)
%
% Modified version of Algorithm A5.4 from 'The NURBS BOOK' pg164.
%
% Copyright (C) 2000 Mark Spink, 2007 Daniel Claxton, 2010-2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
[mc,nc] = size(c);
u = sort(u);
nu = numel(u);
nk = numel(k);
%
% int bspkntins(int d, double *c, int mc, int nc, double *k, int nk,
% double *u, int nu, double *ic, double *ik)
% {
% int ierr = 0;
% int a, b, r, l, i, j, m, n, s, q, ind;
% double alfa;
%
% double **ctrl = vec2mat(c, mc, nc);
ic = zeros(mc,nc+nu); % double **ictrl = vec2mat(ic, mc, nc+nu);
ik = zeros(1,nk+nu);
%
n = nc - 1; % n = nc - 1;
r = nu - 1; % r = nu - 1;
%
m = n + d + 1; % m = n + d + 1;
a = findspan(n, d, u(1), k); % a = findspan(n, d, u[0], k);
b = findspan(n, d, u(r+1), k); % b = findspan(n, d, u[r], k);
b = b+1; % ++b;
%
% for (q = 0; q < mc; q++) {
ic(:,1:a-d+1) = c(:,1:a-d+1); % for (j = 0; j <= a-d; j++) ictrl[j][q] = ctrl[j][q];
ic(:,b+nu:nc+nu) = c(:,b:nc); % for (j = b-1; j <= n; j++) ictrl[j+r+1][q] = ctrl[j][q];
% }
ik(1:a+1) = k(1:a+1); % for (j = 0; j <= a; j++) ik[j] = k[j];
ik(b+d+nu+1:m+nu+1) = k(b+d+1:m+1); % for (j = b+d; j <= m; j++) ik[j+r+1] = k[j];
%
ii = b + d - 1; % i = b + d - 1;
ss = ii + nu; % s = b + d + r;
for jj=r:-1:0 % for (j = r; j >= 0; j--) {
ind = (a+1):ii; % while (u[j] <= k[i] && i > a) {
ind = ind(u(jj+1)<=k(ind+1)); % for (q = 0; q < mc; q++)
ic(:,ind+ss-ii-d) = c(:,ind-d); % ictrl[s-d-1][q] = ctrl[i-d-1][q];
ik(ind+ss-ii+1) = k(ind+1); % ik[s] = k[i];
ii = ii - numel(ind); % --i;
ss = ss - numel(ind); % --s;
% }
ic(:,ss-d) = ic(:,ss-d+1); % ictrl[s-d-1][q] = ictrl[s-d][q];
for l=1:d % for (l = 1; l <= d; l++) {
ind = ss - d + l; % ind = s - d + l;
alfa = ik(ss+l+1) - u(jj+1); % alfa = ik[s+l] - u[j];
if abs(alfa) == 0 % if (fabs(alfa) == 0.0)
ic(:,ind) = ic(:,ind+1); % for (q = 0; q < mc; q++)
% ictrl[ind-1][q] = ictrl[ind][q];
else % else {
alfa = alfa/(ik(ss+l+1) - k(ii-d+l+1)); % alfa /= (ik[s+l] - k[i-d+l]);
tmp = (1-alfa) * ic(:,ind+1); % for (q = 0; q < mc; q++)
ic(:,ind) = alfa*ic(:,ind) + tmp; % ictrl[ind-1][q] = alfa*ictrl[ind-1][q]+(1.0-alfa)*ictrl[ind][q];
end % }
end % }
%
ik(ss+1) = u(jj+1); % ik[s] = u[j];
ss = ss - 1;
end % }
%
% freevec2mat(ctrl);
% freevec2mat(ictrl);
%
% return ierr;
end % }
nurbs-1.3.13/inst/PaxHeaders.26136/nrbmodp.m 0000644 0000000 0000000 00000000132 13070134113 015253 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbmodp.m 0000644 0001750 0001750 00000002702 13070134113 015432 0 ustar 00bect bect 0000000 0000000 function mnrb = nrbmodp (nrb, move, index)
%
% NRBMODP: Modify the coordinates of specific control points of any NURBS
% map. The weight is not changed.
%
% Calling Sequence:
%
% nrb = nrbmodp (nrb, move, index);
%
% INPUT:
%
% nrb - NURBS map to be modified.
% move - vector specifying the displacement of all the ctrl points.
% index - indeces of the control points to be modified.
%
% OUTPUT:
%
% mnrb - the modified NURBS.
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
move = reshape (move, 3, 1);
mnrb = nrb;
[ii, jj, kk] = ind2sub (nrb.number, index);
for count = 1:numel (ii)
mnrb.coefs(1:3,ii(count),jj(count),kk(count)) = nrb.coefs(1:3,ii(count),jj(count),kk(count)) + ...
move * nrb.coefs(4,ii(count),jj(count),kk(count));
end
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbextrude.m 0000644 0000000 0000000 00000000132 13070134113 015774 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbextrude.m 0000644 0001750 0001750 00000005463 13070134113 016162 0 ustar 00bect bect 0000000 0000000 function srf = nrbextrude(curve,vector)
%
% NRBEXTRUDE: Construct a NURBS surface by extruding a NURBS curve, or
% construct a NURBS volume by extruding a NURBS surface.
%
% Calling Sequence:
%
% srf = nrbextrude(crv,vec);
%
% INPUT:
%
% crv : NURBS curve or surface to extrude, see nrbmak.
%
% vec : Vector along which the entity is extruded.
%
% OUTPUT:
%
% srf : NURBS surface or volume constructed.
%
% Description:
%
% Constructs either a NURBS surface by extruding a NURBS curve along a
% defined vector, or a NURBS volume by extruding a NURBS surface. In the
% first case, the NURBS curve forms the U direction of the surface edge, and
% is extruded along the vector in the V direction. In the second case, the
% original surface forms the U and V direction of the volume, and is extruded
% along the W direction.
%
% Examples:
%
% Form a hollow cylinder by extruding a circle along the z-axis.
%
% srf = nrbextrude(nrbcirc, [0,0,1]);
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin < 2)
error('Error too few input arguments!');
end
if (iscell (curve.knots))
if (numel (curve.knots) == 3)
error('Nurbs volumes cannot be extruded!');
end
for ii = 1:size(curve.coefs,3)
coefs(:,:,ii) = vectrans(vector) * squeeze (curve.coefs(:,:,ii));
end
coefs = cat(4,curve.coefs,coefs);
srf = nrbmak(coefs,{curve.knots{:}, [0 0 1 1]});
else
coefs = cat(3,curve.coefs,vectrans(vector)*curve.coefs);
srf = nrbmak(coefs,{curve.knots, [0 0 1 1]});
end
end
%!demo
%! crv = nrbtestcrv;
%! srf = nrbextrude(crv,[0 0 5]);
%! nrbplot(srf,[40 10]);
%! title('Extrusion of a test curve along the z-axis');
%! hold off
%
%!demo
%! crv1 = nrbcirc (1, [0 0], 0, pi/2);
%! crv2 = nrbcirc (2, [0 0], 0, pi/2);
%! srf = nrbruled (crv1, crv2);
%! vol = nrbextrude (srf, [0 0 1]);
%! nrbplot (vol, [30 10 10])
%! title ('Extrusion of the quarter of a ring')
%
%!demo
%! srf = nrbtestsrf;
%! vol = nrbextrude(srf, [0 0 10]);
%! nrbplot(vol,[20 20 20]);
%! title('Extrusion of a test surface along the z-axis');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/vecrot.m 0000644 0000000 0000000 00000000132 13070134113 015114 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecrot.m 0000644 0001750 0001750 00000003112 13070134113 015267 0 ustar 00bect bect 0000000 0000000 function rx = vecrot(angle, vector)
%
% VECROT: Transformation matrix for a rotation around the axis given by a vector.
%
% Calling Sequence:
%
% rx = vecrot (angle, vector);
%
% INPUT:
%
% angle : rotation angle defined in radians
% vector: vector defining the rotation axis
%
% OUTPUT:
%
% rx: (4x4) Transformation matrix.
%
%
% Description:
%
% Return the (4x4) Transformation matrix for a rotation about the axis
% defined by vector, and by the given angle.
%
% See also:
%
% nrbtform
%
% Copyright (C) 2011 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
% Normalize the vector
vec = vector / norm (vector);
sn = sin (angle);
cn = cos (angle);
rx = [cn+vec(1)^2*(1-cn), vec(1)*vec(2)*(1-cn)-vec(3)*sn, vec(1)*vec(3)*(1-cn)+vec(2)*sn, 0;
vec(1)*vec(2)*(1-cn)+vec(3)*sn, cn+vec(2)^2*(1-cn), vec(2)*vec(3)*(1-cn)-vec(1)*sn, 0;
vec(1)*vec(3)*(1-cn)-vec(2)*sn, vec(2)*vec(3)*(1-cn)+vec(1)*sn, cn+vec(3)^2*(1-cn), 0;
0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbline.m 0000644 0000000 0000000 00000000132 13070134113 015243 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbline.m 0000644 0001750 0001750 00000003014 13070134113 015417 0 ustar 00bect bect 0000000 0000000 function curve = nrbline(p1,p2)
%
% NRBLINE: Construct a straight line.
%
% Calling Sequence:
%
% crv = nrbline()
% crv = nrbline(p1,p2)
%
% INPUT:
%
% p1 : 2D or 3D cartesian coordinate of the start point.
%
% p2 : 2D or 3D cartesian coordinate of the end point.
%
% OUTPUT:
%
% crv : NURBS curve for a straight line.
%
% Description:
%
% Constructs NURBS data structure for a straight line. If no rhs
% coordinates are included the function returns a unit straight
% line along the x-axis.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
coefs = [zeros(3,2); ones(1,2)];
if nargin < 2
coefs(1,2) = 1.0;
else
coefs(1:length(p1),1) = p1(:);
coefs(1:length(p2),2) = p2(:);
end
curve = nrbmak(coefs, [0 0 1 1]);
end
%!demo
%! crv = nrbline([0.0 0.0 0.0]',[5.0 4.0 2.0]');
%! nrbplot(crv,1);
%! grid on;
%! title('3D straight line.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/bspdegelev.m 0000644 0000000 0000000 00000000132 13070134113 015732 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspdegelev.m 0000644 0001750 0001750 00000050041 13070134113 016110 0 ustar 00bect bect 0000000 0000000 function [ic,ik] = bspdegelev(d,c,k,t)
% BSPDEGELEV: Degree elevate a univariate B-Spline.
%
% Calling Sequence:
%
% [ic,ik] = bspdegelev(d,c,k,t)
%
% INPUT:
%
% d - Degree of the B-Spline.
% c - Control points, matrix of size (dim,nc).
% k - Knot sequence, row vector of size nk.
% t - Raise the B-Spline degree t times.
%
% OUTPUT:
%
% ic - Control points of the new B-Spline.
% ik - Knot vector of the new B-Spline.
%
% Copyright (C) 2000 Mark Spink, 2007 Daniel Claxton
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
[mc,nc] = size(c);
%
% int bspdegelev(int d, double *c, int mc, int nc, double *k, int nk,
% int t, int *nh, double *ic, double *ik)
% {
% int row,col;
%
% int ierr = 0;
% int i, j, q, s, m, ph, ph2, mpi, mh, r, a, b, cind, oldr, mul;
% int n, lbz, rbz, save, tr, kj, first, kind, last, bet, ii;
% double inv, ua, ub, numer, den, alf, gam;
% double **bezalfs, **bpts, **ebpts, **Nextbpts, *alfs;
%
% double **ctrl = vec2mat(c, mc, nc);
% ic = zeros(mc,nc*(t)); % double **ictrl = vec2mat(ic, mc, nc*(t+1));
%
n = nc - 1; % n = nc - 1;
%
bezalfs = zeros(d+1,d+t+1); % bezalfs = matrix(d+1,d+t+1);
bpts = zeros(mc,d+1); % bpts = matrix(mc,d+1);
ebpts = zeros(mc,d+t+1); % ebpts = matrix(mc,d+t+1);
Nextbpts = zeros(mc,d+1); % Nextbpts = matrix(mc,d+1);
alfs = zeros(d,1); % alfs = (double *) mxMalloc(d*sizeof(double));
%
m = n + d + 1; % m = n + d + 1;
ph = d + t; % ph = d + t;
ph2 = floor(ph / 2); % ph2 = ph / 2;
%
% // compute bezier degree elevation coefficeients
bezalfs(1,1) = 1; % bezalfs[0][0] = bezalfs[ph][d] = 1.0;
bezalfs(d+1,ph+1) = 1; %
for i=1:ph2 % for (i = 1; i <= ph2; i++) {
inv = 1/bincoeff(ph,i); % inv = 1.0 / bincoeff(ph,i);
mpi = min(d,i); % mpi = min(d,i);
%
for j=max(0,i-t):mpi % for (j = max(0,i-t); j <= mpi; j++)
bezalfs(j+1,i+1) = inv*bincoeff(d,j)*bincoeff(t,i-j); % bezalfs[i][j] = inv * bincoeff(d,j) * bincoeff(t,i-j);
end
end % }
%
for i=ph2+1:ph-1 % for (i = ph2+1; i <= ph-1; i++) {
mpi = min(d,i); % mpi = min(d, i);
for j=max(0,i-t):mpi % for (j = max(0,i-t); j <= mpi; j++)
bezalfs(j+1,i+1) = bezalfs(d-j+1,ph-i+1); % bezalfs[i][j] = bezalfs[ph-i][d-j];
end
end % }
%
mh = ph; % mh = ph;
kind = ph+1; % kind = ph+1;
r = -1; % r = -1;
a = d; % a = d;
b = d+1; % b = d+1;
cind = 1; % cind = 1;
ua = k(1); % ua = k[0];
%
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
ic(ii+1,1) = c(ii+1,1); % ictrl[0][ii] = ctrl[0][ii];
end %
for i=0:ph % for (i = 0; i <= ph; i++)
ik(i+1) = ua; % ik[i] = ua;
end %
% // initialise first bezier seg
for i=0:d % for (i = 0; i <= d; i++)
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
bpts(ii+1,i+1) = c(ii+1,i+1); % bpts[i][ii] = ctrl[i][ii];
end
end %
% // big loop thru knot vector
while b < m % while (b < m) {
i = b; % i = b;
while b < m && k(b+1) == k(b+2) % while (b < m && k[b] == k[b+1])
b = b + 1; % b++;
end %
mul = b - i + 1; % mul = b - i + 1;
mh = mh + mul + t; % mh += mul + t;
ub = k(b+1); % ub = k[b];
oldr = r; % oldr = r;
r = d - mul; % r = d - mul;
%
% // insert knot u(b) r times
if oldr > 0 % if (oldr > 0)
lbz = floor((oldr+2)/2); % lbz = (oldr+2) / 2;
else % else
lbz = 1; % lbz = 1;
end %
if r > 0 % if (r > 0)
rbz = ph - floor((r+1)/2); % rbz = ph - (r+1)/2;
else % else
rbz = ph; % rbz = ph;
end %
if r > 0 % if (r > 0) {
% // insert knot to get bezier segment
numer = ub - ua; % numer = ub - ua;
for q=d:-1:mul+1 % for (q = d; q > mul; q--)
alfs(q-mul) = numer / (k(a+q+1)-ua); % alfs[q-mul-1] = numer / (k[a+q]-ua);
end
for j=1:r % for (j = 1; j <= r; j++) {
save = r - j; % save = r - j;
s = mul + j; % s = mul + j;
%
for q=d:-1:s % for (q = d; q >= s; q--)
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
tmp1 = alfs(q-s+1)*bpts(ii+1,q+1);
tmp2 = (1-alfs(q-s+1))*bpts(ii+1,q);
bpts(ii+1,q+1) = tmp1 + tmp2; % bpts[q][ii] = alfs[q-s]*bpts[q][ii]+(1.0-alfs[q-s])*bpts[q-1][ii];
end
end %
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
Nextbpts(ii+1,save+1) = bpts(ii+1,d+1); % Nextbpts[save][ii] = bpts[d][ii];
end
end % }
end % }
% // end of insert knot
%
% // degree elevate bezier
for i=lbz:ph % for (i = lbz; i <= ph; i++) {
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
ebpts(ii+1,i+1) = 0; % ebpts[i][ii] = 0.0;
end
mpi = min(d, i); % mpi = min(d, i);
for j=max(0,i-t):mpi % for (j = max(0,i-t); j <= mpi; j++)
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
tmp1 = ebpts(ii+1,i+1);
tmp2 = bezalfs(j+1,i+1)*bpts(ii+1,j+1);
ebpts(ii+1,i+1) = tmp1 + tmp2; % ebpts[i][ii] = ebpts[i][ii] + bezalfs[i][j]*bpts[j][ii];
end
end
end % }
% // end of degree elevating bezier
%
if oldr > 1 % if (oldr > 1) {
% // must remove knot u=k[a] oldr times
first = kind - 2; % first = kind - 2;
last = kind; % last = kind;
den = ub - ua; % den = ub - ua;
bet = floor((ub-ik(kind)) / den); % bet = (ub-ik[kind-1]) / den;
%
% // knot removal loop
for tr=1:oldr-1 % for (tr = 1; tr < oldr; tr++) {
i = first; % i = first;
j = last; % j = last;
kj = j - kind + 1; % kj = j - kind + 1;
while j-i > tr % while (j - i > tr) {
% // loop and compute the new control points
% // for one removal step
if i < cind % if (i < cind) {
alf = (ub-ik(i+1))/(ua-ik(i+1)); % alf = (ub-ik[i])/(ua-ik[i]);
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
tmp1 = alf*ic(ii+1,i+1);
tmp2 = (1-alf)*ic(ii+1,i);
ic(ii+1,i+1) = tmp1 + tmp2; % ictrl[i][ii] = alf * ictrl[i][ii] + (1.0-alf) * ictrl[i-1][ii];
end
end % }
if j >= lbz % if (j >= lbz) {
if j-tr <= kind-ph+oldr % if (j-tr <= kind-ph+oldr) {
gam = (ub-ik(j-tr+1)) / den; % gam = (ub-ik[j-tr]) / den;
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
tmp1 = gam*ebpts(ii+1,kj+1);
tmp2 = (1-gam)*ebpts(ii+1,kj+2);
ebpts(ii+1,kj+1) = tmp1 + tmp2; % ebpts[kj][ii] = gam*ebpts[kj][ii] + (1.0-gam)*ebpts[kj+1][ii];
end % }
else % else {
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
tmp1 = bet*ebpts(ii+1,kj+1);
tmp2 = (1-bet)*ebpts(ii+1,kj+2);
ebpts(ii+1,kj+1) = tmp1 + tmp2; % ebpts[kj][ii] = bet*ebpts[kj][ii] + (1.0-bet)*ebpts[kj+1][ii];
end
end % }
end % }
i = i + 1; % i++;
j = j - 1; % j--;
kj = kj - 1; % kj--;
end % }
%
first = first - 1; % first--;
last = last + 1; % last++;
end % }
end % }
% // end of removing knot n=k[a]
%
% // load the knot ua
if a ~= d % if (a != d)
for i=0:ph-oldr-1 % for (i = 0; i < ph-oldr; i++) {
ik(kind+1) = ua; % ik[kind] = ua;
kind = kind + 1; % kind++;
end
end % }
%
% // load ctrl pts into ic
for j=lbz:rbz % for (j = lbz; j <= rbz; j++) {
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
ic(ii+1,cind+1) = ebpts(ii+1,j+1); % ictrl[cind][ii] = ebpts[j][ii];
end
cind = cind + 1; % cind++;
end % }
%
if b < m % if (b < m) {
% // setup for next pass thru loop
for j=0:r-1 % for (j = 0; j < r; j++)
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
bpts(ii+1,j+1) = Nextbpts(ii+1,j+1); % bpts[j][ii] = Nextbpts[j][ii];
end
end
for j=r:d % for (j = r; j <= d; j++)
for ii=0:mc-1 % for (ii = 0; ii < mc; ii++)
bpts(ii+1,j+1) = c(ii+1,b-d+j+1); % bpts[j][ii] = ctrl[b-d+j][ii];
end
end
a = b; % a = b;
b = b+1; % b++;
ua = ub; % ua = ub;
% }
else % else
% // end knot
for i=0:ph % for (i = 0; i <= ph; i++)
ik(kind+i+1) = ub; % ik[kind+i] = ub;
end
end
end % }
% End big while loop % // end while loop
%
% *nh = mh - ph - 1;
%
% freevec2mat(ctrl);
% freevec2mat(ictrl);
% freematrix(bezalfs);
% freematrix(bpts);
% freematrix(ebpts);
% freematrix(Nextbpts);
% mxFree(alfs);
%
% return(ierr);
end % }
function b = bincoeff(n,k)
% Computes the binomial coefficient.
%
% ( n ) n!
% ( ) = --------
% ( k ) k!(n-k)!
%
% b = bincoeff(n,k)
%
% Algorithm from 'Numerical Recipes in C, 2nd Edition' pg215.
% double bincoeff(int n, int k)
% {
b = floor(0.5+exp(factln(n)-factln(k)-factln(n-k))); % return floor(0.5+exp(factln(n)-factln(k)-factln(n-k)));
end % }
function f = factln(n)
% computes ln(n!)
if n <= 1, f = 0; return, end
f = gammaln(n+1); %log(factorial(n));
end nurbs-1.3.13/inst/PaxHeaders.26136/nrbsquare.m 0000644 0000000 0000000 00000000132 13070134113 015614 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbsquare.m 0000644 0001750 0001750 00000005161 13070134113 015775 0 ustar 00bect bect 0000000 0000000 function srf = nrbsquare (corner, lengthx, lengthy, varargin)
%
% NRBSQUARE: create the NURBS surface for a square.
%
% Calling Sequence:
%
% srf = nrbsquare (corner, lengthx, lengthy);
% srf = nrbsquare (corner, lengthx, lengthy, degree);
% srf = nrbsquare (corner, lengthx, lengthy, degree, nsub);
%
% INPUT:
% corner : the coordinates of the bottom left corner of the square.
% lenghtx : the length along the x direction.
% lenghty : the length along the y direction.
% degree : the degree of the NURBS surface, in each direction.
% nsub : the number of subdivision of the NURBS surface, in each direction.
%
% OUTPUT:
% srf : the NURBS surface.
%
% Copyright (C) 2016 Jacopo Corno, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (isempty (corner))
corner = [0 0];
end
nsub = [1 1];
degree = [1 1];
if (numel (varargin) >= 1)
if (numel (varargin{1}) == 1)
degree = [varargin{1} varargin{1}];
elseif (numel (varargin{1}) == 2)
degree = varargin{1};
else
error ('The degree vector should provide the degree in each direction (two values).');
end
if (numel (varargin) == 2)
if (numel (varargin{2}) == 1)
nsub = [varargin{2} varargin{2}];
elseif (numel (varargin{2}) == 2)
nsub = varargin{2};
else
error ('The nsub vector should provide the number of intervals in each direction (two values).');
end
end
end
srf = nrb4surf (corner, corner+[lengthx 0], corner+[0 lengthy], corner+[lengthx lengthy]);
srf = nrbdegelev (srf, degree-[1 1]);
[~,~,new_knots] = kntrefine (srf.knots, nsub-1, degree, degree-[1 1]);
srf = nrbkntins (srf, new_knots);
end
%!test
%! srf = nrbsquare ([], 1, 2, 2, 4);
%! assert (srf.order, [3 3]);
%! knt = [0 0 0 1/4 1/2 3/4 1 1 1];
%! assert (srf.knots, {knt knt})
%! x = linspace (0, 1, 100);
%! [X,Y] = ndgrid (x, x);
%! vals = nrbeval (srf, {x x});
%! assert (squeeze(vals(1,:,:)), X, 1e-15);
%! assert (squeeze(vals(2,:,:)), 2*Y, 1e-15);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbbasisfun.m 0000644 0000000 0000000 00000000126 13070134113 016131 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbbasisfun.m 0000644 0001750 0001750 00000016523 13070134113 016313 0 ustar 00bect bect 0000000 0000000 function [B, id] = nrbbasisfun (points, nrb)
% NRBBASISFUN: Basis functions for NURBS
%
% Calling Sequence:
%
% B = nrbbasisfun (u, crv)
% B = nrbbasisfun ({u, v}, srf)
% [B, N] = nrbbasisfun ({u, v}, srf)
% [B, N] = nrbbasisfun (pts, srf)
% [B, N] = nrbbasisfun ({u, v, w}, vol)
% [B, N] = nrbbasisfun (pts, vol)
%
% INPUT:
%
% u - parametric coordinates along u direction
% v - parametric coordinates along v direction
% w - parametric coordinates along w direction
% pts - array of scattered points in parametric domain, array size: (ndim,num_points)
% crv - NURBS curve
% srf - NURBS surface
% vol - NURBS volume
%
% If the parametric coordinates are given in a cell-array, the values
% are computed in a tensor product set of points
%
% OUTPUT:
%
% B - Value of the basis functions at the points
% size(B)=[npts, prod(nrb.order)]
%
% N - Indices of the basis functions that are nonvanishing at each
% point. size(N) == size(B)
%
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2015 Jacopo Corno
% Copyright (C) 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if ( (nargin<2) ...
|| (nargout>2) ...
|| (~isstruct(nrb)) ...
|| (iscell(points) && ~iscell(nrb.knots)) ...
|| (~iscell(points) && iscell(nrb.knots) && (size(points,1)~=numel(nrb.number))) ...
)
error('Incorrect input arguments in nrbbasisfun');
end
if (~iscell (nrb.knots)) %% NURBS curve
knt = {nrb.knots};
else %% NURBS surface or volume
knt = nrb.knots;
end
ndim = numel (nrb.number);
w = reshape (nrb.coefs(4,:), [nrb.number 1]);
for idim = 1:ndim
if (iscell (points))
pts_dim = points{idim};
else
pts_dim = points(idim,:);
end
sp{idim} = findspan (nrb.number(idim)-1, nrb.order(idim)-1, pts_dim, knt{idim});
N{idim} = basisfun(sp{idim}, pts_dim, nrb.order(idim)-1, knt{idim});
num{idim} = numbasisfun (sp{idim}, pts_dim, nrb.order(idim)-1, knt{idim}) + 1;
end
if (ndim == 1)
id = num{1};
B = reshape (w(num{1}), size(N{1})) .* N{1};
B = bsxfun (@(x,y) x./y, B, sum(B,2));
% B = B ./ sum(B,2);
else
if (iscell (points))
npts_dim = cellfun (@numel, points);
cumnpts = cumprod([1 npts_dim]);
npts = prod (npts_dim);
val_aux = 1;
numaux = 1;
cumorder = cumprod ([1 nrb.order]);
cumnumber = cumprod ([1 nrb.number]);
for idim = 1:ndim
val_aux = kron (N{idim}, val_aux);
num_dim = reshape (num{idim}, 1, npts_dim(idim), 1, nrb.order(idim));
num_dim = repmat (num_dim, cumnpts(idim), 1, cumorder(idim), 1);
num_prev = reshape (numaux, cumnpts(idim), 1, cumorder(idim), 1);
num_prev = repmat (num_prev, 1, npts_dim(idim), 1, nrb.order(idim));
numaux = sub2ind ([cumnumber(idim) nrb.number(idim)], num_prev, num_dim);
numaux = reshape (numaux, cumnpts(idim+1), cumorder(idim+1));
end
B = reshape (val_aux, npts, prod (nrb.order));
id = reshape (numaux, npts, prod (nrb.order));
W = w(id);
B = bsxfun (@(x,y) x./y, W.*B, sum (W .* B, 2));
else
npts = numel (points(1,:));
B = zeros (npts, prod(nrb.order));
id = zeros (npts, prod(nrb.order));
local_num = cell (ndim, 1);
for ipt = 1:npts
val_aux = 1;
for idim = 1:ndim
val_aux = reshape (val_aux.' * N{idim}(ipt,:), 1, []);
% val_aux2 = kron (N{idim}(ipt,:), val_aux);
local_num{idim} = num{idim}(ipt,:);
end
[local_num{:}] = ndgrid (local_num{:});
id(ipt,:) = reshape (sub2ind (nrb.number, local_num{:}), 1, size(id, 2));
W = reshape (w(id(ipt,:)), size(val_aux));
val_aux = W .* val_aux;
B(ipt,:) = val_aux / sum (val_aux);
end
end
end
end
%!demo
%! U = [0 0 0 0 1 1 1 1];
%! x = [0 1/3 2/3 1] ;
%! y = [0 0 0 0];
%! w = [1 1 1 1];
%! nrb = nrbmak ([x;y;y;w], U);
%! u = linspace(0, 1, 30);
%! B = nrbbasisfun (u, nrb);
%! xplot = sum(bsxfun(@(x,y) x.*y, B, x),2);
%! plot(xplot, B)
%! title('Cubic Bernstein polynomials')
%! hold off
%!test
%! U = [0 0 0 0 1 1 1 1];
%! x = [0 1/3 2/3 1] ;
%! y = [0 0 0 0];
%! w = rand(1,4);
%! nrb = nrbmak ([x;y;y;w], U);
%! u = linspace(0, 1, 30);
%! B = nrbbasisfun (u, nrb);
%! xplot = sum(bsxfun(@(x,y) x.*y, B, x),2);
%!
%! yy = y; yy(1) = 1;
%! nrb2 = nrbmak ([x.*w;yy;y;w], U);
%! aux = nrbeval(nrb2,u);
%! %figure, plot(xplot, B(:,1), aux(1,:).', w(1)*aux(2,:).')
%! assert(B(:,1), w(1)*aux(2,:).', 1e-6)
%!
%! yy = y; yy(2) = 1;
%! nrb2 = nrbmak ([x.*w;yy;y;w], U);
%! aux = nrbeval(nrb2, u);
%! %figure, plot(xplot, B(:,2), aux(1,:).', w(2)*aux(2,:).')
%! assert(B(:,2), w(2)*aux(2,:).', 1e-6)
%!
%! yy = y; yy(3) = 1;
%! nrb2 = nrbmak ([x.*w;yy;y;w], U);
%! aux = nrbeval(nrb2,u);
%! %figure, plot(xplot, B(:,3), aux(1,:).', w(3)*aux(2,:).')
%! assert(B(:,3), w(3)*aux(2,:).', 1e-6)
%!
%! yy = y; yy(4) = 1;
%! nrb2 = nrbmak ([x.*w;yy;y;w], U);
%! aux = nrbeval(nrb2,u);
%! %figure, plot(xplot, B(:,4), aux(1,:).', w(4)*aux(2,:).')
%! assert(B(:,4), w(4)*aux(2,:).', 1e-6)
%!test
%! p = 2; q = 3; m = 4; n = 5;
%! Lx = 1; Ly = 1;
%! nrb = nrb4surf ([0 0], [1 0], [0 1], [1 1]);
%! nrb = nrbdegelev (nrb, [p-1, q-1]);
%! aux1 = linspace(0,1,m); aux2 = linspace(0,1,n);
%! nrb = nrbkntins (nrb, {aux1(2:end-1), aux2(2:end-1)});
%! u = rand (1, 30); v = rand (1, 10);
%! u = u - min (u); u = u / max (u);
%! v = v - min (v); v = v / max (v);
%! [B, N] = nrbbasisfun ({u, v}, nrb);
%! assert (sum(B, 2), ones(300, 1), 1e-6)
%! assert (all (all (B<=1)), true)
%! assert (all (all (B>=0)), true)
%! assert (all (all (N>0)), true)
%! assert (all (all (N <= prod (nrb.number))), true)
%! assert (max (max (N)),prod (nrb.number))
%! assert (min (min (N)),1)
%!test
%! p1 = 2; p2 = 3; p3 = 2;
%! n1 = 4; n2 = 5; n3 = 4;
%! Lx = 1; Ly = 1; Lz = 1;
%! crv = nrbline([1 0], [2 0]);
%! nrb = nrbtransp (nrbrevolve (crv, [], [0 0 1], pi/2));
%! nrb = nrbextrude (nrb, [0 0 1]);
%! nrb = nrbdegelev (nrb, [p1-1, p2-2, p3-1]);
%! aux1 = linspace(0,1,n1); aux2 = linspace(0,1,n2); aux3 = linspace(0,1,n3);
%! nrb = nrbkntins (nrb, {aux1(2:end-1), aux2(2:end-1), aux3(2:end-1)});
%!
%! u = rand (1, 12); v = rand (1, 10); w = rand (1, 15);
%! u = u - min (u); u = u / max (u);
%! v = v - min (v); v = v / max (v);
%! w = w - min (w); w = w / max (w);
%! [B, N] = nrbbasisfun ({u, v, w}, nrb);
%! assert (all(sum(B, 2) - ones(numel(u)*numel(v)*numel(w),1) < 1e-6))
%! assert (all (all (B <= 1)) == true)
%! assert (all (all (B >= 0)) == true)
%! assert (all (all (N > 0)) == true)
%! assert (all (all (N <= prod (nrb.number))) == true)
%! assert (max (max (N)) == prod (nrb.number))
%! assert (min (min (N))== 1) nurbs-1.3.13/inst/PaxHeaders.26136/nrbextract.m 0000644 0000000 0000000 00000000132 13070134113 015766 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbextract.m 0000644 0001750 0001750 00000006443 13070134113 016153 0 ustar 00bect bect 0000000 0000000 function crvs = nrbextract(srf)
%
% NRBEXTRACT: construct NURBS curves by extracting the boundaries of a NURBS surface, or NURBS surfaces by extracting the boundary of a NURBS volume.
% It only works for geometries constructed with open knot vectors. For a NURBS curve,
% it returns two structures with the the boundary knots and control points.
%
% Calling Sequence:
%
% crvs = nrbextract(surf);
%
% INPUT:
%
% surf : NURBS surface or volume, see nrbmak.
%
% OUTPUT:
%
% crvs : array of NURBS curves or NURBS surfaces extracted.
%
% Description:
%
% Constructs either an array of four NURBS curves, by extracting the boundaries
% of a NURBS surface, or an array of six surfaces, by extracting the boundaries
% of a NURBS volume. The new entities are ordered in the following way
%
% 1: U = 0
% 2: U = 1
% 3: V = 0
% 4: V = 1
% 5: W = 0 (only for volumes)
% 6: W = 1 (only for volumes)
%
% Copyright (C) 2010,2014,2015 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (~iscell (srf.knots))
crvs(1).knots = srf.knots(1);
crvs(1).coefs = srf.coefs(:,1);
crvs(2).knots = srf.knots(end);
crvs(2).coefs = srf.coefs(:,end);
return
end
for idim = 1:numel(srf.knots)
ord = srf.order(idim);
if (srf.knots{idim}(1) ~= srf.knots{idim}(ord) || ...
srf.knots{idim}(end) ~= srf.knots{idim}(end-ord+1))
error ('nrbextract: only working for open knot vectors')
end
end
if (numel (srf.knots) == 2)
for ind = 1:2
ind2 = mod (ind, 2) + 1; %ind2 = [2 1];
bnd1 = (ind - 1) * 2 + 1;
bnd2 = (ind - 1) * 2 + 2;
if (ind == 1)
coefs1 = squeeze (srf.coefs(:,1,:));
coefs2 = squeeze (srf.coefs(:,end,:));
elseif (ind == 2)
coefs1 = squeeze (srf.coefs(:,:,1));
coefs2 = squeeze (srf.coefs(:,:,end));
end
crvs(bnd1) = nrbmak (coefs1, srf.knots{ind2});
crvs(bnd2) = nrbmak (coefs2, srf.knots{ind2});
end
elseif (numel (srf.knots) == 3)
for ind = 1:3
inds = setdiff (1:3, ind);
bnd1 = (ind - 1) * 2 + 1;
bnd2 = (ind - 1) * 2 + 2;
if (ind == 1)
coefs1 = squeeze (srf.coefs(:,1,:,:));
coefs2 = squeeze (srf.coefs(:,end,:,:));
elseif (ind == 2)
coefs1 = squeeze (srf.coefs(:,:,1,:));
coefs2 = squeeze (srf.coefs(:,:,end,:));
elseif (ind == 3)
coefs1 = squeeze (srf.coefs(:,:,:,1));
coefs2 = squeeze (srf.coefs(:,:,:,end));
end
crvs(bnd1) = nrbmak (coefs1, {srf.knots{inds(1)} srf.knots{inds(2)}});
crvs(bnd2) = nrbmak (coefs2, {srf.knots{inds(1)} srf.knots{inds(2)}});
end
else
error ('The entity is not a surface nor a volume')
end
end
nurbs-1.3.13/inst/PaxHeaders.26136/vecrotx.m 0000644 0000000 0000000 00000000132 13070134113 015304 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecrotx.m 0000644 0001750 0001750 00000003201 13070134113 015456 0 ustar 00bect bect 0000000 0000000 function rx = vecrotx(angle)
%
% VECROTX: Transformation matrix for a rotation around the x axis.
%
% Calling Sequence:
%
% rx = vecrotx(angle);
%
% INPUT:
%
% angle : rotation angle defined in radians
%
% OUTPUT:
%
% rx : (4x4) Transformation matrix.
%
%
% Description:
%
% Return the (4x4) Transformation matrix for a rotation about the x axis
% by the defined angle.
%
% The matrix is:
%
% [ 1 0 0 0]
% [ 0 cos(angle) -sin(angle) 0]
% [ 0 sin(angle) cos(angle) 0]
% [ 0 0 0 1]
%
% Examples:
%
% Rotate the NURBS line (0.0 0.0 0.0) - (3.0 3.0 3.0) by 45 degrees
% around the x-axis
%
% line = nrbline([0.0 0.0 0.0],[3.0 3.0 3.0]);
% trans = vecrotx(%pi/4);
% rline = nrbtform(line, trans);
%
% See also:
%
% nrbtform
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
sn = sin(angle);
cn = cos(angle);
rx = [1 0 0 0; 0 cn -sn 0; 0 sn cn 0; 0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/bspinterpsurf.m 0000644 0000000 0000000 00000000126 13070134113 016523 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/bspinterpsurf.m 0000644 0001750 0001750 00000010100 13070134113 016666 0 ustar 00bect bect 0000000 0000000 function srf = bspinterpsurf (X, Y, Z, p, method)
%
% BSPINTERPSURF: B-Spline surface interpolation.
%
% Calling Sequence:
%
% srf = bspinterpsurf (Q, p, method);
%
% INPUT:
%
% X, Y, Z - grid of points to be interpolated. (See ndgrid)
% p - degree of the interpolating curve ([degree_x, degree_y]).
% method - parametrization method. The available choices are:
% 'equally_spaced'
% 'chord_length' (default)
%
% OUTPUT:
%
% srf - the B-Spline surface.
%
% See The NURBS book pag. 376 for more information. As of now only the
% chord length method is implemented.
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
if (nargin < 5 || isempty (method))
method = 'chord_length';
end
[n, m] = size (X);
Q = zeros (3, n, m);
Q(1,:,:) = X;
Q(2,:,:) = Y;
Q(3,:,:) = Z;
if (strcmpi (method, 'equally_spaced'))
u = linspace (0, 1, n);
v = linspace (0, 1, m);
elseif (strcmp (method, 'chord_length'))
u = zeros (m, n);
for ii = 1:m
d = sum (sqrt (sum (diff (squeeze(Q(:,:,ii))')'.^2,1)));
u(ii,2:n) = cumsum (sqrt (sum (diff(Q(:,:,ii), [], 2).^2, 1)))/d;
% for jj = 2:n-1
% u(ii,jj) = u(ii,jj-1) + norm (Q(:,jj,ii) - Q(:,jj-1,ii)) / d;
% end
u(ii,end) = 1;
end
u = mean (u);
v = zeros (n, m);
for ii = 1:n
d = sum (sqrt (sum (diff (squeeze(Q(:,ii,:))')'.^2,1)));
v(ii,2:m) = cumsum (sqrt (sum (diff(Q(:,ii,:), [], 3).^2, 1)))/d;
% for jj = 2:m-1
% v(ii,jj) = v(ii,jj-1) + norm (Q(:,ii,jj) - Q(:,ii,jj-1)) / d;
% end
v(ii,end) = 1;
end
v = mean (v);
end
% TODO: implement centripetal method
% Compute knot vectors
knts{1} = zeros (1, n+p(1)+1);
for jj = 2:n-p(1)
knts{1}(jj+p(1)) = 1/p(1) * sum (u(jj:jj+p(1)-1));
end
knts{1}(end-p(1):end) = ones (1, p(1)+1);
knts{2} = zeros (1, m+p(2)+1);
for jj = 2:m-p(2)
knts{2}(jj+p(2)) = 1/p(2) * sum (v(jj:jj+p(2)-1));
end
knts{2}(end-p(2):end) = ones (1, p(2)+1);
% Interpolation
R = zeros (size (Q));
P = zeros (4, n, m);
for ii = 1:m
A = zeros (n, n);
A(1,1) = 1;
A(n,n) = 1;
for jj=2:n-1
span = findspan (n, p(1), u(jj), knts{1});
A(jj,span-p(1)+1:span+1) = basisfun (span, u(jj), p(1), knts{1});
end
R(1,:,ii) = A \ squeeze(Q(1,:,ii))';
R(2,:,ii) = A \ squeeze(Q(2,:,ii))';
R(3,:,ii) = A \ squeeze(Q(3,:,ii))';
end
for ii = 1:n
A = zeros (m, m);
A(1,1) = 1;
A(m,m) = 1;
for jj=2:m-1
span = findspan (m, p(2), v(jj), knts{2});
A(jj,span-p(2)+1:span+1) = basisfun (span, v(jj), p(2), knts{2});
end
P(1,ii,:) = A \ squeeze(R(1,ii,:));
P(2,ii,:) = A \ squeeze(R(2,ii,:));
P(3,ii,:) = A \ squeeze(R(3,ii,:));
end
P(4,:,:) = ones (n, m);
% Create B-Spline interpolant
srf = nrbmak (P, knts);
end
%!demo
%! x = linspace (-3, 3, 40);
%! y = linspace (-3, 3, 40);
%! [X, Y] = meshgrid (x, y);
%! Z = peaks (X, Y);
%!
%! srf1 = bspinterpsurf (X, Y, Z, [2 2], 'equally_spaced');
%! srf2 = bspinterpsurf (X, Y, Z, [2 2], 'chord_length');
%! figure
%! nrbkntplot(srf1)
%! title ('Approximation of the peaks functions, with the equally spaced method')
%! figure
%! nrbkntplot(srf2)
%! title ('Approximation of the peaks functions, with the chord length method')
nurbs-1.3.13/inst/PaxHeaders.26136/crvkntremove.m 0000644 0000000 0000000 00000000126 13070134113 016342 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/crvkntremove.m 0000644 0001750 0001750 00000010361 13070134113 016516 0 ustar 00bect bect 0000000 0000000
function [rcrv, t] = crvkntremove (crv, u, r, s, num, d)
%
% CRVKNTREMOVE: Remove one knot from the knot-vector of a NURBS curve.
%
% Calling Sequence:
%
% [rcrv, remflag] = crvkntremove (crv, u, r, s, num, d);
%
% INPUT:
%
% crv : NURBS curve, see nrbmak.
%
% u : knot to be removed.
%
% r : index of the knot to be removed.
%
% s : multiplicity of the knot to be removed.
%
% num : number of knot removals requested.
%
% d : curve deviation tolerance.
%
% OUTPUT:
%
% rcrv : new NURBS structure for the curve with knot u remuved.
%
% t : actual number of knot removals performed.
%
%
%
% DESCRIPTION:
%
% Remove knot u from the NURBS curve crv at most num times.
% Check that the maximum deviation of the curve be less than d.
% Based on algorithm A5.8 NURBS Book (pag183)
%
% SEE ALSO:
%
% nrbkntins
%
% Copyright (C) 2013 Jacopo Corno
% Copyright (C) 2013 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
[U, Pw, t] = RemoveCurveKnot (crv.number, crv.order - 1, crv.knots, ...
crv.coefs, u, r, s, num, d);
rcrv = nrbmak (Pw, U);
end
%!test
%! crv = nrbdegelev (nrbline (), 3);
%! acrv = nrbkntins (crv, [.11 .11 .11]);
%! [rcrv, t] = crvkntremove (acrv, .11, 8, 3, 3, 1e-10);
%! assert (crv.knots, rcrv.knots, 1e-10);
%! assert (t, 3);
%!test
%! crv = nrbcirc ();
%! acrv = nrbkntins (crv, [.3 .3]);
%! [rcrv, t] = crvkntremove (acrv, .3, 7, 2, 2, 1e-10);
%! assert (crv.knots, rcrv.knots, 1e-10);
%! assert (t, 2);
function [U, Pw, t] = RemoveCurveKnot (n, p, U, Pw, u, r, s, num, d)
% see algorithm A5.8 NURBS Book (pag183)
w = min (Pw(4,:));
Pmax = max (sqrt (sum (Pw.^2, 1)));
TOL = d*w / (1 + Pmax);
m = n + p + 1;
ord = p + 1;
fout = (2*r - s - p) / 2; % first control point out
last = r - s;
first = r - p;
temp = zeros (4, 2*p + 1);
for t = 0:num-1
off = first - 1; % diff in index between temp and P
temp(:,1) = Pw(:,off);
temp(:,last+1-off+1) = Pw(:,last+1);
i = first;
j = last;
ii = 1;
jj = last - off;
remflag = 0;
while (j - i > t)
% compute new control points for one removal step
alfi = (u-U(i)) / (U(i+ord+t)-U(i));
alfj = (u-U(j-t)) / (U(j+ord)-U(j-t));
temp(:,ii+1) = (Pw(:,i)-(1.0-alfi).*temp(:,ii-1+1))./alfi;
temp(:,jj+1) = (Pw(:,j)-alfj.*temp(:,jj+1+1))./(1.0-alfj);
i = i + 1;
ii = ii + 1;
j = j - 1;
jj = jj - 1;
end
if (j - i <= t)
% check if knot removable
if (norm (temp(:,ii-1+1) - temp(:,jj+1+1)) <= TOL)
remflag = 1;
else
alfi = (u-U(i)) / (U(i+ord+t)-U(i));
if (norm (Pw(:,i) - (alfi.*temp(:,ii+t+1+1) + ...
(1-alfi).*temp(:,ii-1+1))) <= TOL)
remflag = 1;
end%if
end%if
end%if
if (remflag == 0)
break; % cannot remove any more knots -> get out of for loop
else
% successful removal -> save new control points
i = first;
j = last;
while (j - i > t)
Pw(:,i) = temp(:,i-off+1);
Pw(:,j) = temp(:,j-off+1);
i = i + 1;
j = j - 1;
end
end%if
first = first - 1;
last = last + 1;
t = t + 1;
end % end of for loop
if (t == 0)
return;
end%if
% shift knots
for k = r+1:m
U(k-t) = U(k);
end
U = U(1:end-t);
j = floor(fout);
i = j;
for k = 1:t-1
if (mod (k, 2) == 1)
i = i+1;
else
j = j-1;
end%if
end
% shift points
for k = i+1:n
Pw(:,j) = Pw(:,k);
j = j+1;
end
Pw = Pw(:,1:end-t);
return;
end
nurbs-1.3.13/inst/PaxHeaders.26136/vecscale.m 0000644 0000000 0000000 00000000132 13070134113 015377 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecscale.m 0000644 0001750 0001750 00000003224 13070134113 015556 0 ustar 00bect bect 0000000 0000000 function ss = vecscale(vector)
%
% VECSCALE: Transformation matrix for a scaling.
%
% Calling Sequence:
%
% ss = vecscale(svec)
%
% INPUT:
%
% svec : A vectors defining the scaling along the x,y and z axes.
% i.e. [sx, sy, sy]
%
% OUTPUT:
%
% ss : Scaling Transformation Matrix
%
% Description:
%
% Returns a (4x4) Transformation matrix for scaling.
%
% The matrix is:
%
% [ sx 0 0 0]
% [ 0 sy 0 0]
% [ 0 0 sz 0]
% [ 0 0 0 1]
%
% Example:
%
% Scale up the NURBS line (0.0,0.0,0.0) - (1.0,1.0,1.0) by 3 along
% the x-axis, 2 along the y-axis and 4 along the z-axis.
%
% line = nrbline([0.0 0.0 0.0],[1.0 1.0 1.0]);
% trans = vecscale([3.0 2.0 4.0]);
% sline = nrbtform(line, trans);
%
% See also:
%
% nrbtform
%
% Copyright (C) 2000 Mark Spink, 2007 Daniel Claxton
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 1
error('Scaling vector not specified');
end
s = [vector(:);0;0];
ss = [s(1) 0 0 0; 0 s(2) 0 0; 0 0 s(3) 0; 0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/vecrotz.m 0000644 0000000 0000000 00000000132 13070134113 015306 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecrotz.m 0000644 0001750 0001750 00000003332 13070134113 015465 0 ustar 00bect bect 0000000 0000000 function rz = vecrotz(angle)
%
% VECROTZ: Transformation matrix for a rotation around the z axis.
%
% Calling Sequence:
%
% rz = vecrotz(angle);
%
% INPUT:
%
% angle : rotation angle defined in radians
%
% OUTPUT:
%
% rz : (4x4) Transformation matrix.
%
%
% Description:
%
% Return the (4x4) Transformation matrix for a rotation about the z axis
% by the defined angle.
%
% The matrix is:
%
% [ cos(angle) -sin(angle) 0 0]
% [ -sin(angle) cos(angle) 0 0]
% [ 0 0 1 0]
% [ 0 0 0 1]
%
% Examples:
%
% Rotate the NURBS line (0.0 0.0 0.0) - (3.0 3.0 3.0) by 45 degrees
% around the z-axis
%
% line = nrbline([0.0 0.0 0.0],[3.0 3.0 3.0]);
% trans = vecrotz(%pi/4);
% rline = nrbtform(line, trans);
%
% See also:
%
% nrbtform
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
sn = sin(angle);
cn = cos(angle);
rz = [cn -sn 0 0; sn cn 0 0; 0 0 1 0; 0 0 0 1];
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbtform.m 0000644 0000000 0000000 00000000132 13070134113 015443 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbtform.m 0000644 0001750 0001750 00000004727 13070134113 015633 0 ustar 00bect bect 0000000 0000000 function nurbs = nrbtform(nurbs,tmat)
%
% NRBTFORM: Apply transformation matrix to the NURBS.
%
% Calling Sequence:
%
% tnurbs = nrbtform(nurbs,tmatrix);
%
% INPUT:
%
% nurbs : NURBS data structure (see nrbmak for details).
%
% tmatrix : Transformation matrix, a matrix of size (4,4) defining
% a single or multiple transformations.
%
% OUTPUT:
%
% tnurbs : The return transformed NURBS data structure.
%
% Description:
%
% The NURBS is transform as defined a transformation matrix of size (4,4),
% such as a rotation, translation or change in scale. The transformation
% matrix can define a single transformation or multiple series of
% transformations. The matrix can be simply constructed by the functions
% vecscale, vectrans and vecrot, and also vecrotx, vecroty, and vecrotz.
%
% Examples:
%
% Rotate a square by 45 degrees about the z axis.
%
% rsqr = nrbtform(nrbrect(), vecrotz(45*pi/180));
% nrbplot(rsqr, 1000);
%
% See also:
%
% vecscale, vectrans, vecrot, vecrotx, vecroty, vecrotz
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 2
error('Not enough input arguments!');
end;
if iscell(nurbs.knots)
if size(nurbs.knots,2) == 2
% NURBS is a surface
[dim,nu,nv] = size(nurbs.coefs);
nurbs.coefs = reshape(tmat*reshape(nurbs.coefs,dim,nu*nv),[dim nu nv]);
elseif size(nurbs.knots,2) == 3
% NURBS is a volume
[dim,nu,nv,nw] = size(nurbs.coefs);
nurbs.coefs = reshape(tmat*reshape(nurbs.coefs,dim,nu*nv*nw),[dim nu nv nw]);
end
else
% NURBS is a curve
nurbs.coefs = tmat*nurbs.coefs;
end
end
%!demo
%! xx = vectrans([2.0 1.0])*vecroty(pi/8)*vecrotx(pi/4)*vecscale([1.0 2.0]);
%! c0 = nrbtform(nrbcirc, xx);
%! nrbplot(c0,50);
%! grid on
%! title('Construction of an ellipse by transforming a unit circle.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/kntbrkdegmult.m 0000644 0000000 0000000 00000000126 13070134113 016472 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/kntbrkdegmult.m 0000644 0001750 0001750 00000006612 13070134113 016652 0 ustar 00bect bect 0000000 0000000 % KNTBRKDEGMULT: Construct an open knot vector by giving the sequence of
% knots, the degree and the multiplicity.
%
% knots = kntbrkdegreg (breaks, degree)
% knots = kntbrkdegreg (breaks, degree, mult)
%
% INPUT:
%
% breaks: sequence of knots.
% degree: polynomial degree of the splines associated to the knot vector.
% mult: multiplicity of the knots.
%
% OUTPUT:
%
% knots: knot vector.
%
% If MULT has as many entries as BREAKS, or as the number of interior
% knots, a different multiplicity will be assigned to each knot. If
% MULT is not present, it will be taken equal to 1.
%
% Copyright (C) 2010 Carlo de Falco, Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
function knots = kntbrkdegmult (breaks, degree, mult)
if (iscell (breaks))
if (nargin == 2)
mult = 1;
end
if (numel(breaks)~=numel(degree) || numel(breaks)~=numel(mult))
error('kntbrkdegmult: degree and multiplicity must have the same length as the number of knot vectors')
end
degree = num2cell (degree);
if (~iscell (mult))
mult = num2cell (mult);
end
knots = cellfun (@do_kntbrkdegmult, breaks, degree, mult, 'uniformoutput', false);
else
if (nargin == 2)
mult = 1;
end
knots = do_kntbrkdegmult (breaks, degree, mult);
end
end
function knots = do_kntbrkdegmult (breaks, degree, mult)
if (numel (breaks) < 2)
error ('kntbrkdegmult: the knots sequence should contain at least two points')
end
if (numel (mult) == 1)
mults = [degree+1, mult(ones (1, numel (breaks) - 2)), degree+1];
elseif (numel (mult) == numel (breaks))
mults = [degree+1 mult(2:end-1) degree+1];
elseif (numel (mult) == numel (breaks) - 2)
mults = [degree+1 mult degree+1];
else
error('kntbrkdegmult: the length of mult should be equal to one or the number of knots')
end
if (any (mults > degree+1))
warning ('kntbrkdegmult: some knots have higher multiplicity than the degree+1')
end
breaks = sort (breaks);
lm = numel (mults);
sm = sum (mults);
mm = zeros (1,sm);
mm (cumsum ([1 reshape(mults (1:end-1), 1, lm-1)])) = ones (1,lm);
knots = breaks (cumsum (mm));
end
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! knots = kntbrkdegmult (breaks, degree);
%! assert (knots, [0 0 0 0 1 2 3 4 4 4 4])
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! mult = 2;
%! knots = kntbrkdegmult (breaks, degree, mult);
%! assert (knots, [0 0 0 0 1 1 2 2 3 3 4 4 4 4])
%!test
%! breaks = [0 1 2 3 4];
%! degree = 3;
%! mult = [1 2 3];
%! knots = kntbrkdegmult (breaks, degree, mult);
%! assert (knots, [0 0 0 0 1 2 2 3 3 3 4 4 4 4])
%!test
%! breaks = {[0 1 2 3 4] [0 1 2 3]};
%! degree = [3 2];
%! mult = {[1 2 3] 2};
%! knots = kntbrkdegmult (breaks, degree, mult);
%! assert (knots, {[0 0 0 0 1 2 2 3 3 3 4 4 4 4] [0 0 0 1 1 2 2 3 3 3]})
nurbs-1.3.13/inst/PaxHeaders.26136/vecmag2.m 0000644 0000000 0000000 00000000132 13070134113 015136 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecmag2.m 0000644 0001750 0001750 00000002501 13070134113 015312 0 ustar 00bect bect 0000000 0000000 function mag = vecmag2(vec)
%
% VECMAG2: Squared magnitude of a set of vectors.
%
% Calling Sequence:
%
% mvec = vecmag2(vec)
%
% INPUT:
%
% vec : An array of column vectors represented by a matrix of
% size (dim,nv), where dim is the dimension of the vector and
% nv the number of vectors.
%
% OUTPUT:
%
% mvec : Squared magnitude of the vectors, vector of size (1,nv).
%
% Description:
%
% Determines the squared magnitude of the vectors.
%
% Examples:
%
% Find the squared magnitude of the two vectors (0.0,2.0,1.3)
% and (1.5,3.4,2.3)
%
% mvec = vecmag2([0.0 1.5; 2.0 3.4; 1.3 2.3]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
mag = sum(vec.^2);
end
nurbs-1.3.13/inst/PaxHeaders.26136/numbasisfun.m 0000644 0000000 0000000 00000000132 13070134113 016144 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/numbasisfun.m 0000644 0001750 0001750 00000002766 13070134113 016335 0 ustar 00bect bect 0000000 0000000 function B = numbasisfun (iv, uv, p, U)
% NUMBASISFUN: List non-zero Basis functions for B-Spline in a given knot-span
%
% Calling Sequence:
%
% N = numbasisfun(i,u,p,U)
%
% INPUT:
%
% i - knot span ( from FindSpan() )
% u - parametric point
% p - spline degree
% U - knot sequence
%
% OUTPUT:
%
% N - Basis functions (numel(u)x(p+1))
%
% See also:
%
% basisfun, basisfunder
%
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
B = bsxfun (@(a, b) a+b,iv-p, (0:p).').';
end
%!test
%! n = 3;
%! U = [0 0 0 1/2 1 1 1];
%! p = 2;
%! u = linspace (0, 1, 10);
%! s = findspan (n, p, u, U);
%! Bref = [0 0 0 0 0 1 1 1 1 1; ...
%! 1 1 1 1 1 2 2 2 2 2; ...
%! 2 2 2 2 2 3 3 3 3 3].';
%! B = numbasisfun (s, u, p, U);
%! assert (B, Bref) nurbs-1.3.13/inst/PaxHeaders.26136/nrbcirc.m 0000644 0000000 0000000 00000000132 13070134113 015234 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbcirc.m 0000644 0001750 0001750 00000005734 13070134113 015423 0 ustar 00bect bect 0000000 0000000 function curve = nrbcirc(radius,center,sang,eang)
%
% NRBCIRC: Construct a circular arc.
%
% Calling Sequence:
%
% crv = nrbcirc()
% crv = nrbcirc(radius)
% crv = nrbcirc(radius,center)
% crv = nrbcirc(radius,center,sang,eang)
%
% INPUT:
%
% radius : Radius of the circle, default 1.0
%
% center : Center of the circle, default (0,0,0)
%
% sang : Start angle, default 0 radians (0 degrees)
%
% eang : End angle, default 2*pi radians (360 degrees)
%
% OUTPUT:
%
% crv : NURBS curve for a circular arc.
%
% Description:
%
% Constructs NURBS data structure for a circular arc in the x-y plane. If
% no rhs arguments are supplied a unit circle with center (0.0,0.0) is
% constructed.
%
% Angles are defined as positive in the anti-clockwise direction.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 1
radius = 1;
end
if nargin < 2
center = [];
end
if nargin < 4
sang = 0;
eang = 2*pi;
end
sweep = eang - sang; % sweep angle of arc
if sweep < 0
sweep = 2*pi + sweep;
end
if abs(sweep) <= pi/2
narcs = 1; % number of arc segments
knots = [0 0 0 1 1 1];
elseif abs(sweep) <= pi
narcs = 2;
knots = [0 0 0 0.5 0.5 1 1 1];
elseif abs(sweep) <= 3*pi/2
narcs = 3;
knots = [0 0 0 1/3 1/3 2/3 2/3 1 1 1];
else
narcs = 4;
knots = [0 0 0 0.25 0.25 0.5 0.5 0.75 0.75 1 1 1];
end
dsweep = sweep/(2*narcs); % arc segment sweep angle/2
% determine middle control point and weight
wm = cos(dsweep);
x = radius*wm;
y = radius*sin(dsweep);
xm = x+y*tan(dsweep);
% arc segment control points
ctrlpt = [ x wm*xm x; % w*x - coordinate
-y 0 y; % w*y - coordinate
0 0 0; % w*z - coordinate
1 wm 1]; % w - coordinate
% build up complete arc from rotated segments
coefs = zeros(4,2*narcs+1); % nurbs control points of arc
xx = vecrotz(sang + dsweep);
coefs(:,1:3) = xx*ctrlpt; % rotate to start angle
xx = vecrotz(2*dsweep);
for n = 2:narcs
m = 2*n+[0 1];
coefs(:,m) = xx*coefs(:,m-2);
end
% vectrans arc if necessary
if ~isempty(center)
xx = vectrans(center);
coefs = xx*coefs;
end
curve = nrbmak(coefs,knots);
end
%!demo
%! for r = 1:9
%! crv = nrbcirc(r,[],45*pi/180,315*pi/180);
%! nrbplot(crv,50);
%! hold on;
%! end
%! hold off;
%! axis equal;
%! title('NURBS construction of several 2D arcs.');
nurbs-1.3.13/inst/PaxHeaders.26136/nrbrevolve.m 0000644 0000000 0000000 00000000132 13070134113 015776 x ustar 00 30 mtime=1491122251.492615127
30 atime=1491122251.492615127
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbrevolve.m 0000644 0001750 0001750 00000012772 13070134113 016165 0 ustar 00bect bect 0000000 0000000 function surf = nrbrevolve(curve,pnt,vec,theta)
%
% NRBREVOLVE: Construct a NURBS surface by revolving a NURBS curve, or
% construct a NURBS volume by revolving a NURBS surface.
%
% Calling Sequence:
%
% srf = nrbrevolve(crv,pnt,vec[,ang])
%
% INPUT:
%
% crv : NURBS curve or surface to revolve, see nrbmak.
%
% pnt : Coordinates of the point used to define the axis
% of rotation.
%
% vec : Vector defining the direction of the rotation axis.
%
% ang : Angle to revolve the curve, default 2*pi
%
% OUTPUT:
%
% srf : constructed surface or volume
%
% Description:
%
% Construct a NURBS surface by revolving the profile NURBS curve around
% an axis defined by a point and vector.
%
% Examples:
%
% Construct a sphere by rotating a semicircle around a x-axis.
%
% crv = nrbcirc(1.0,[0 0 0],0,pi);
% srf = nrbrevolve(crv,[0 0 0],[1 0 0]);
% nrbplot(srf,[20 20]);
%
% NOTE:
%
% The algorithm:
%
% 1) vectrans the point to the origin (0,0,0)
% 2) rotate the vector into alignment with the z-axis
%
% for each control point along the curve
%
% 3) determine the radius and angle of control
% point to the z-axis
% 4) construct a circular arc in the x-y plane with
% this radius and start angle and sweep angle theta
% 5) combine the arc and profile, coefs and weights.
%
% next control point
%
% 6) rotate and vectrans the surface back into position
% by reversing 1 and 2.
%
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin < 3)
error('Not enough arguments to construct revolved surface');
end
if (nargin < 4)
theta = 2.0*pi;
end
if (iscell (curve.knots) && numel(curve.knots) == 3)
error('The function nrbrevolve is not yet ready to create volumes')
end
% Translate curve the center point to the origin
if isempty(pnt)
pnt = zeros(3,1);
end
if length(pnt) ~= 3
error('All point and vector coordinates must be 3D');
end
% Translate and rotate the original curve or surface into alignment with the z-axis
T = vectrans(-pnt);
angx = vecangle(vec(1),vec(3));
RY = vecroty(-angx);
vectmp = RY*[vecnorm(vec(:));1.0];
angy = vecangle(vectmp(2),vectmp(3));
RX = vecrotx(angy);
curve = nrbtform(curve,RX*RY*T);
% Construct an arc
arc = nrbcirc(1.0,[],0.0,theta);
if (iscell (curve.knots))
% Construct the revolved volume
coefs = zeros([4 arc.number curve.number]);
angle = squeeze (vecangle(curve.coefs(2,:,:),curve.coefs(1,:,:)));
radius = squeeze (vecmag(curve.coefs(1:2,:,:)));
for i = 1:curve.number(1)
for j = 1:curve.number(2)
coefs(:,:,i,j) = vecrotz(angle(i,j))*vectrans([0.0 0.0 curve.coefs(3,i,j)])*...
vecscale([radius(i,j) radius(i,j)])*arc.coefs;
coefs(4,:,i,j) = coefs(4,:,i,j)*curve.coefs(4,i,j);
end
end
surf = nrbmak(coefs,{arc.knots, curve.knots{:}});
else
% Construct the revolved surface
coefs = zeros(4, arc.number, curve.number);
angle = vecangle(curve.coefs(2,:),curve.coefs(1,:));
radius = vecmag(curve.coefs(1:2,:));
for i = 1:curve.number
coefs(:,:,i) = vecrotz(angle(i))*vectrans([0.0 0.0 curve.coefs(3,i)])*...
vecscale([radius(i) radius(i)])*arc.coefs;
coefs(4,:,i) = coefs(4,:,i)*curve.coefs(4,i);
end
surf = nrbmak(coefs,{arc.knots, curve.knots});
end
% Rotate and vectrans the surface back into position
T = vectrans(pnt);
RX = vecrotx(-angy);
RY = vecroty(angx);
surf = nrbtform(surf,T*RY*RX);
end
%!demo
%! sphere = nrbrevolve(nrbcirc(1,[],0.0,pi),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbplot(sphere,[40 40],'light','on');
%! title('Ball and tori - surface construction by revolution');
%! hold on;
%! torus = nrbrevolve(nrbcirc(0.2,[0.9 1.0]),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbplot(torus,[40 40],'light','on');
%! nrbplot(nrbtform(torus,vectrans([-1.8])),[20 10],'light','on');
%! hold off;
%!demo
%! pnts = [3.0 5.5 5.5 1.5 1.5 4.0 4.5;
%! 0.0 0.0 0.0 0.0 0.0 0.0 0.0;
%! 0.5 1.5 4.5 3.0 7.5 6.0 8.5];
%! crv = nrbmak(pnts,[0 0 0 1/4 1/2 3/4 3/4 1 1 1]);
%!
%! xx = vecrotz(25*pi/180)*vecroty(15*pi/180)*vecrotx(20*pi/180);
%! nrb = nrbtform(crv,vectrans([5 5])*xx);
%!
%! pnt = [5 5 0]';
%! vec = xx*[0 0 1 1]';
%! srf = nrbrevolve(nrb,pnt,vec(1:3));
%!
%! p = nrbeval(srf,{linspace(0.0,1.0,100) linspace(0.0,1.0,100)});
%! surfl(squeeze(p(1,:,:)),squeeze(p(2,:,:)),squeeze(p(3,:,:)));
%! title('Construct of a 3D surface by revolution of a curve.');
%! shading interp;
%! colormap(copper);
%! axis equal;
%! hold off
%!demo
%! crv1 = nrbcirc(1,[0 0],0, pi/2);
%! crv2 = nrbcirc(2,[0 0],0, pi/2);
%! srf = nrbruled (crv1, crv2);
%! srf = nrbtform (srf, [1 0 0 0; 0 1 0 1; 0 0 1 0; 0 0 0 1]);
%! vol = nrbrevolve (srf, [0 0 0], [1 0 0], pi/2);
%! nrbplot(vol, [30 30 30], 'light', 'on')
nurbs-1.3.13/inst/PaxHeaders.26136/vecmag.m 0000644 0000000 0000000 00000000132 13070134113 015054 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecmag.m 0000644 0001750 0001750 00000002425 13070134113 015235 0 ustar 00bect bect 0000000 0000000 function mag = vecmag(vec)
%
% VECMAG: Magnitude of the vectors.
%
% Calling Sequence:
%
% mvec = vecmag(vec)
%
% INPUT:
%
% vec : An array of column vectors represented by a matrix of
% size (dim,nv), where is the dimension of the vector and
% nv the number of vectors.
%
% OUTPUT:
%
% mvec : Magnitude of the vectors, vector of size (1,nv).
%
% Description:
%
% Determines the magnitude of the vectors.
%
% Examples:
%
% Find the magnitude of the two vectors (0.0,2.0,1.3) and (1.5,3.4,2.3)
%
% mvec = vecmag([0.0 1.5; 2.0 3.4; 1.3 2.3]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
mag = sqrt(sum(vec.^2));
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbeval_der_w.m 0000644 0000000 0000000 00000000132 13070134113 016423 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbeval_der_w.m 0000644 0001750 0001750 00000011310 13070134113 016575 0 ustar 00bect bect 0000000 0000000 function der = nrbeval_der_w (nrb, i, points)
%
% NRBEVAL_DER_W: Compute the derivatives of a NURBS object at the point u
% with respect to the weight of the i-th control point.
%
% Calling Sequence:
%
% der = nrbeval_der_p (crv, i, u);
% der = nrbeval_der_p (srf, i, p);
% der = nrbeval_der_p (srf, i, {u v});
% der = nrbeval_der_p (vol, i, p);
% der = nrbeval_der_p (vol, i, {u v w});
%
% INPUT:
%
% crv - NURBS curve.
% srf - NURBS surface.
% vol - NURBS volume.
% i - Index of the control point.
% u or p(1,:,:) - parametric points along u direction
% v or p(2,:,:) - parametric points along v direction
% w or p(3,:,:) - parametric points along w direction
%
% OUTPUT:
%
% der - Derivatives.
% size(der) = [3, numel(u)] for curves
% or [3, numel(u)*numel(v)] for surfaces
% or [3, numel(u)*numel(v)*numel(w)] for volumes
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
if (iscell(points))
npts = prod (cellfun (@numel, points));
else
npts = size (points, 2);
end
der = zeros (3, npts);
[evalu, den] = nrbeval (nrb, points);
[N, I] = nrbbasisfun (points, nrb);
if (iscell (points))
evalu = reshape (evalu, size(evalu, 1), []);
den = reshape (den, 1, []);
end
% if (numel (nrb.number) == 1) % 1D
% I = I + 1; % id is 0-based
% end
[ii, jj, kk] = ind2sub (nrb.number, i);
w_i = nrb.coefs(4,ii,jj,kk);
P_i = nrb.coefs(1:3,ii,jj,kk) ./ w_i;
for ipnt = 1:npts
[is, loc] = ismember (i, I(ipnt,:));
if (is)
der(:,ipnt) = N(ipnt,loc) ./ w_i .* P_i - evalu(:,ipnt) .* N(ipnt,loc) ./ w_i ./ den(ipnt);
end
end
end
%!test % 1D
%! nrb = nrbkntins (nrbcirc (1, [0 0], 0, pi/2), .5);
%! u = linspace (0, 1, 11);
%! delta_w = .01;
%! n = nrb.number;
%! der_ex = zeros (3, numel (u), n);
%! der_fd = zeros (3, numel (u), n);
%! for iw = 1:n
%! new_w1 = nrb.coefs (4, iw) + delta_w;
%! new_w2 = nrb.coefs (4, iw) - delta_w;
%! nrb1 = nrbmodw (nrb, new_w1, iw);
%! nrb2 = nrbmodw (nrb, new_w2, iw);
%! der_ex(:,:,iw) = nrbeval_der_w (nrb, iw, u);
%! p2 = nrbeval (nrb2, u);
%! p1 = nrbeval (nrb1, u);
%! der_fd(:,:,iw) = -(p2 - p1) ./ (2*delta_w);
%! end
%! error = max (abs (der_ex(:) - der_fd(:)));
%! assert (error < 1.e-4)
%!
%!test %2D
%! crv = nrbline([1 0], [2 0]);
%! nrb = nrbtransp (nrbrevolve (crv, [], [0 0 1], pi/2));
%! new_knots = linspace (1/9, 8/9, 8);
%! nrb = nrbkntins (nrb, {new_knots, new_knots});
%! u = linspace (0, 1, 5);
%! v = u;
%! delta_w = .01;
%! n = nrb.number(1) * nrb.number(2);
%! der_ex = zeros (3, numel(u)* numel(v), n);
%! der_fd = zeros (3, numel(u)* numel(v), n);
%! for iw = 1:nrb.number
%! new_w1 = nrb.coefs (4, iw) + delta_w;
%! new_w2 = nrb.coefs (4, iw) - delta_w;
%! nrb1 = nrbmodw (nrb, new_w1, iw);
%! nrb2 = nrbmodw (nrb, new_w2, iw);
%! der_ex(:,:,iw) = nrbeval_der_w (nrb, iw, {u v});
%! p2 = nrbeval (nrb2, {u v});
%! p1 = nrbeval (nrb1, {u v});
%! der_fd(:,:,iw) = reshape (-(p2 - p1) ./ (2*delta_w), 3, []);
%! end
%! error = max (abs (der_ex(:) - der_fd(:)));
%! assert (error < 1.e-5)
%!
%!test % 3D
%! crv = nrbline([1 0], [2 0]);
%! nrb = nrbtransp (nrbrevolve (crv, [], [0 0 1], pi/2));
%! nrb = nrbextrude (nrb, [0 0 1]);
%! u = 0:.33:.99;
%! v = 0:.1:.9;
%! w = [.25 .5 .75];
%! delta_w = .01;
%! n = nrb.number(1) * nrb.number(2) * nrb.number(3);
%! der_ex = zeros (3, numel(u)*numel(v)*numel(w), n);
%! der_fd = zeros (3, numel(u)*numel(v)*numel(w), n);
%! for iw = 1:nrb.number
%! new_w1 = nrb.coefs (4, iw) + delta_w;
%! new_w2 = nrb.coefs (4, iw) - delta_w;
%! nrb1 = nrbmodw (nrb, new_w1, iw);
%! nrb2 = nrbmodw (nrb, new_w2, iw);
%! der_ex(:,:,iw) = nrbeval_der_w (nrb, iw, {u v w});
%! p2 = nrbeval (nrb2, {u v w});
%! p1 = nrbeval (nrb1, {u v w});
%! der_fd(:,:,iw) = reshape (-(p2 - p1) ./ (2*delta_w), 3, []);
%! end
%! error = max (max (squeeze (max (abs (der_ex - der_fd)))));
%! assert (error < 1.e-4)
nurbs-1.3.13/inst/PaxHeaders.26136/nrbeval.m 0000644 0000000 0000000 00000000132 13070134113 015243 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbeval.m 0000644 0001750 0001750 00000022235 13070134113 015425 0 ustar 00bect bect 0000000 0000000 function [p,w] = nrbeval(nurbs,tt)
%
% NRBEVAL: Evaluate a NURBS at parametric points.
%
% Calling Sequences:
%
% [p,w] = nrbeval(crv,ut)
% [p,w] = nrbeval(srf,{ut,vt})
% [p,w] = nrbeval(vol,{ut,vt,wt})
% [p,w] = nrbeval(srf,pts)
%
% INPUT:
%
% crv : NURBS curve, see nrbmak.
%
% srf : NURBS surface, see nrbmak.
%
% vol : NURBS volume, see nrbmak.
%
% ut : Parametric evaluation points along U direction.
%
% vt : Parametric evaluation points along V direction.
%
% wt : Parametric evaluation points along W direction.
%
% pts : Array of scattered points in parametric domain
%
% OUTPUT:
%
% p : Evaluated points on the NURBS curve, surface or volume as
% Cartesian coordinates (x,y,z). If w is included on the lhs argument
% list the points are returned as homogeneous coordinates (wx,wy,wz).
%
% w : Weights of the homogeneous coordinates of the evaluated
% points. Note inclusion of this argument changes the type
% of coordinates returned in p (see above).
%
% Description:
%
% Evaluation of NURBS curves, surfaces or volume at parametric points along
% the U, V and W directions. Either homogeneous coordinates are returned
% if the weights are requested in the lhs arguments, or as Cartesian coordinates.
% This function utilises the 'C' interface bspeval.
%
% Examples:
%
% Evaluate the NURBS circle at twenty points from 0.0 to 1.0
%
% nrb = nrbcirc;
% ut = linspace(0.0,1.0,20);
% p = nrbeval(nrb,ut);
%
% See also:
%
% bspeval
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2010 Carlo de Falco
% Copyright (C) 2010, 2011, 2015 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin < 2)
error('Not enough input arguments');
end
foption = 1; % output format 3D cartesian coordinates
if (nargout == 2)
foption = 0; % output format 4D homogenous coordinates
end
if (~isstruct(nurbs))
error('NURBS representation is not structure!');
end
if (~strcmp(nurbs.form,'B-NURBS'))
error('Not a recognised NURBS representation');
end
if (iscell(nurbs.knots))
if (size(nurbs.knots,2) == 3)
%% NURBS structure represents a volume
num1 = nurbs.number(1);
num2 = nurbs.number(2);
num3 = nurbs.number(3);
degree = nurbs.order-1;
if (iscell(tt))
nt1 = numel (tt{1});
nt2 = numel (tt{2});
nt3 = numel (tt{3});
%% evaluate along the w direction
val = reshape (nurbs.coefs, 4*num1*num2, num3);
val = bspeval (degree(3), val, nurbs.knots{3}, tt{3});
val = reshape (val, [4 num1 num2 nt3]);
%% Evaluate along the v direction
val = permute (val, [1 2 4 3]);
val = reshape (val, 4*num1*nt3, num2);
val = bspeval (degree(2), val, nurbs.knots{2}, tt{2});
val = reshape (val, [4 num1 nt3 nt2]);
val = permute (val, [1 2 4 3]);
%% Evaluate along the u direction
val = permute (val, [1 3 4 2]);
val = reshape (val, 4*nt2*nt3, num1);
val = bspeval (degree(1), val, nurbs.knots{1}, tt{1});
val = reshape (val, [4 nt2 nt3 nt1]);
val = permute (val, [1 4 2 3]);
pnts = val;
p = pnts(1:3,:,:,:);
w = pnts(4,:,:,:);
if (foption)
p = p./repmat(w,[3 1 1 1]);
end
else
%% Evaluate at scattered points
%% tt(1,:) represents the u direction
%% tt(2,:) represents the v direction
%% tt(3,:) represents the w direction
st = size(tt);
if (st(1) ~= 3 && st(2) == 3 && numel(st) == 2)
tt = tt';
st = size (tt);
end
nt = prod(st(2:end));
tt = reshape (tt, [3, nt]);
%% evaluate along the w direction
val = reshape(nurbs.coefs,4*num1*num2,num3);
val = bspeval(degree(3),val,nurbs.knots{3},tt(3,:));
val = reshape(val,[4 num1 num2 nt]);
%% evaluate along the v direction
val2 = zeros(4*num1,nt);
for v = 1:nt
coefs = reshape(val(:,:,:,v),4*num1,num2);
val2(:,v) = bspeval(degree(2),coefs,nurbs.knots{2},tt(2,v));
end
val2 = reshape(val2,[4 num1 nt]);
%% evaluate along the u direction
pnts = zeros(4,nt);
for v = 1:nt
coefs = reshape (val2(:,:,v), [4 num1]);
pnts(:,v) = bspeval(degree(1),coefs,nurbs.knots{1},tt(1,v));
end
w = pnts(4,:);
p = pnts(1:3,:);
if (foption)
p = p./repmat(w,[3, 1]);
end
if (numel(st) ~= 2)
w = reshape (w, [st(2:end)]);
p = reshape (p, [3, st(2:end)]);
end
end
elseif (size(nurbs.knots,2) == 2)
%% NURBS structure represents a surface
num1 = nurbs.number(1);
num2 = nurbs.number(2);
degree = nurbs.order-1;
if (iscell(tt))
%% Evaluate over a [u,v] grid
%% tt{1} represents the u direction
%% tt{2} represents the v direction
nt1 = length(tt{1});
nt2 = length(tt{2});
%% Evaluate along the v direction
val = reshape(nurbs.coefs,4*num1,num2);
val = bspeval(degree(2),val,nurbs.knots{2},tt{2});
val = reshape(val,[4 num1 nt2]);
%% Evaluate along the u direction
val = permute(val,[1 3 2]);
val = reshape(val,4*nt2,num1);
val = bspeval(degree(1),val,nurbs.knots{1},tt{1});
val = reshape(val,[4 nt2 nt1]);
val = permute(val,[1 3 2]);
w = val(4,:,:);
p = val(1:3,:,:);
if (foption)
p = p./repmat(w,[3 1 1]);
end
else
%% Evaluate at scattered points
%% tt(1,:) represents the u direction
%% tt(2,:) represents the v direction
st = size(tt);
if (st(1) ~= 2 && st(2) == 2 && numel(st) == 2)
tt = tt';
st = size (tt);
end
nt = prod(st(2:end));
tt = reshape (tt, [2, nt]);
val = reshape(nurbs.coefs,4*num1,num2);
val = bspeval(degree(2),val,nurbs.knots{2},tt(2,:));
val = reshape(val,[4 num1 nt]);
%% evaluate along the u direction
pnts = zeros(4,nt);
for v = 1:nt
coefs = reshape (val(:,:,v), [4 num1]);
pnts(:,v) = bspeval(degree(1),coefs,nurbs.knots{1},tt(1,v));
end
w = pnts(4,:);
p = pnts(1:3,:);
if (foption)
p = p./repmat(w,[3, 1]);
end
if (numel(st) ~= 2)
w = reshape (w, [st(2:end)]);
p = reshape (p, [3, st(2:end)]);
end
end
end
else
%% NURBS structure represents a curve
%% tt represent a vector of parametric points in the u direction
if (iscell (tt) && numel (tt) == 1)
tt = cell2mat (tt);
end
st = size (tt);
val = bspeval(nurbs.order-1,nurbs.coefs,nurbs.knots,tt(:)');
w = val(4,:);
p = val(1:3,:);
if foption
p = p./repmat(w,3,1);
end
if (st(1) ~= 1 || numel(st) ~= 2)
w = reshape (w, st);
p = reshape (p, [3, st]);
end
end
end
%!demo
%! srf = nrbtestsrf;
%! p = nrbeval(srf,{linspace(0.0,1.0,20) linspace(0.0,1.0,20)});
%! h = surf(squeeze(p(1,:,:)),squeeze(p(2,:,:)),squeeze(p(3,:,:)));
%! title('Test surface.');
%! hold off
%!test
%! knots{1} = [0 0 0 1 1 1];
%! knots{2} = [0 0 0 .5 1 1 1];
%! knots{3} = [0 0 0 0 1 1 1 1];
%! cx = [0 0.5 1]; nx = length(cx);
%! cy = [0 0.25 0.75 1]; ny = length(cy);
%! cz = [0 1/3 2/3 1]; nz = length(cz);
%! coefs(1,:,:,:) = repmat(reshape(cx,nx,1,1),[1 ny nz]);
%! coefs(2,:,:,:) = repmat(reshape(cy,1,ny,1),[nx 1 nz]);
%! coefs(3,:,:,:) = repmat(reshape(cz,1,1,nz),[nx ny 1]);
%! coefs(4,:,:,:) = 1;
%! nurbs = nrbmak(coefs, knots);
%! x = rand(5,1); y = rand(5,1); z = rand(5,1);
%! tt = [x y z]';
%! points = nrbeval(nurbs,tt);
%!
%! assert(points,tt,1e-10)
%!
%!test
%! knots{1} = [0 0 0 1 1 1];
%! knots{2} = [0 0 0 0 1 1 1 1];
%! knots{3} = [0 0 1 1];
%! cx = [0 0 1]; nx = length(cx);
%! cy = [0 0 0 1]; ny = length(cy);
%! cz = [0 1]; nz = length(cz);
%! coefs(1,:,:,:) = repmat(reshape(cx,nx,1,1),[1 ny nz]);
%! coefs(2,:,:,:) = repmat(reshape(cy,1,ny,1),[nx 1 nz]);
%! coefs(3,:,:,:) = repmat(reshape(cz,1,1,nz),[nx ny 1]);
%! coefs(4,:,:,:) = 1;
%! nurbs = nrbmak(coefs, knots);
%! x = rand(5,1); y = rand(5,1); z = rand(5,1);
%! tt = [x y z]';
%! points = nrbeval(nurbs,tt);
%! assert(points,[x.^2 y.^3 z]',1e-10);
%!
%!test
%! knots{1} = [0 0 0 1 1 1];
%! knots{2} = [0 0 0 0 1 1 1 1];
%! knots{3} = [0 0 1 1];
%! cx = [0 0 1]; nx = length(cx);
%! cy = [0 0 0 1]; ny = length(cy);
%! cz = [0 1]; nz = length(cz);
%! coefs(1,:,:,:) = repmat(reshape(cx,nx,1,1),[1 ny nz]);
%! coefs(2,:,:,:) = repmat(reshape(cy,1,ny,1),[nx 1 nz]);
%! coefs(3,:,:,:) = repmat(reshape(cz,1,1,nz),[nx ny 1]);
%! coefs(4,:,:,:) = 1;
%! coefs = coefs([2 1 3 4],:,:,:);
%! nurbs = nrbmak(coefs, knots);
%! x = rand(5,1); y = rand(5,1); z = rand(5,1);
%! tt = [x y z]';
%! points = nrbeval(nurbs,tt);
%! [y.^3 x.^2 z]';
%! assert(points,[y.^3 x.^2 z]',1e-10);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbexport.m 0000644 0000000 0000000 00000000132 13070134113 015635 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbexport.m 0000644 0001750 0001750 00000012340 13070134113 016013 0 ustar 00bect bect 0000000 0000000 function nrbexport (varargin)
%
% NRBEXPORT: export NURBS geometries to a format compatible with the one used in GeoPDEs.
%
% Calling Sequence:
%
% nrbexport (nurbs, filename);
% nrbexport (nurbs, interfaces, boundaries, filename);
% nrbexport (nurbs, interfaces, boundaries, subdomains, filename);
% nrbexport (nurbs, filename, version);
% nrbexport (nurbs, interfaces, boundaries, filename, version);
% nrbexport (nurbs, interfaces, boundaries, subdomains, filename, version);
%
% INPUT:
%
% nurbs : NURBS curve, surface or volume, see nrbmak.
% interfaces: interface information for GeoPDEs (see nrbmultipatch)
% boundaries: boundary information for GeoPDEs (see nrbmultipatch)
% filename : name of the output file.
% version : either '-V0.7' or '-V2.1', to select the file format
%
%
% Description:
%
% The data of the nurbs structure is written in the file, in a format
% that can be read by GeoPDEs. By default, the file is saved in the
% format used by GeoPDEs 2.1. For the format of GeoPDEs 2.0 use the
% option '-v0.7'. Earlier versions of GeoPDEs are not supported.
%
% Copyright (C) 2011, 2014, 2015 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (strcmpi (varargin{end}, '-v0.7'))
version = '0.7';
else
version = '2.1';
end
if (nargin == 2 || nargin == 3)
nurbs = varargin{1};
filename = varargin{2};
if (numel (nurbs) > 1)
warning ('Automatically creating the interface information with nrbmultipatch')
[interfaces, boundaries] = nrbmultipatch (nurbs);
subdomains = [];
else
interfaces = []; boundaries = []; subdomains = [];
end
elseif (nargin == 4 || (nargin == 5 && ischar(varargin{4})))
nurbs = varargin{1};
interfaces = varargin{2};
boundaries = varargin{3};
filename = varargin{4};
subdomains = [];
elseif (nargin == 6 || (nargin == 5 && ~ischar(varargin{4})))
nurbs = varargin{1};
interfaces = varargin{2};
boundaries = varargin{3};
subdomains = varargin{4};
filename = varargin{5};
else
error ('nrbexport: wrong number of input arguments')
end
fid = fopen (filename, 'w');
if (fid < 0)
error ('nrbexport: cannot open file %s', filename);
end
ndim = numel (nurbs(1).order);
npatch = numel (nurbs);
rdim = 1;
if (strcmp (version, '0.7'))
rdim = ndim;
else
for iptc = 1:npatch
if (any (abs(nurbs(iptc).coefs(3,:)) > 1e-12))
rdim = 3;
break
elseif (any (abs(nurbs(iptc).coefs(2,:)) > 1e-12))
rdim = 2;
end
end
end
if (strcmp (version, '0.7'))
fprintf (fid, '%s\n', '# nurbs mesh v.0.7');
else
fprintf (fid, '%s\n', '# nurbs mesh v.2.1');
end
fprintf (fid, '%s\n', '#');
fprintf (fid, '%s\n', ['# ' date]);
fprintf (fid, '%s\n', '#');
if (strcmp (version, '0.7'))
fprintf (fid, '%i ', ndim, npatch, numel(interfaces), numel(subdomains));
else
fprintf (fid, '%i ', ndim, rdim, npatch, numel(interfaces), numel(subdomains));
end
fprintf (fid, '\n');
for iptc = 1:npatch
fprintf (fid, '%s %i \n', 'PATCH', iptc);
fprintf (fid, '%i ', nurbs(iptc).order-1);
fprintf (fid, '\n');
fprintf (fid, '%i ', nurbs(iptc).number);
fprintf (fid, '\n');
if (iscell (nurbs(iptc).knots))
for ii = 1:ndim
fprintf (fid, '%1.15f ', nurbs(iptc).knots{ii});
fprintf (fid, '\n');
end
else
fprintf (fid, '%1.15f ', nurbs(iptc).knots);
fprintf (fid, '\n');
end
for ii = 1:rdim
fprintf (fid, '%1.15f ', nurbs(iptc).coefs(ii,:,:));
fprintf (fid, '\n');
end
fprintf (fid, '%1.15f ', nurbs(iptc).coefs(4,:,:));
fprintf (fid, '\n');
end
for intrfc = 1:numel(interfaces)
if (isfield (interfaces, 'ref'))
fprintf (fid, '%s \n', interfaces(intrfc).ref);
else
fprintf (fid, '%s %i \n', 'INTERFACE', intrfc);
end
fprintf (fid, '%i %i \n', interfaces(intrfc).patch1, interfaces(intrfc).side1);
fprintf (fid, '%i %i \n', interfaces(intrfc).patch2, interfaces(intrfc).side2);
if (ndim == 2)
fprintf (fid, '%i \n', interfaces(intrfc).ornt);
elseif (ndim == 3)
fprintf (fid, '%i %i %i \n', interfaces(intrfc).flag, interfaces(intrfc).ornt1, interfaces(intrfc).ornt2);
end
end
for isubd = 1:numel(subdomains)
% The subdomain part should be fixed
fprintf (fid, '%s \n', subdomains(isubd).name);
fprintf (fid, '%i ', subdomains(isubd).patches);
fprintf (fid, '\n');
end
for ibnd = 1:numel (boundaries)
if (isfield (boundaries, 'name'))
fprintf (fid, '%s \n', boundaries(ibnd).name);
else
fprintf (fid, '%s %i \n', 'BOUNDARY', ibnd);
end
fprintf (fid, '%i \n', boundaries(ibnd).nsides);
for ii = 1:boundaries(ibnd).nsides
fprintf (fid, '%i %i \n', boundaries(ibnd).patches(ii), boundaries(ibnd).faces(ii));
end
end
fclose (fid);
end
nurbs-1.3.13/inst/PaxHeaders.26136/vecnorm.m 0000644 0000000 0000000 00000000132 13070134113 015263 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/vecnorm.m 0000644 0001750 0001750 00000002600 13070134113 015437 0 ustar 00bect bect 0000000 0000000 function nvec = vecnorm(vec)
%
% VECNORM: Normalise the vectors.
%
% Calling Sequence:
%
% nvec = vecnorn(vec);
%
% INPUT:
%
% vec : An array of column vectors represented by a matrix of
% size (dim,nv), where is the dimension of the vector and
% nv the number of vectors.
%
% OUTPUT:
%
% nvec : Normalised vectors, matrix the smae size as vec.
%
% Description:
%
% Normalises the array of vectors, returning the unit vectors.
%
% Examples:
%
% Normalise the two vectors (0.0,2.0,1.3) and (1.5,3.4,2.3)
%
% nvec = vecnorm([0.0 1.5; 2.0 3.4; 1.3 2.3]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
nvec = vec./repmat(sqrt(sum(vec.^2)),[size(vec,1) ones(1,ndims(vec)-1)]);
end
nurbs-1.3.13/inst/PaxHeaders.26136/tbasisfun.m 0000644 0000000 0000000 00000000132 13070134113 015610 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/tbasisfun.m 0000644 0001750 0001750 00000007611 13070134113 015773 0 ustar 00bect bect 0000000 0000000 function [N, Nder] = tbasisfun (u, p, U)
%
% TBASISFUN: Compute a B- or T-Spline basis function, and its derivatives, from its local knot vector.
%
% usage:
%
% [N, Nder] = tbasisfun (u, p, U)
% [N, Nder] = tbasisfun ([u; v], [p q], {U, V})
% [N, Nder] = tbasisfun ([u; v; w], [p q r], {U, V, W})
%
% INPUT:
%
% u or [u; v] : points in parameter space where the basis function is to be
% evaluated
%
% U or {U, V} : local knot vector
%
% p or [p q] : polynomial degree of the basis function
%
% OUTPUT:
%
% N : basis function evaluated at the given parametric points
% Nder : basis function gradient evaluated at the given parametric points
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2012 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (~ iscell (U))
U = sort (U);
if (numel (U) ~= p+2)
error ('tbasisfun: knot vector and degree do not correspond')
end
if (nargout == 1)
N = onebasisfun__ (u, p, U);
else
[N, Nder] = onebasisfunder__ (u, p, U);
end
elseif (size(U,2) == 2)
U{1} = sort(U{1}); U{2} = sort(U{2});
if (numel(U{1}) ~= p(1)+2 || numel(U{2}) ~= p(2)+2)
error ('tbasisfun: knot vector and degree do not correspond')
end
if (nargout == 1)
Nu = onebasisfun__ (u(1,:), p(1), U{1});
Nv = onebasisfun__ (u(2,:), p(2), U{2});
N = Nu.*Nv;
elseif (nargout == 2)
[Nu, Ndu] = onebasisfunder__ (u(1,:), p(1), U{1});
[Nv, Ndv] = onebasisfunder__ (u(2,:), p(2), U{2});
N = Nu.*Nv;
Nder(1,:) = Ndu.*Nv;
Nder(2,:) = Nu.*Ndv;
end
elseif (size(U,2) == 3)
U{1} = sort(U{1}); U{2} = sort(U{2}); U{3} = sort(U{3});
if (numel(U{1}) ~= p(1)+2 || numel(U{2}) ~= p(2)+2 || numel(U{3}) ~= p(3)+2)
error ('tbasisfun: knot vector and degree do not correspond')
end
if (nargout == 1)
Nu = onebasisfun__ (u(1,:), p(1), U{1});
Nv = onebasisfun__ (u(2,:), p(2), U{2});
Nw = onebasisfun__ (u(3,:), p(3), U{3});
N = Nu.*Nv.*Nw;
else
[Nu, Ndu] = onebasisfunder__ (u(1,:), p(1), U{1});
[Nv, Ndv] = onebasisfunder__ (u(2,:), p(2), U{2});
[Nw, Ndw] = onebasisfunder__ (u(3,:), p(3), U{3});
N = Nu.*Nv.*Nw;
Nder(1,:) = Ndu.*Nv.*Nw;
Nder(2,:) = Nu.*Ndv.*Nw;
Nder(3,:) = Nu.*Nv.*Ndw;
end
end
end
%!demo
%! U = {[0 0 1/2 1 1], [0 0 0 1 1]};
%! p = [3, 3];
%! [X, Y] = meshgrid (linspace(0, 1, 30));
%! u = [X(:), Y(:)]';
%! N = tbasisfun (u, p, U);
%! surf (X, Y, reshape (N, size(X)))
%! title('Basis function associated to a local knot vector')
%! hold off
%!test
%! U = [0 1/2 1];
%! p = 1;
%! u = [0.3 0.4 0.6 0.7];
%! [N, Nder] = tbasisfun (u, p, U);
%! assert (N, [0.6 0.8 0.8 0.6], 1e-12);
%! assert (Nder, [2 2 -2 -2], 1e-12);
%!test
%! U = {[0 1/2 1] [0 1/2 1]};
%! p = [1 1];
%! u = [0.3 0.4 0.6 0.7; 0.3 0.4 0.6 0.7];
%! [N, Nder] = tbasisfun (u, p, U);
%! assert (N, [0.36 0.64 0.64 0.36], 1e-12);
%! assert (Nder, [1.2 1.6 -1.6 -1.2; 1.2 1.6 -1.6 -1.2], 1e-12);
%!test
%! U = {[0 1/2 1] [0 1/2 1] [0 1/2 1]};
%! p = [1 1 1];
%! u = [0.4 0.4 0.6 0.6; 0.4 0.4 0.6 0.6; 0.4 0.6 0.4 0.6];
%! [N, Nder] = tbasisfun (u, p, U);
%! assert (N, [0.512 0.512 0.512 0.512], 1e-12);
%! assert (Nder, [1.28 1.28 -1.28 -1.28; 1.28 1.28 -1.28 -1.28; 1.28 -1.28 1.28 -1.28], 1e-12);
nurbs-1.3.13/inst/PaxHeaders.26136/aveknt.m 0000644 0000000 0000000 00000000132 13070134113 015102 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/aveknt.m 0000644 0001750 0001750 00000005224 13070134113 015263 0 ustar 00bect bect 0000000 0000000 function pts = aveknt (varargin)
% AVEKNT: compute the knot averages (Greville points) of a knot vector
%
% Calling Sequence:
%
% pts = aveknt (knt, p)
% pts = aveknt (nrb)
%
% INPUT:
%
% knt - knot sequence
% p - spline order (degree + 1)
% nrb - NURBS structure (see nrbmak)
%
% OUTPUT:
%
% pts - average knots. If the input is a NURBS, it gives a cell-array,
% with the average knots in each direction
%
% See also:
%
% Copyright (C) 2016 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin == 1)
if (isfield (varargin{1}, 'form'))
nrb = varargin{1};
knt = nrb.knots;
order = nrb.order;
else
error ('The input should be a NURBS structure, or a knot vector and the order. See the help for details')
end
elseif (nargin == 2)
knt = varargin{1};
order = varargin{2};
else
error ('The input should be a NURBS structure, or a knot vector and the order. See the help for details')
end
onedim = false;
if (~iscell (knt))
knt = {knt};
onedim = true;
end
ndim = numel (knt);
pts = cell (ndim, 1);
for idim = 1:ndim
if (numel (knt{idim}) < order(idim)+1)
error ('The knot vector must contain at least p+2 knots, with p the degree')
end
knt_aux = repmat (knt{idim}(2:end-1), 1, order(idim)-1);
knt_aux = [knt_aux(:); zeros(order(idim)-1, 1)];
knt_aux = reshape (knt_aux, [], order(idim)-1);
pts{idim} = sum (knt_aux.', 1) / (order(idim)-1);
pts{idim} = pts{idim}(1:end-order(idim)+1);
end
if (onedim)
pts = pts{1};
end
end
%!test
%! knt = [0 0 0 0.5 1 1 1];
%! pts = aveknt (knt, 3);
%! assert (pts - [0 1/4 3/4 1] < 1e-14)
%!
%!test
%! knt = {[0 0 0 0.5 1 1 1] [0 0 0 0 1/3 2/3 1 1 1 1]};
%! pts = aveknt (knt, [3 4]);
%! assert (pts{1} - [0 1/4 3/4 1] < 1e-14);
%! assert (pts{2} - [0 1/9 1/3 2/3 8/9 1] < 1e-14);
%!
%!test
%! nrb = nrb4surf([0 0], [1 0], [0 1], [1 1]);
%! nrb = nrbkntins (nrbdegelev (nrb, [1 2]), {[1/2] [1/3 2/3]});
%! pts = aveknt (nrb);
%! assert (pts{1} - [0 1/4 3/4 1] < 1e-14);
%! assert (pts{2} - [0 1/9 1/3 2/3 8/9 1] < 1e-14);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbmodw.m 0000644 0000000 0000000 00000000132 13070134113 015262 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbmodw.m 0000644 0001750 0001750 00000002667 13070134113 015453 0 ustar 00bect bect 0000000 0000000 function mnrb = nrbmodw (nrb, new_w, index)
%
% NRBMODW: Modify the weights of specific control points of any NURBS map.
%
% Calling Sequence:
%
% nrb = nrbmodw (nrb, new_w, index);
%
% INPUT:
%
% nrb - NURBS map to be modified.
% new_w - vector specifying the new weigths.
% index - indices of the control points to be modified.
%
% OUTPUT:
%
% mnrb - the modified NURBS.
%
% Copyright (C) 2015 Jacopo Corno
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
%
mnrb = nrb;
[ii, jj, kk] = ind2sub (nrb.number, index);
for count = 1:numel (ii)
mnrb.coefs(:,ii(count),jj(count),kk(count)) = ...
[nrb.coefs(1:3,ii(count),jj(count),kk(count))./repmat(nrb.coefs(4,ii(count),jj(count),kk(count)),3,1).*new_w(count); new_w(count)];
end
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbkntplot.m 0000644 0000000 0000000 00000000132 13070134113 016007 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbkntplot.m 0000644 0001750 0001750 00000017500 13070134113 016170 0 ustar 00bect bect 0000000 0000000 function nrbkntplot (nurbs)
% NRBKNTPLOT: Plot a NURBS entity with the knots subdivision.
%
% Calling Sequence:
%
% nrbkntplot(nurbs)
%
% INPUT:
%
% nurbs: NURBS curve, surface or volume, see nrbmak.
%
% Example:
%
% Plot the test surface with its knot vector
%
% nrbkntplot(nrbtestsrf)
%
% See also:
%
% nrbctrlplot
%
% Copyright (C) 2011, 2012 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if (nargin < 1)
error ('nrbkntplot: Need a NURBS to plot!');
end
% Default values
light='on';
cmap='summer';
colormap (cmap);
hold_flag = ishold;
if (iscell (nurbs.knots))
if (size (nurbs.knots,2) == 2) % plot a NURBS surface
nsub = 100;
nrbplot (nurbs, [nsub nsub], 'light', light, 'colormap', cmap);
hold on
% And plot the knots
knt1 = unique (nurbs.knots{1}(nurbs.order(1):end-nurbs.order(1)+1));
knt2 = unique (nurbs.knots{2}(nurbs.order(2):end-nurbs.order(2)+1));
p1 = nrbeval (nurbs, {knt1, linspace(knt2(1),knt2(end),nsub)});
p2 = nrbeval (nurbs, {linspace(knt1(1),knt1(end),nsub), knt2});
if (any (nurbs.coefs(3,:)))
% surface in a 3D space
for ii = 1:numel(knt1)
plot3 (squeeze(p1(1,ii,:)), squeeze(p1(2,ii,:)), squeeze(p1(3,ii,:)),'k');
end
for ii = 1:numel(knt2)
plot3 (squeeze(p2(1,:,ii)), squeeze(p2(2,:,ii)), squeeze(p2(3,:,ii)),'k');
end
else
% plain surface
for ii = 1:numel(knt1)
plot (squeeze(p1(1,ii,:)), squeeze (p1(2,ii,:)),'k');
end
for ii = 1:numel(knt2)
plot (p2(1,:,ii),p2(2,:,ii),'k');
end
end
elseif (size (nurbs.knots,2) == 3) % plot a NURBS volume
% Plot the boundaries
bnd = nrbextract (nurbs);
nrbkntplot (bnd(1));
hold on
for iface = 2:6
nrbkntplot (bnd(iface));
end
end
else % plot a NURBS curve
nsub = 1000;
nrbplot (nurbs, nsub);
hold on
% And plot the knots
order = nurbs.order;
p = nrbeval (nurbs, unique (nurbs.knots(order:end-order+1)));
if (any (nurbs.coefs(3,:))) % plot a 3D curve
plot3 (p(1,:), p(2,:), p(3,:), 'rx');
else % plot a 2D curve
plot (p(1,:), p(2,:), 'rx');
end
end
if (~hold_flag)
hold off
end
end
%!demo
%! crv = nrbtestcrv;
%! nrbkntplot(crv)
%! title('Test curve')
%! hold off
%!demo
%! sphere = nrbrevolve(nrbcirc(1,[],0.0,pi),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbkntplot(sphere);
%! title('Ball and torus - surface construction by revolution');
%! hold on;
%! torus = nrbrevolve(nrbcirc(0.2,[0.9 1.0]),[0.0 0.0 0.0],[1.0 0.0 0.0]);
%! nrbkntplot(torus);
%! hold off
%!demo
%! knots = {[0 0 0 1/2 1 1 1] [0 0 0 1 1 1]...
%! [0 0 0 1/6 2/6 1/2 1/2 4/6 5/6 1 1 1]};
%!
%! coefs = [-1.0000 -0.9734 -0.7071 1.4290 1.0000 3.4172
%! 0 2.4172 0 0.0148 -2.0000 -1.9734
%! 0 2.0000 4.9623 9.4508 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -0.8536 0 -0.6036 1.9571 1.2071 3.5000
%! 0.3536 2.5000 0.2500 0.5429 -1.7071 -1.0000
%! 0 2.0000 4.4900 8.5444 3.4142 2.0000
%! 0.8536 1.0000 0.6036 1.0000 0.8536 1.0000
%! -0.3536 -4.0000 -0.2500 -1.2929 1.7071 1.0000
%! 0.8536 0 0.6036 -2.7071 -1.2071 -5.0000
%! 0 2.0000 4.4900 10.0711 3.4142 2.0000
%! 0.8536 1.0000 0.6036 1.0000 0.8536 1.0000
%! 0 -4.0000 0 0.7071 2.0000 5.0000
%! 1.0000 4.0000 0.7071 -0.7071 -1.0000 -5.0000
%! 0 2.0000 4.9623 14.4142 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -2.5000 -4.0000 -1.7678 0.7071 1.0000 5.0000
%! 0 4.0000 0 -0.7071 -3.5000 -5.0000
%! 0 2.0000 6.0418 14.4142 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -2.4379 0 -1.7238 2.7071 1.9527 5.0000
%! 0.9527 4.0000 0.6737 1.2929 -3.4379 -1.0000
%! 0 2.0000 6.6827 10.0711 4.0000 2.0000
%! 1.0000 1.0000 0.7071 1.0000 1.0000 1.0000
%! -0.9734 -1.0000 -0.6883 0.7071 3.4172 1.0000
%! 2.4172 0 1.7092 -1.4142 -1.9734 -2.0000
%! 0 4.0000 6.6827 4.9623 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! 0 -0.8536 0 0.8536 3.5000 1.2071
%! 2.5000 0.3536 1.7678 -1.2071 -1.0000 -1.7071
%! 0 3.4142 6.0418 4.4900 4.0000 0
%! 1.0000 0.8536 0.7071 0.6036 1.0000 0.8536
%! -4.0000 -0.3536 -2.8284 1.2071 1.0000 1.7071
%! 0 0.8536 0 -0.8536 -5.0000 -1.2071
%! 0 3.4142 7.1213 4.4900 4.0000 0
%! 1.0000 0.8536 0.7071 0.6036 1.0000 0.8536
%! -4.0000 0 -2.8284 1.4142 5.0000 2.0000
%! 4.0000 1.0000 2.8284 -0.7071 -5.0000 -1.0000
%! 0 4.0000 10.1924 4.9623 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! -4.0000 -2.5000 -2.8284 0.7071 5.0000 1.0000
%! 4.0000 0 2.8284 -2.4749 -5.0000 -3.5000
%! 0 4.0000 10.1924 6.0418 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! 0 -2.4379 0 1.3808 5.0000 1.9527
%! 4.0000 0.9527 2.8284 -2.4309 -1.0000 -3.4379
%! 0 4.0000 7.1213 6.6827 4.0000 0
%! 1.0000 1.0000 0.7071 0.7071 1.0000 1.0000
%! -1.0000 -0.9734 0.2071 2.4163 1.0000 3.4172
%! 0 2.4172 -1.2071 -1.3954 -2.0000 -1.9734
%! 2.0000 4.0000 7.0178 6.6827 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -0.8536 0 0.3536 2.4749 1.2071 3.5000
%! 0.3536 2.5000 -0.8536 -0.7071 -1.7071 -1.0000
%! 1.7071 4.0000 6.3498 6.0418 1.7071 0
%! 0.8536 1.0000 0.8536 0.7071 0.8536 1.0000
%! -0.3536 -4.0000 0.8536 0.7071 1.7071 1.0000
%! 0.8536 0 -0.3536 -3.5355 -1.2071 -5.0000
%! 1.7071 4.0000 6.3498 7.1213 1.7071 0
%! 0.8536 1.0000 0.8536 0.7071 0.8536 1.0000
%! 0 -4.0000 1.2071 3.5355 2.0000 5.0000
%! 1.0000 4.0000 -0.2071 -3.5355 -1.0000 -5.0000
%! 2.0000 4.0000 7.0178 10.1924 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -2.5000 -4.0000 -0.5429 3.5355 1.0000 5.0000
%! 0 4.0000 -1.9571 -3.5355 -3.5000 -5.0000
%! 2.0000 4.0000 8.5444 10.1924 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000
%! -2.4379 0 -0.0355 3.5355 1.9527 5.0000
%! 0.9527 4.0000 -1.4497 -0.7071 -3.4379 -1.0000
%! 2.0000 4.0000 9.4508 7.1213 2.0000 0
%! 1.0000 1.0000 1.0000 0.7071 1.0000 1.0000];
%! coefs = reshape (coefs, 4, 4, 3, 9);
%! horseshoe = nrbmak (coefs, knots);
%! nrbkntplot (horseshoe);
nurbs-1.3.13/inst/PaxHeaders.26136/veccross.m 0000644 0000000 0000000 00000000132 13070134113 015441 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/veccross.m 0000644 0001750 0001750 00000003431 13070134113 015620 0 ustar 00bect bect 0000000 0000000 function cross = veccross(vec1,vec2)
%
% VECCROSS: The cross product of two vectors.
%
% Calling Sequence:
%
% cross = veccross(vec1,vec2);
%
% INPUT:
%
% vec1 : An array of column vectors represented by a matrix of
% vec2 size (dim,nv), where is the dimension of the vector and
% nv the number of vectors.
%
% OUTPUT:
%
% cross : Array of column vectors, each element is corresponding
% to the cross product of the respective components in vec1
% and vec2.
%
% Description:
%
% Cross product of two vectors.
%
% Examples:
%
% Determine the cross products of:
% (2.3,3.4,5.6) and (1.2,4.5,1.2)
% (5.1,0.0,2.3) and (2.5,3.2,4.0)
%
% cross = veccross([2.3 5.1; 3.4 0.0; 5.6 2.3],[1.2 2.5; 4.5 3.2; 1.2 4.0]);
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if size(vec1,1) == 2
% 2D vector
cross = zeros(size(vec1));
cross(3,:) = vec1(1,:).*vec2(2,:)-vec1(2,:).*vec2(1,:);
else
% 3D vector
cross = [vec1(2,:).*vec2(3,:)-vec1(3,:).*vec2(2,:);
vec1(3,:).*vec2(1,:)-vec1(1,:).*vec2(3,:);
vec1(1,:).*vec2(2,:)-vec1(2,:).*vec2(1,:)];
end
end
nurbs-1.3.13/inst/PaxHeaders.26136/nrbcylind.m 0000644 0000000 0000000 00000000132 13070134113 015576 x ustar 00 30 mtime=1491122251.484615243
30 atime=1491122251.484615243
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbcylind.m 0000644 0001750 0001750 00000003523 13070134113 015757 0 ustar 00bect bect 0000000 0000000 function surf = nrbcylind(height,radius,center,sang,eang)
%
% NRBCYLIND: Construct a cylinder or cylindrical patch.
%
% Calling Sequence:
%
% srf = nrbcylind()
% srf = nrbcylind(height)
% srf = nrbcylind(height,radius)
% srf = nrbcylind(height,radius,center)
% srf = nrbcylind(height,radius,center,sang,eang)
%
% INPUT:
%
% height : Height of the cylinder along the axis, default 1.0
%
% radius : Radius of the cylinder, default 1.0
%
% center : Center of the cylinder, default (0,0,0)
%
% sang : Start angle relative to the origin, default 0.
%
% eang : End angle relative to the origin, default 2*pi.
%
% OUTPUT:
%
% srf : cylindrical surface patch
%
% Description:
%
% Construct a cylinder or cylindrical patch by extruding a circular arc.
%
% Copyright (C) 2000 Mark Spink
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
if nargin < 1
height = 1;
end
if nargin < 2
radius = 1;
end
if nargin < 3
center = [];
end
if nargin < 5
sang = 0;
eang = 2*pi;
end
surf = nrbextrude(nrbcirc(radius,center,sang,eang),[0.0 0.0 height]);
end
%!demo
%! srf = nrbcylind(3,1,[],3*pi/2,pi);
%! nrbplot(srf,[20,20]);
%! axis equal;
%! title('Cylinderical section by extrusion of a circular arc.');
%! hold off
nurbs-1.3.13/inst/PaxHeaders.26136/private 0000644 0000000 0000000 00000000132 13070134113 015031 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.516614779
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/ 0000755 0001750 0001750 00000000000 13070134113 015264 5 ustar 00bect bect 0000000 0000000 nurbs-1.3.13/inst/private/PaxHeaders.26136/onebasisfunder__.m 0000644 0000000 0000000 00000000132 13070134113 020571 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/onebasisfunder__.m 0000644 0001750 0001750 00000001764 13070134113 020757 0 ustar 00bect bect 0000000 0000000 function [N, Nder] = onebasisfunder__ (u, p, U)
% __ONEBASISFUNDER__: Undocumented internal function
%
% Copyright (C) 2012 Rafael Vazquez
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
N = zeros (size (u));
Nder = zeros (size (u));
for ii = 1:numel (u)
if (~ any (U <= u(ii))) || (~ any (U > u(ii)))
continue;
elseif (p == 0)
N(ii) = 1;
Nder(ii) = 0;
continue;
else
ln = u(ii) - U(1);
ld = U(end-1) - U(1);
if (ld ~= 0)
aux = onebasisfun__ (u(ii), p-1, U(1:end-1))/ ld;
N(ii) = N(ii) + ln * aux;
Nder(ii) = Nder(ii) + p * aux;
end
dn = U(end) - u(ii);
dd = U(end) - U(2);
if (dd ~= 0)
aux = onebasisfun__ (u(ii), p-1, U(2:end))/ dd;
N(ii) = N(ii) + dn * aux;
Nder(ii) = Nder(ii) - p * aux;
end
end
end
end
nurbs-1.3.13/inst/private/PaxHeaders.26136/nrb_crv_basisfun_der__.m 0000644 0000000 0000000 00000000132 13070134113 021741 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/nrb_crv_basisfun_der__.m 0000644 0001750 0001750 00000002143 13070134113 022117 0 ustar 00bect bect 0000000 0000000 function [Bu, nbfu] = nrb_crv_basisfun_der__ (points, nrb)
% __NRB_CRV_BASISFUN_DER__: Undocumented internal function
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2013 Rafael Vazquez
%
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
warning ('nrb_crv_basisfunder__ is deprecated. Use nrbbasisfunder, instead')
n = size (nrb.coefs, 2) -1;
p = nrb.order -1;
u = points;
U = nrb.knots;
w = nrb.coefs(4,:);
spu = findspan (n, p, u, U);
nbfu = numbasisfun (spu, u, p, U);
Nprime = basisfunder (spu, p, u, U, 1);
N = reshape (Nprime(:,1,:), numel(u), p+1);
Nprime = reshape (Nprime(:,2,:), numel(u), p+1);
[Dpc, Dpk] = bspderiv (p, w, U);
D = bspeval (p, w, U, u);
Dprime = bspeval (p-1, Dpc, Dpk, u);
Bu1 = bsxfun (@(np, d) np/d , Nprime.', D);
Bu2 = bsxfun (@(n, dp) n*dp, N.', Dprime./D.^2);
Bu = w(nbfu+1) .* (Bu1 - Bu2).';
end
nurbs-1.3.13/inst/private/PaxHeaders.26136/nrb_crv_basisfun__.m 0000644 0000000 0000000 00000000132 13070134113 021107 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/nrb_crv_basisfun__.m 0000644 0001750 0001750 00000001353 13070134113 021267 0 ustar 00bect bect 0000000 0000000 function [B, nbfu] = nrb_crv_basisfun__ (points, nrb);
% __NRB_CRV_BASISFUN__: Undocumented internal function
%
% Copyright (C) 2009 Carlo de Falco
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
warning ('nrb_crv_basisfun__ is deprecated. Use nrbbasisfun, instead')
n = size (nrb.coefs, 2) -1;
p = nrb.order -1;
u = points;
U = nrb.knots;
w = nrb.coefs(4,:);
spu = findspan (n, p, u, U);
nbfu = numbasisfun (spu, u, p, U);
N = w(nbfu+1) .* basisfun (spu, u, p, U);
B = bsxfun (@(x,y) x./y, N, sum (N,2));
end
nurbs-1.3.13/inst/private/PaxHeaders.26136/nrb_srf_basisfun_der__.m 0000644 0000000 0000000 00000000132 13070134113 021741 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/nrb_srf_basisfun_der__.m 0000644 0001750 0001750 00000003122 13070134113 022115 0 ustar 00bect bect 0000000 0000000 function [Bu, Bv, N] = nrb_srf_basisfun_der__ (points, nrb);
% __NRB_SRF_BASISFUN_DER__: Undocumented internal function
%
% Copyright (C) 2009 Carlo de Falco
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
warning ('nrb_srf_basisfunder__ is deprecated. Use nrbbasisfunder, instead')
m = size (nrb.coefs, 2) -1;
n = size (nrb.coefs, 3) -1;
p = nrb.order(1) -1;
q = nrb.order(2) -1;
u = points(1,:);
v = points(2,:);
npt = length(u);
U = nrb.knots{1};
V = nrb.knots{2};
w = squeeze(nrb.coefs(4,:,:));
spu = findspan (m, p, u, U);
spv = findspan (n, q, v, V);
N = nrbnumbasisfun (points, nrb);
NuIkuk = basisfun (spu, u, p, U);
NvJkvk = basisfun (spv, v, q, V);
NuIkukprime = basisfunder (spu, p, u, U, 1);
NuIkukprime = reshape (NuIkukprime(:,2,:), npt, []);
NvJkvkprime = basisfunder (spv, q, v, V, 1);
NvJkvkprime = reshape (NvJkvkprime(:,2,:), npt, []);
for k=1:npt
wIkaJkb(1:p+1, 1:q+1) = reshape (w(N(k, :)), p+1, q+1);
Num = (NuIkuk(k, :).' * NvJkvk(k, :)) .* wIkaJkb;
Num_du = (NuIkukprime(k, :).' * NvJkvk(k, :)) .* wIkaJkb;
Num_dv = (NuIkuk(k, :).' * NvJkvkprime(k, :)) .* wIkaJkb;
Denom = sum(sum(Num));
Denom_du = sum(sum(Num_du));
Denom_dv = sum(sum(Num_dv));
Bu(k, :) = reshape((Num_du/Denom - Denom_du.*Num/Denom.^2),1,[]);
Bv(k, :) = reshape((Num_dv/Denom - Denom_dv.*Num/Denom.^2),1,[]);
end
end nurbs-1.3.13/inst/private/PaxHeaders.26136/onebasisfun__.m 0000644 0000000 0000000 00000000132 13070134113 020076 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/onebasisfun__.m 0000644 0001750 0001750 00000002533 13070134113 020257 0 ustar 00bect bect 0000000 0000000 function Nip = onebasisfun__ (u, p, U)
% __ONEBASISFUN__: Undocumented internal function
%
% Adapted from Algorithm A2.4 from 'The NURBS BOOK' pg74.
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2012 Rafael Vazquez
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
Nip = zeros (size (u));
N = zeros (p+1, 1);
for ii = 1:numel(u)
if ((u(ii) == U(1)) && (U(1) == U(end-1)) || ...
(u(ii) == U(end)) && (U(end) == U(2)))
Nip(ii) = 1;
continue
end
if (~ any (U <= u(ii))) || (~ any (U > u(ii)))
continue;
end
for jj = 1:p+1 % Initialize zero-th degree functions
if (u(ii) >= U(jj) && u(ii) < U(jj+1))
N(jj) = 1;
else
N(jj) = 0;
end
end
for k = 1:p
if (N(1) == 0)
saved = 0;
else
saved = (u(ii) - U(1))*N(1) / (U(k+1)-U(1));
end
for jj = 1:p-k+1
Uleft = U(1+jj);
Uright = U(1+jj+k);
if (N(jj+1) == 0)
N(jj) = saved;
saved = 0;
else
temp = N(jj+1)/(Uright-Uleft);
N(jj) = saved + (Uright - u(ii))*temp;
saved = (u(ii) - Uleft)*temp;
end
end
end
Nip(ii) = N(1);
end
end
nurbs-1.3.13/inst/private/PaxHeaders.26136/nrb_srf_numbasisfun__.m 0000644 0000000 0000000 00000000132 13070134113 021627 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/nrb_srf_numbasisfun__.m 0000644 0001750 0001750 00000001624 13070134113 022010 0 ustar 00bect bect 0000000 0000000 function idx = nrb_srf_numbasisfun__ (points, nrb)
% __NRB_SRF_NUMBASISFUN__: Undocumented internal function
%
% Copyright (C) 2009 Carlo de Falco
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
warning ('nrb_srf_numbasisfun__ is deprecated. Use nrbnumbasisfun, instead')
m = nrb.number(1)-1;
n = nrb.number(2)-1;
npt = size(points,2);
u = points(1,:);
v = points(2,:);
U = nrb.knots{1};
V = nrb.knots{2};
p = nrb.order(1)-1;
q = nrb.order(2)-1;
spu = findspan (m, p, u, U);
Ik = numbasisfun (spu, u, p, U);
spv = findspan (n, q, v, V);
Jk = numbasisfun (spv, v, q, V);
for k=1:npt
[Jkb, Ika] = meshgrid(Jk(k, :), Ik(k, :));
idx(k, :) = sub2ind([m+1, n+1], Ika(:)+1, Jkb(:)+1);
end
end
nurbs-1.3.13/inst/private/PaxHeaders.26136/nrb_srf_basisfun__.m 0000644 0000000 0000000 00000000132 13070134113 021107 x ustar 00 30 mtime=1491122251.496615069
30 atime=1491122251.496615069
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/private/nrb_srf_basisfun__.m 0000644 0001750 0001750 00000002303 13070134113 021263 0 ustar 00bect bect 0000000 0000000 function [B, N] = nrb_srf_basisfun__ (points, nrb);
% __NRB_SRF_BASISFUN__: Undocumented internal function
%
% Copyright (C) 2009 Carlo de Falco
% This software comes with ABSOLUTELY NO WARRANTY; see the file
% COPYING for details. This is free software, and you are welcome
% to distribute it under the conditions laid out in COPYING.
warning ('nrb_srf_basisfun__ is deprecated. Use nrbbasisfun, instead')
m = size (nrb.coefs, 2) -1;
n = size (nrb.coefs, 3) -1;
p = nrb.order(1) -1;
q = nrb.order(2) -1;
u = points(1,:);
v = points(2,:);
npt = length(u);
U = nrb.knots{1};
V = nrb.knots{2};
w = squeeze(nrb.coefs(4,:,:));
spu = findspan (m, p, u, U);
spv = findspan (n, q, v, V);
NuIkuk = basisfun (spu, u, p, U);
NvJkvk = basisfun (spv, v, q, V);
indIkJk = nrbnumbasisfun (points, nrb);
for k=1:npt
wIkaJkb(1:p+1, 1:q+1) = reshape (w(indIkJk(k, :)), p+1, q+1);
NuIkukaNvJkvk(1:p+1, 1:q+1) = (NuIkuk(k, :).' * NvJkvk(k, :));
RIkJk(k, :) = reshape((NuIkukaNvJkvk .* wIkaJkb ./ sum(sum(NuIkukaNvJkvk .* wIkaJkb))),1,[]);
end
B = RIkJk;
N = indIkJk;
end
nurbs-1.3.13/inst/PaxHeaders.26136/basisfun.m 0000644 0000000 0000000 00000000132 13070134113 015424 x ustar 00 30 mtime=1491122251.476615358
30 atime=1491122251.476615358
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/basisfun.m 0000644 0001750 0001750 00000004455 13070134113 015612 0 ustar 00bect bect 0000000 0000000 function B = basisfun (iv, uv, p, U)
% BASISFUN: Basis function for B-Spline
%
% Calling Sequence:
%
% N = basisfun(iv,uv,p,U)
%
% INPUT:
%
% iv - knot span ( from FindSpan() )
% uv - parametric points
% p - spline degree
% U - knot sequence
%
% OUTPUT:
%
% N - Basis functions vector(numel(uv)*(p+1))
%
% Adapted from Algorithm A2.2 from 'The NURBS BOOK' pg70.
%
% See also:
%
% numbasisfun, basisfunder, findspan
%
% Copyright (C) 2000 Mark Spink
% Copyright (C) 2007 Daniel Claxton
% Copyright (C) 2009 Carlo de Falco
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
B = zeros(numel(uv), p+1);
for jj = 1:numel(uv)
i = iv(jj) + 1; %% findspan uses 0-based numbering
u = uv(jj);
left = zeros(p+1,1);
right = zeros(p+1,1);
N(1) = 1;
for j=1:p
left(j+1) = u - U(i+1-j);
right(j+1) = U(i+j) - u;
saved = 0;
for r=0:j-1
temp = N(r+1)/(right(r+2) + left(j-r+1));
N(r+1) = saved + right(r+2)*temp;
saved = left(j-r+1)*temp;
end
N(j+1) = saved;
end
B (jj, :) = N;
end
end
%!test
%! n = 3;
%! U = [0 0 0 1/2 1 1 1];
%! p = 2;
%! u = linspace (0, 1, 10);
%! s = findspan (n, p, u, U);
%! Bref = [1.00000 0.00000 0.00000
%! 0.60494 0.37037 0.02469
%! 0.30864 0.59259 0.09877
%! 0.11111 0.66667 0.22222
%! 0.01235 0.59259 0.39506
%! 0.39506 0.59259 0.01235
%! 0.22222 0.66667 0.11111
%! 0.09877 0.59259 0.30864
%! 0.02469 0.37037 0.60494
%! 0.00000 0.00000 1.00000];
%! B = basisfun (s, u, p, U);
%! assert (B, Bref, 1e-5);
nurbs-1.3.13/inst/PaxHeaders.26136/curvederiveval.m 0000644 0000000 0000000 00000000126 13070134113 016643 x ustar 00 28 mtime=1491122251.4806153
28 atime=1491122251.4806153
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/curvederiveval.m 0000644 0001750 0001750 00000004061 13070134113 017017 0 ustar 00bect bect 0000000 0000000 function ck = curvederiveval (n, p, U, P, u, d)
%
% CURVEDERIVEVAL: Compute the derivatives of a B-spline curve.
%
% usage: ck = curvederiveval (n, p, U, P, u, d)
%
% INPUT:
%
% n+1 = number of control points
% p = spline order
% U = knots
% P = control points
% u = evaluation point
% d = derivative order
%
% OUTPUT:
%
% ck (k+1) = curve differentiated k times
%
% Adaptation of algorithm A3.4 from the NURBS book, pg99
%
% Copyright (C) 2009 Carlo de Falco
% Copyright (C) 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
ck = zeros (d+1, 1);
du = min (d, p);
span = findspan (n, p, u, U);
N = zeros (p+1, p+1);
for ip=0:p
N(1:ip+1,ip+1) = basisfun (span, u, ip, U)';
end
pk = curvederivcpts (n, p, U, P, du, span-p, span);
for k = 0:du
for j = 0:p-k
ck(k+1) = ck(k+1) + N(j+1,p-k+1)*pk(k+1,j+1);
end
end
end
%!test
%! k = [0 0 0 1 1 1];
%! coefs(:,1) = [0;0;0;1];
%! coefs(:,2) = [1;0;1;1];
%! coefs(:,3) = [1;1;1;1];
%! crv = nrbmak (coefs, k);
%! ck = curvederiveval (crv.number-1, crv.order-1, crv.knots, squeeze (crv.coefs(1,:,:)), 0.5, 2);
%! assert(ck, [0.75; 1; -2]);
%! ck = curvederiveval (crv.number-1, crv.order-1, crv.knots, squeeze (crv.coefs(2,:,:)), 0.5, 2);
%! assert(ck, [0.25; 1; 2]);
%! ck = curvederiveval (crv.number-1, crv.order-1, crv.knots, squeeze (crv.coefs(3,:,:)), 0.5, 2);
%! assert(ck, [0.75; 1; -2]);
nurbs-1.3.13/inst/PaxHeaders.26136/nrbmak.m 0000644 0000000 0000000 00000000132 13070134113 015064 x ustar 00 30 mtime=1491122251.488615185
30 atime=1491122251.488615185
30 ctime=1491122251.516614779
nurbs-1.3.13/inst/nrbmak.m 0000644 0001750 0001750 00000020736 13070134113 015252 0 ustar 00bect bect 0000000 0000000 function nurbs = nrbmak(coefs,knots)
%
% NRBMAK: Construct the NURBS structure given the control points
% and the knots.
%
% Calling Sequence:
%
% nurbs = nrbmak(cntrl,knots);
%
% INPUT:
%
% cntrl : Control points, these can be either Cartesian or
% homogeneous coordinates.
%
% For a curve the control points are represented by a
% matrix of size (dim,nu), for a surface a multidimensional
% array of size (dim,nu,nv), for a volume a multidimensional array
% of size (dim,nu,nv,nw). Where nu is number of points along
% the parametric U direction, nv the number of points along
% the V direction and nw the number of points along the W direction.
% dim is the dimension. Valid options
% are
% 2 .... (x,y) 2D Cartesian coordinates
% 3 .... (x,y,z) 3D Cartesian coordinates
% 4 .... (wx,wy,wz,w) 4D homogeneous coordinates
%
% knots : Non-decreasing knot sequence spanning the interval
% [0.0,1.0]. It's assumed that the geometric entities
% are clamped to the start and end control points by knot
% multiplicities equal to the spline order (open knot vector).
% For curve knots form a vector and for surfaces (volumes)
% the knots are stored by two (three) vectors for U and V (and W)
% in a cell structure {uknots vknots} ({uknots vknots wknots}).
%
% OUTPUT:
%
% nurbs : Data structure for representing a NURBS entity
%
% NURBS Structure:
%
% Both curves and surfaces are represented by a structure that is
% compatible with the Spline Toolbox from Mathworks
%
% nurbs.form .... Type name 'B-NURBS'
% nurbs.dim .... Dimension of the control points
% nurbs.number .... Number of Control points
% nurbs.coefs .... Control Points
% nurbs.order .... Order of the spline
% nurbs.knots .... Knot sequence
%
% Note: the control points are always converted and stored within the
% NURBS structure as 4D homogeneous coordinates. A curve is always stored
% along the U direction, and the vknots element is an empty matrix. For
% a surface the spline order is a vector [du,dv] containing the order
% along the U and V directions respectively. For a volume the order is
% a vector [du dv dw]. Recall that order = degree + 1.
%
% Description:
%
% This function is used as a convenient means of constructing the NURBS
% data structure. Many of the other functions in the toolbox rely on the
% NURBS structure been correctly defined as shown above. The nrbmak not
% only constructs the proper structure, but also checks for consistency.
% The user is still free to build his own structure, in fact a few
% functions in the toolbox do this for convenience.
%
% Examples:
%
% Construct a 2D line from (0.0,0.0) to (1.5,3.0).
% For a straight line a spline of order 2 is required.
% Note that the knot sequence has a multiplicity of 2 at the
% start (0.0,0.0) and end (1.0 1.0) in order to clamp the ends.
%
% line = nrbmak([0.0 1.5; 0.0 3.0],[0.0 0.0 1.0 1.0]);
% nrbplot(line, 2);
%
% Construct a surface in the x-y plane i.e
%
% ^ (0.0,1.0) ------------ (1.0,1.0)
% | | |
% | V | |
% | | Surface |
% | | |
% | | |
% | (0.0,0.0) ------------ (1.0,0.0)
% |
% |------------------------------------>
% U
%
% coefs = cat(3,[0 0; 0 1],[1 1; 0 1]);
% knots = {[0 0 1 1] [0 0 1 1]}
% plane = nrbmak(coefs,knots);
% nrbplot(plane, [2 2]);
%
% Copyright (C) 2000 Mark Spink, 2010 Rafael Vazquez
%
% This program is free software: you can redistribute it and/or modify
% it under the terms of the GNU General Public License as published by
% the Free Software Foundation, either version 3 of the License, or
% (at your option) any later version.
% This program is distributed in the hope that it will be useful,
% but WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
% GNU General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with this program. If not, see .
nurbs = struct ('form', 'B-NURBS', 'dim', 4, 'number', [], 'coefs', [], ...
'knots', [], 'order', []);
nurbs.form = 'B-NURBS';
nurbs.dim = 4;
np = size(coefs);
dim = np(1);
if iscell(knots)
if size(knots,2) == 3
if (numel(np) == 3)
np(4) = 1;
elseif (numel(np)==2)
np(3:4) = 1;
end
% constructing a volume
nurbs.number = np(2:4);
if (dim < 4)
nurbs.coefs = repmat([0.0 0.0 0.0 1.0]',[1 np(2:4)]);
nurbs.coefs(1:dim,:,:,:) = coefs;
else
nurbs.coefs = coefs;
end
uorder = size(knots{1},2)-np(2);
vorder = size(knots{2},2)-np(3);
worder = size(knots{3},2)-np(4);
uknots = sort(knots{1});
vknots = sort(knots{2});
wknots = sort(knots{3});
% uknots = (uknots-uknots(uorder))/(uknots(end-uorder+1)-uknots(uorder));
% vknots = (vknots-vknots(vorder))/(vknots(end-vorder+1)-vknots(vorder));
% wknots = (wknots-wknots(worder))/(wknots(end-worder+1)-wknots(worder));
nurbs.knots = {uknots vknots wknots};
nurbs.order = [uorder vorder worder];
elseif size(knots,2) == 2
if (numel(np)==2); np(3) = 1; end
% constructing a surface
nurbs.number = np(2:3);
if (dim < 4)
nurbs.coefs = repmat([0.0 0.0 0.0 1.0]',[1 np(2:3)]);
nurbs.coefs(1:dim,:,:) = coefs;
else
nurbs.coefs = coefs;
end
uorder = size(knots{1},2)-np(2);
vorder = size(knots{2},2)-np(3);
uknots = sort(knots{1});
vknots = sort(knots{2});
% uknots = (uknots-uknots(uorder))/(uknots(end-uorder+1)-uknots(uorder));
% vknots = (vknots-vknots(vorder))/(vknots(end-vorder+1)-vknots(vorder));
nurbs.knots = {uknots vknots};
nurbs.order = [uorder vorder];
end
else
% constructing a curve
nurbs.number = np(2);
if (dim < 4)
nurbs.coefs = repmat([0.0 0.0 0.0 1.0]',[1 np(2)]);
nurbs.coefs(1:dim,:) = coefs;
else
nurbs.coefs = coefs;
end
order = size (knots,2) - np(2);
nurbs.order = order;
knots = sort(knots);
% nurbs.knots = (knots-knots(order))/(knots(end-order+1)-knots(order));
nurbs.knots = knots;
end
end
%!demo
%! pnts = [0.5 1.5 4.5 3.0 7.5 6.0 8.5;
%! 3.0 5.5 5.5 1.5 1.5 4.0 4.5;
%! 0.0 0.0 0.0 0.0 0.0 0.0 0.0];
%! crv = nrbmak(pnts,[0 0 0 1/4 1/2 3/4 3/4 1 1 1]);
%! nrbplot(crv,100)
%! title('Test curve')
%! hold off
%!demo
%! pnts = [0.5 1.5 4.5 3.0 7.5 6.0 8.5;
%! 3.0 5.5 5.5 1.5 1.5 4.0 4.5;
%! 0.0 0.0 0.0 0.0 0.0 0.0 0.0];
%! crv = nrbmak(pnts,[0 0 0 0.1 1/2 3/4 3/4 1 1 1]);
%! nrbplot(crv,100)
%! title('Test curve with a slight variation of the knot vector')
%! hold off
%!demo
%! pnts = zeros(3,5,5);
%! pnts(:,:,1) = [ 0.0 3.0 5.0 8.0 10.0;
%! 0.0 0.0 0.0 0.0 0.0;
%! 2.0 2.0 7.0 7.0 8.0];
%! pnts(:,:,2) = [ 0.0 3.0 5.0 8.0 10.0;
%! 3.0 3.0 3.0 3.0 3.0;
%! 0.0 0.0 5.0 5.0 7.0];
%! pnts(:,:,3) = [ 0.0 3.0 5.0 8.0 10.0;
%! 5.0 5.0 5.0 5.0 5.0;
%! 0.0 0.0 5.0 5.0 7.0];
%! pnts(:,:,4) = [ 0.0 3.0 5.0 8.0 10.0;
%! 8.0 8.0 8.0 8.0 8.0;
%! 5.0 5.0 8.0 8.0 10.0];
%! pnts(:,:,5) = [ 0.0 3.0 5.0 8.0 10.0;
%! 10.0 10.0 10.0 10.0 10.0;
%! 5.0 5.0 8.0 8.0 10.0];
%!
%! knots{1} = [0 0 0 1/3 2/3 1 1 1];
%! knots{2} = [0 0 0 1/3 2/3 1 1 1];
%!
%! srf = nrbmak(pnts,knots);
%! nrbplot(srf,[20 20])
%! title('Test surface')
%! hold off
%!demo
%! coefs =[ 6.0 0.0 6.0 1;
%! -5.5 0.5 5.5 1;
%! -5.0 1.0 -5.0 1;
%! 4.5 1.5 -4.5 1;
%! 4.0 2.0 4.0 1;
%! -3.5 2.5 3.5 1;
%! -3.0 3.0 -3.0 1;
%! 2.5 3.5 -2.5 1;
%! 2.0 4.0 2.0 1;
%! -1.5 4.5 1.5 1;
%! -1.0 5.0 -1.0 1;
%! 0.5 5.5 -0.5 1;
%! 0.0 6.0 0.0 1]';
%! knots = [0 0 0 0 .1 .2 .3 .4 .5 .6 .7 .8 .9 1 1 1 1];
%!
%! crv = nrbmak(coefs,knots);
%! nrbplot(crv,100);
%! grid on;
%! title('3D helical curve.');
%! hold off
nurbs-1.3.13/PaxHeaders.26136/src 0000644 0000000 0000000 00000000132 13070134113 013171 x ustar 00 30 mtime=1491122251.504614953
30 atime=1491122251.516614779
30 ctime=1491122251.516614779
nurbs-1.3.13/src/ 0000755 0001750 0001750 00000000000 13070134113 013424 5 ustar 00bect bect 0000000 0000000 nurbs-1.3.13/src/PaxHeaders.26136/basisfun.cc 0000644 0000000 0000000 00000000132 13070134113 015367 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/src/basisfun.cc 0000644 0001750 0001750 00000004414 13070134113 015550 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include "low_level_functions.h"
DEFUN_DLD(basisfun, args, nargout, "\n\
BASISFUN: Compute B-Spline Basis Functions \n\
\n\
Calling Sequence:\n\
\n\
N = basisfun(iv,uv,p,U)\n\
\n\
INPUT:\n\
\n\
iv - knot span ( from FindSpan() )\n\
uv - parametric point\n\
p - spline degree\n\
U - knot sequence\n\
\n\
OUTPUT:\n\
\n\
N - Basis functions vector(numel(uv)*(p+1))\n\
\n\
Algorithm A2.2 from 'The NURBS BOOK' pg70.\n\
\n\
")
{
octave_value_list retval;
const NDArray i = args(0).array_value();
const NDArray u = args(1).array_value();
int p = args(2).idx_type_value();
const RowVector U = args(3).row_vector_value();
RowVector N(p+1, 0.0);
Matrix B(u.numel (), p+1, 0.0);
if (!error_state)
{
for (octave_idx_type ii(0); ii < u.numel (); ii++)
{
basisfun(int(i(ii)), u(ii), p, U, N);
B.insert(N, ii, 0);
}
retval(0) = octave_value(B);
}
return retval;
}
/*
%!shared n, U, p, u, s
%!test
%! n = 3;
%! U = [0 0 0 1/2 1 1 1];
%! p = 2;
%! u = linspace(0, 1, 10);
%! s = findspan(n, p, u, U);
%! assert (s, [2*ones(1, 5) 3*ones(1, 5)]);
%!test
%! Bref = [1.00000 0.00000 0.00000
%! 0.60494 0.37037 0.02469
%! 0.30864 0.59259 0.09877
%! 0.11111 0.66667 0.22222
%! 0.01235 0.59259 0.39506
%! 0.39506 0.59259 0.01235
%! 0.22222 0.66667 0.11111
%! 0.09877 0.59259 0.30864
%! 0.02469 0.37037 0.60494
%! 0.00000 0.00000 1.00000];
%! B = basisfun(s, u, p, U);
%! assert (B, Bref, 1e-5);
*/
nurbs-1.3.13/src/PaxHeaders.26136/low_level_functions.h 0000644 0000000 0000000 00000000132 13070134113 017477 x ustar 00 30 mtime=1491122251.504614953
30 atime=1491122251.504614953
30 ctime=1491122251.516614779
nurbs-1.3.13/src/low_level_functions.h 0000644 0001750 0001750 00000003156 13070134113 017662 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
octave_idx_type findspan(int n, int p, double u, const RowVector& U);
void basisfun(int i, double u, int p, const RowVector& U, RowVector& N);
void basisfunder (int i, int pl, double uu, const RowVector& u_knotl,
int nders, NDArray& dersv);
int curvederivcpts (octave_idx_type n, octave_idx_type p,
const RowVector &U, const NDArray &P,
octave_idx_type d, octave_idx_type r1,
octave_idx_type r2,
Matrix &pk);
int surfderivcpts (octave_idx_type n, octave_idx_type p, const RowVector& U,
octave_idx_type m, octave_idx_type q, const RowVector& V,
const Matrix& P, octave_idx_type d, octave_idx_type r1,
octave_idx_type r2, octave_idx_type s1,
octave_idx_type s2, NDArray &pkl);
int surfderiveval (octave_idx_type n, octave_idx_type p, const RowVector &U,
octave_idx_type m, octave_idx_type q, const RowVector &V,
const Matrix &P, double u, double v, octave_idx_type d,
Matrix &skl);
nurbs-1.3.13/src/PaxHeaders.26136/Makefile 0000644 0000000 0000000 00000000132 13070134113 014706 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/src/Makefile 0000644 0001750 0001750 00000000707 13070134113 015070 0 ustar 00bect bect 0000000 0000000 OCTFILES=basisfun.oct \
basisfunder.oct \
bspderiv.oct \
bspeval.oct \
curvederivcpts.oct \
nrb_srf_basisfun__.oct \
nrb_srf_basisfun_der__.oct \
nrbsurfderiveval.oct \
surfderivcpts.oct \
surfderiveval.oct \
tbasisfun.oct
MKOCTFILE ?= mkoctfile
all: $(OCTFILES)
low_level_functions.o: low_level_functions.cc
$(MKOCTFILE) -c $<
%.oct: %.cc low_level_functions.o
$(MKOCTFILE) $< low_level_functions.o
clean:
-rm -f *.o core octave-core *.oct *~
nurbs-1.3.13/src/PaxHeaders.26136/basisfunder.cc 0000644 0000000 0000000 00000000132 13070134113 016062 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/src/basisfunder.cc 0000644 0001750 0001750 00000003734 13070134113 016247 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include "low_level_functions.h"
DEFUN_DLD(basisfunder, args, nargout,"\n\
BASISFUNDER: B-Spline Basis function derivatives\n\
\n\
Calling Sequence:\n\
\n\
ders = basisfunder (ii, pl, uu, k, nd)\n\
\n\
INPUT:\n\
\n\
ii - knot span\n\
pl - degree of curve\n\
uu - parametric points\n\
k - knot vector\n\
nd - number of derivatives to compute\n\
\n\
OUTPUT:\n\
\n\
ders - ders(n, i, :) (i-1)-th derivative at n-th point\n\
\n\
Adapted from Algorithm A2.3 from 'The NURBS BOOK' pg72. \n\
\n\
")
{
octave_value_list retval;
const NDArray i = args(0).array_value ();
int pl = args(1).int_value ();
const NDArray u = args(2).array_value ();
const RowVector U = args(3).row_vector_value ();
int nd = args(4).int_value ();
if (!error_state)
{
if (i.numel () != u.numel ())
print_usage ();
NDArray dersv (dim_vector (i.numel (), nd+1, pl+1), 0.0);
NDArray ders(dim_vector(nd+1, pl+1), 0.0);
for ( octave_idx_type jj(0); jj < i.numel (); jj++)
{
basisfunder (int (i(jj)), pl, u(jj), U, nd, ders);
for (octave_idx_type kk(0); kk < nd+1; kk++)
for (octave_idx_type ll(0); ll < pl+1; ll++)
{
dersv(jj, kk, ll) = ders(kk, ll);
}
}
retval(0) = dersv;
}
return retval;
}
nurbs-1.3.13/src/PaxHeaders.26136/nrb_srf_basisfun__.cc 0000644 0000000 0000000 00000000132 13070134113 017400 x ustar 00 30 mtime=1491122251.504614953
30 atime=1491122251.504614953
30 ctime=1491122251.516614779
nurbs-1.3.13/src/nrb_srf_basisfun__.cc 0000644 0001750 0001750 00000011621 13070134113 017557 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include
#include
#include "low_level_functions.h"
DEFUN_DLD(nrb_srf_basisfun__, args, nargout,"\
NRB_SRF_BASISFUN__: Undocumented private function\
")
{
octave_value_list retval, newargs;
const NDArray points = args(0).array_value();
const octave_scalar_map nrb = args(1).scalar_map_value();
if (!error_state)
{
const Cell knots = nrb.contents("knots").cell_value();
const NDArray coefs = nrb.contents("coefs").array_value();
octave_idx_type m = static_cast ((nrb.contents("number").vector_value())(0)) - 1; // m = size (nrb.coefs, 2) -1;
octave_idx_type n = static_cast ((nrb.contents("number").vector_value())(1)) - 1; // n = size (nrb.coefs, 3) -1;
octave_idx_type p = static_cast ((nrb.contents("order").vector_value())(0)) - 1; // p = nrb.order(1) -1;
octave_idx_type q = static_cast ((nrb.contents("order").vector_value())(1)) - 1; // q = nrb.order(2) -1;
Array idx(dim_vector (2, 1), idx_vector(':'));
idx(0) = 0;
const NDArray u(points.index (idx).squeeze ()); // u = points(1,:);
idx(0) = 1;
const NDArray v(points.index (idx).squeeze ()); // v = points(2,:);
octave_idx_type npt = u.numel (); // npt = length(u);
RowVector M(p+1, 0.0), N (q+1, 0.0);
Matrix RIkJk(npt, (p+1)*(q+1), 0.0);
Matrix indIkJk(npt, (p+1)*(q+1), 0.0);
RowVector denom(npt, 0.0);
const RowVector U(knots(0).row_vector_value ()); // U = nrb.knots{1};
const RowVector V(knots(1).row_vector_value ()); // V = nrb.knots{2};
Array idx2(dim_vector (3, 1), idx_vector(':')); idx2(0) = 3;
NDArray w (coefs.index (idx2).squeeze ()); // w = squeeze(nrb.coefs(4,:,:));
RowVector spu(u);
for (octave_idx_type ii(0); ii < npt; ii++)
{
spu(ii) = findspan(m, p, u(ii), U);
} // spu = findspan (m, p, u, U);
newargs(3) = U; newargs(2) = p; newargs(1) = u; newargs(0) = spu;
Matrix Ik = feval (std::string("numbasisfun"), newargs, 1)(0).matrix_value (); // Ik = numbasisfun (spu, u, p, U);
RowVector spv(v);
for (octave_idx_type ii(0); ii < v.numel (); ii++)
{
spv(ii) = findspan(n, q, v(ii), V);
} // spv = findspan (n, q, v, V);
newargs(3) = V; newargs(2) = q; newargs(1) = v; newargs(0) = spv;
Matrix Jk = feval (std::string("numbasisfun"), newargs, 1)(0).matrix_value (); // Jk = numbasisfun (spv, v, q, V);
Matrix NuIkuk(npt, p+1, 0.0);
for (octave_idx_type ii(0); ii < npt; ii++)
{
basisfun (int(spu(ii)), u(ii), p, U, M);
NuIkuk.insert (M, ii, 0);
} // NuIkuk = basisfun (spu, u, p, U);
Matrix NvJkvk(v.numel (), q+1, 0.0);
for (octave_idx_type ii(0); ii < npt; ii++)
{
basisfun(int(spv(ii)), v(ii), q, V, N);
NvJkvk.insert (N, ii, 0);
} // NvJkvk = basisfun (spv, v, q, V);
for (octave_idx_type k(0); k < npt; k++)
for (octave_idx_type ii(0); ii < p+1; ii++)
for (octave_idx_type jj(0); jj < q+1; jj++)
denom(k) += NuIkuk(k, ii) * NvJkvk(k, jj) *
w(static_cast (Ik(k, ii)),
static_cast (Jk(k, jj)));
for (octave_idx_type k(0); k < npt; k++)
for (octave_idx_type ii(0); ii < p+1; ii++)
for (octave_idx_type jj(0); jj < q+1; jj++)
{
RIkJk(k, octave_idx_type(ii+(p+1)*jj)) = NuIkuk(k, ii) * NvJkvk(k, jj) *
w(static_cast (Ik(k, ii)), static_cast (Jk(k, jj)))
/ denom(k);
indIkJk(k, octave_idx_type(ii+(p+1)*jj))= Ik(k, ii) + (m+1) * Jk(k, jj) + 1;
}
// for k=1:npt
// [Jkb, Ika] = meshgrid(Jk(k, :), Ik(k, :));
// indIkJk(k, :) = sub2ind([m+1, n+1], Ika(:)+1, Jkb(:)+1);
// wIkaJkb(1:p+1, 1:q+1) = reshape (w(indIkJk(k, :)), p+1, q+1);
// NuIkukaNvJkvk(1:p+1, 1:q+1) = (NuIkuk(k, :).' * NvJkvk(k, :));
// RIkJk(k, :) = (NuIkukaNvJkvk .* wIkaJkb ./ sum(sum(NuIkukaNvJkvk .* wIkaJkb)))(:).';
// end
retval(0) = RIkJk; // B = RIkJk;
retval(1) = indIkJk; // N = indIkJk;
}
return retval;
}
nurbs-1.3.13/src/PaxHeaders.26136/bspderiv.cc 0000644 0000000 0000000 00000000132 13070134113 015373 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/src/bspderiv.cc 0000644 0001750 0001750 00000004052 13070134113 015552 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include "low_level_functions.h"
DEFUN_DLD(bspderiv, args, nargout,"\n\
BSPDERIV: B-Spline derivative\n\
\n\
\n\
Calling Sequence:\n\
\n\
[dc,dk] = bspderiv(d,c,k)\n\
\n\
INPUT:\n\
\n\
d - degree of the B-Spline\n\
c - control points double matrix(mc,nc)\n\
k - knot sequence double vector(nk)\n\
\n\
OUTPUT:\n\
\n\
dc - control points of the derivative double matrix(mc,nc)\n\
dk - knot sequence of the derivative double vector(nk)\n\
\n\
Modified version of Algorithm A3.3 from 'The NURBS BOOK' pg98.\n\
")
{
//if (bspderiv_bad_arguments(args, nargout))
// return octave_value_list();
int d = args(0).int_value();
const Matrix c = args(1).matrix_value();
const RowVector k = args(2).row_vector_value();
octave_value_list retval;
octave_idx_type mc = c.rows(), nc = c.cols(), nk = k.numel();
Matrix dc (mc, nc-1, 0.0);
RowVector dk(nk-2, 0.0);
if (!error_state)
{
double tmp;
for (octave_idx_type i(0); i<=nc-2; i++)
{
tmp = (double)d / (k(i+d+1) - k(i+1));
for ( octave_idx_type j(0); j<=mc-1; j++)
dc(j,i) = tmp*(c(j,i+1) - c(j,i));
}
for ( octave_idx_type i(1); i <= nk-2; i++)
dk(i-1) = k(i);
if (nargout>1)
retval(1) = octave_value(dk);
retval(0) = octave_value(dc);
}
return(retval);
}
nurbs-1.3.13/src/PaxHeaders.26136/surfderiveval.cc 0000644 0000000 0000000 00000000132 13070134113 016436 x ustar 00 30 mtime=1491122251.504614953
30 atime=1491122251.504614953
30 ctime=1491122251.516614779
nurbs-1.3.13/src/surfderiveval.cc 0000644 0001750 0001750 00000005747 13070134113 016631 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include "low_level_functions.h"
#include
DEFUN_DLD(surfderiveval, args, nargout,"\
\nSURFDERIVEVAL: Compute the derivatives of a B-spline surface\
\n\
\n usage: skl = surfderiveval (n, p, U, m, q, V, P, u, v, d) \
\n\
\n INPUT: \
\n\
\n n+1, m+1 = number of control points\
\n p, q = spline order\
\n U, V = knots\
\n P = control points\
\n u,v = evaluation points\
\n d = derivative order\
\n\
\n OUTPUT:\
\n\
\n skl (k+1, l+1) = surface differentiated k\
\n times in the u direction and l\
\n times in the v direction\
\n\
\n Adaptation of algorithm A3.8 from the NURBS book\n")
{
//function skl = surfderiveval (n, p, U, m, q, V, P, u, v, d)
octave_value_list retval;
octave_idx_type n = args(0).idx_type_value ();
octave_idx_type p = args(1).idx_type_value ();
RowVector U = args(2).row_vector_value (false, true);
octave_idx_type m = args(3).idx_type_value ();
octave_idx_type q = args(4).idx_type_value ();
RowVector V = args(5).row_vector_value (false, true);
Matrix P = args(6).matrix_value ();
double u = args(7).double_value ();
double v = args(8).double_value ();
octave_idx_type d = args(9).idx_type_value ();
if (! error_state)
{
Matrix skl;
surfderiveval (n, p, U, m, q, V, P, u, v, d, skl);
retval(0) = octave_value (skl);
}
return retval;
}
/*
%!shared srf
%!test
%! k = [0 0 0 1 1 1];
%! c = [0 1/2 1];
%! [coef(2,:,:), coef(1,:,:)] = meshgrid (c, c);
%! srf = nrbmak (coef, {k, k});
%! skl = surfderiveval (srf.number(1)-1,
%! srf.order(1)-1,
%! srf.knots{1},
%! srf.number(2)-1,
%! srf.order(2)-1,
%! srf.knots{2},
%! squeeze(srf.coefs(1,:,:)), .5, .5, 1) ;
%! assert (skl, [.5 0; 1 0])
%!test
%! srf = nrbkntins (srf, {[], rand(1,2)});
%! skl = surfderiveval (srf.number(1)-1,
%! srf.order(1)-1,
%! srf.knots{1},
%! srf.number(2)-1,
%! srf.order(2)-1,
%! srf.knots{2},
%! squeeze(srf.coefs(1,:,:)), .5, .5, 1) ;
%! assert (skl, [.5 0; 1 0], 100*eps)
*/
nurbs-1.3.13/src/PaxHeaders.26136/curvederivcpts.cc 0000644 0000000 0000000 00000000132 13070134113 016625 x ustar 00 30 mtime=1491122251.500615011
30 atime=1491122251.500615011
30 ctime=1491122251.516614779
nurbs-1.3.13/src/curvederivcpts.cc 0000644 0001750 0001750 00000004657 13070134113 017017 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include "low_level_functions.h"
DEFUN_DLD(curvederivcpts, args, nargout,"\
\nCURVEDERIVCPTS: Compute control points of n-th derivatives of a B-spline curve.\n \
\n \
\n usage: pk = curvederivcpts (n, p, U, P, d) \
\n pk = curvederivcpts (n, p, U, P, d, r1 r2) \
\n \
\n If r1, r2 are not given, all the control points are computed. \
\n \
\n INPUT: \
\n n+1 = number of control points \
\n p = degree of the spline \
\n d = maximum derivative order (d<=p) \
\n U = knots \
\n P = control points \
\n r1 = first control point to compute \
\n r2 = auxiliary index for the last control point to compute \
\n\
\n OUTPUT: \
\n pk(k,i) = i-th control point (k-1)-th derivative, r1 <= i <= r2-k \
\n \
\n Adaptation of algorithm A3.3 from the NURBS book\n")
{
octave_value_list retval;
octave_idx_type n = args(0).idx_type_value ();
octave_idx_type p = args(1).idx_type_value ();
RowVector U = args(2).row_vector_value (false, true);
NDArray P = args(3).array_value ();
octave_idx_type d = args(4).idx_type_value ();
octave_idx_type r1(0), r2(n);
if (args.length () == 7)
{
r1 = args (5).idx_type_value ();
r2 = args (6).idx_type_value ();
}
else if (args.length () > 5)
print_usage ();
if (! error_state)
{
octave_idx_type r = r2 - r1;
Matrix pk (d+1 <= r+1 ? d+1 : r+1, r+1, 0.0);
curvederivcpts (n, p, U, P, d, r1, r2, pk);
retval(0) = octave_value (pk);
}
return retval;
}
/*
%!test
%! line = nrbmak([0.0 1.5; 0.0 3.0],[0.0 0.0 1.0 1.0]);
%! pk = curvederivcpts (line.number-1, line.order-1, line.knots,
%! line.coefs(1,:), 2);
%! assert (pk, [0 3/2; 3/2 0], 100*eps);
*/
nurbs-1.3.13/src/PaxHeaders.26136/nrbsurfderiveval.cc 0000644 0000000 0000000 00000000132 13070134113 017140 x ustar 00 30 mtime=1491122251.504614953
30 atime=1491122251.504614953
30 ctime=1491122251.516614779
nurbs-1.3.13/src/nrbsurfderiveval.cc 0000644 0001750 0001750 00000040644 13070134113 017326 0 ustar 00bect bect 0000000 0000000 /* Copyright (C) 2009 Carlo de Falco
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see .
*/
#include
#include
#include
#include "low_level_functions.h"
static double gammaln(double xx)
// Compute logarithm of the gamma function
// Algorithm from 'Numerical Recipes in C, 2nd Edition' pg214.
{
double x,y,tmp,ser;
static double cof[6] = {76.18009172947146,-86.50532032291677,
24.01409824083091,-1.231739572450155,
0.12086650973866179e-2, -0.5395239384953e-5};
int j;
y = x = xx;
tmp = x + 5.5;
tmp -= (x+0.5) * log(tmp);
ser = 1.000000000190015;
for (j=0; j<=5; j++) ser += cof[j]/++y;
return -tmp+log(2.5066282746310005*ser/x);
}
static double factln(int n)
// computes ln(n!)
// Numerical Recipes in C
// Algorithm from 'Numerical Recipes in C, 2nd Edition' pg215.
{
static int ntop = 0;
static double a[101];
if (n <= 1) return 0.0;
while (n > ntop)
{
++ntop;
a[ntop] = gammaln(ntop+1.0);
}
return a[n];
}
static double bincoeff(int n, int k)
// Computes the binomial coefficient.
//
// ( n ) n!
// ( ) = --------
// ( k ) k!(n-k)!
//
// Algorithm from 'Numerical Recipes in C, 2nd Edition' pg215.
{
return floor(0.5+exp(factln(n)-factln(k)-factln(n-k)));
}
DEFUN_DLD(nrbsurfderiveval, args, nargout,"\
\nNRBSURFDERIVEVAL: Evaluate n-th order derivatives of a NURBS surface.\n\
\n\
\n usage: skl = nrbsurfderiveval (srf, [u; v], d) \
\n\
\n INPUT :\
\n\
\n srf : NURBS surface structure, see nrbmak\
\n\
\n u, v : parametric coordinates of the point where we compute the\
\n derivatives\
\n\
\n d : number of partial derivatives to compute\
\n\
\n OUTPUT :\
\n\
\n skl (i, j, k, l) = i-th component derived j-1,k-1 times at the\
\n l-th point.\
\n\
\n Adaptation of algorithm A4.4 from the NURBS book\n")
{
//function skl = nrbsurfderiveval (srf, uv, d)
octave_value_list retval;
octave_scalar_map srf = args(0).scalar_map_value();
Matrix uv = args(1).matrix_value ();
octave_idx_type d = args(2).idx_type_value ();
if (! error_state)
{
Array idxta (dim_vector (4, 1), 0);
dim_vector idxa; idxa.resize (4);
idxa(0) = 3; idxa(1) = d+1;
idxa(2) = d+1; idxa(3) = uv.columns ();
NDArray skl (idxa, 0.0);
octave_idx_type n = octave_idx_type
((srf.contents("number").row_vector_value())(0) - 1);
octave_idx_type m = octave_idx_type
((srf.contents("number").row_vector_value())(1) - 1);
octave_idx_type p = octave_idx_type
((srf.contents("order").row_vector_value())(0) - 1);
octave_idx_type q = octave_idx_type
((srf.contents("order").row_vector_value())(1) - 1);
Cell knots = srf.contents("knots").cell_value();
RowVector knotsu = knots.elem (0).row_vector_value ();
RowVector knotsv = knots.elem (1).row_vector_value ();
NDArray coefs = srf.contents("coefs").array_value();
Array idx(dim_vector (3, 1), idx_vector(':'));
idx (0) = idx_vector (3);
Matrix weights (NDArray (coefs.index (idx).squeeze ()));
for (octave_idx_type iu(0); iu