function [V,F,UV,TF,N,NF] = readOBJ(filename,varargin)
% READOBJ reads an OBJ file with vertex/face information
%
% [V,F,UV,TF,N,NF] = readOBJ(filename)
% [V,F,UV,TF,N,NF] = readOBJ(filename,'ParameterName',ParameterValue,...)
%
% Input:
% filename path to .obj file
% Optional:
% 'Quads' whether to output face information in X by 4 matrices (faces
% with degree larger than 4 are still triangulated). A trailing zero
% will mean a triangle was read.
% Outputs:
% V #V by 3 list of vertices
% F #F by 3 list of triangle indices
% UV #V by 2 list of texture coordinates
% TF #F by 3 list of triangle texture coordinates
% N #V by 3 list of normals
% NF #F by 3 list of triangle corner normal indices into N
%
% Examples:
% % read a quad/triangle mesh and display it
% [V,F] = readOBJ('quads.obj','Quads',true);
% % Turn triangles into degenerate quads
% DF = (F==0).*F(:,[4 1 2 3])+(F~=0).*F;
% trisurf(DF,V(:,1),V(:,2),V(:,3));
%
%
% See also: load_mesh, readOBJfast, readOFF
% default values
quads = false;
% Map of parameter names to variable names
params_to_variables = containers.Map( ...
{'Quads'}, ...
{'quads'});
v = 1;
while v <= numel(varargin)
param_name = varargin{v};
if isKey(params_to_variables,param_name)
assert(v+1<=numel(varargin));
v = v+1;
% Trick: use feval on anonymous function to use assignin to this workspace
feval(@()assignin('caller',params_to_variables(param_name),varargin{v}));
else
error('Unsupported parameter: %s',varargin{v});
end
v=v+1;
end
numv = 0;
numf = 0;
numuv = 0;
numtf = 0;
numn = 0;
numnf = 0;
% simplex size
if quads
ss = 4;
else
ss = 3;
end
% Amortized array allocation
V = zeros(10000,3);
F = zeros(10000,ss);
UV = zeros(10000,3);
TF = zeros(10000,ss);
N = zeros(10000,3);
NF = zeros(10000,ss);
triangulated = false;
all_ss = true;
fp = fopen( filename, 'r' );
type = fscanf( fp, '%s', 1 );
count = 0;
while strcmp( type, '' ) == 0
line = fgets(fp);
if strcmp( type, 'v' ) == 1
v = sscanf( line, '%lf %lf %lf' );
numv = numv+1;
if(numv>size(V,1))
V = cat(1,V,zeros(10000,3));
end
V(numv,:) = [v(1:3)'];
elseif strcmp( type, 'vt')
v = sscanf( line, '%f %f %f' );
numuv = numuv+1;
if size(UV,2)>2 && length(v) == 2
UV = UV(:,1:2);
end
if(numuv>size(UV,1))
UV = cat(1,UV,zeros(10000,length(v)));
end
UV(numuv,:) = [v'];
elseif strcmp( type, 'vn')
n = sscanf( line, '%f %f %f' );
numn = numn+1;
if(numn>size(N,1))
N = cat(1,N,zeros(10000,3));
end
N(numn,:) = [n'];
elseif strcmp( type, 'f' ) == 1
[t, count] = sscanf(line,'%d/%d/%d %d/%d/%d %d/%d/%d %d/%d/%d %d/%d/%d');
if (count>2)
tf = t(2:3:end);
nf = t(3:3:end);
t = t(1:3:end);
else
[t, count] = sscanf(line, '%d/%d %d/%d %d/%d %d/%d %d/%d');
if (count>2)
tf = t(2:2:end);
t = t(1:2:end);
nf = -ones(numel(t),1);
else
[t, count] = sscanf(line, '%d//%d %d//%d %d//%d %d//%d %d//%d');
if (count>2)
nf = t(2:2:end);
t = t(1:2:end);
tf = -ones(numel(t),1);
else
[t, count] = sscanf( line, '%d %d %d %d %d %d %d %d %d %d %d\n' );
if (count>2)
tf = -ones(numel(t),1);
nf = -ones(numel(t),1);
else
[t, count] = sscanf( line, '%d// %d// %d// %d// %d// %d// %d// %d// %d// %d// %d//\n' );
tf = -ones(numel(t),1);
nf = -ones(numel(t),1);
end
end
end
end
t = t + (t<0).* (numv+1);
tf = tf + (tf<0).*(numuv+1);
nf = nf + (nf<0).*(numn+1);
assert(numel(t) == numel(tf));
assert(numel(t) == numel(nf));
if numel(t) > ss
if ~triangulated
warning('Trivially triangulating high degree facets');
end
triangulated = true;
end
j = 2;
i = 1;
%Vt = V(t,:);
%[~,A] = affine_fit(Vt);
%VtA = Vt*A;
%VtA0 = Vt*A;
%[~,alpha] = curvature(VtA);
%flip = -sign(sum(alpha));
%E = [1:size(VtA,1);2:size(VtA,1) 1]';
%[dV,dF] = triangle(VtA,E,[]);
%if size(dF,1)>2
% tsurf(dF,dV);
% hold on;
% plot(VtA0([1:end 1],1),VtA0([1:end 1],2),'LineWidth',3);
% hold off
% pause
%end
while true
if numel(t) > ss
corners = [1 2 3];
%plot(VtA0([1:end 1],1),VtA0([1:end 1],2));
%hold on;
%plot(VtA([1:3],1),VtA([1:3],2),'LineWidth',3);
%hold off;
%expand_axis(2);
%pause;
%[~,alpha] = curvature(VtA,[1 2;2 3]);
%alpha = flip * alpha(2);
%others = VtA(setdiff(1:end,corners),:);
%these = VtA(corners,:);
%w = inpolygon(others(:,1),others(:,2),these(:,1),these(:,2));
%alpha
%if alpha>=0 && ~any(w)
% % lazy
% t = t([2:end 1]);
% VtA = VtA([2:end 1],:);
% continue;
%end
else
if all_ss && numel(t)<ss
warning('Small degree facet found');
all_ss = false;
end
corners = 1:numel(t);
end
numf = numf+1;
if(numf>size(F,1))
F = cat(1,F,zeros(10000,ss));
end
F(numf,1:numel(corners)) = [t(corners)'];
numtf = numtf+1;
if(numtf>size(TF,1))
TF = cat(1,TF,zeros(10000,ss));
end
TF(numtf,1:numel(corners)) = [tf(corners)'];
numnf = numnf+1;
if(numnf>size(NF,1))
NF = cat(1,NF,zeros(10000,ss));
end
NF(numnf,1:numel(corners)) = [nf(corners)'];
if numel(t) <= ss
break;
end
t = t([1 3:end]);
%VtA = VtA([1 3:end],:);
if numel(t) < 3
break;
end
end
elseif strcmp( type, '#' ) == 1
%fscanf( fp, '%s\n', 1 );
% ignore line
end
type = fscanf( fp, '%s', 1 );
end
fclose( fp );
%try
% F = cell2mat(F);
%end
V = V(1:numv,:);
F = F(1:numf,:);
UV = UV(1:numuv,:);
TF = TF(1:numtf,:);
N = N(1:numn,:);
NF = NF(1:numnf,:);
%% transform into array if all faces have the same number of vertices
if (size(UV,1)>0) UV = UV; end
end
注意, maya, meshlab中索引是以0为基础的, 而matlab 里面是以1为基础的, 所以要想选择同一个点, 当maya里面索引为17的时候, matlab相应的应该为18
read obj
最新推荐文章于 2023-09-01 15:17:35 发布