function [final_angles,final_tear] = fn_fold_relax_fmincon_springs(fold_angles,CP,thresh,springs) theta_angles = CP.theta_angles ; edges_at_vertex = CP.edges_at_vertex; % Minimize tearing for simpe quads with fixed|rho| - using % fmincon % find null spaces [C,~] = fnm_compute_CF(zeros(size(CP.alledges,1),1),CP.theta_angles,CP.edges_at_vertex,1e-12); [u,s,v]=svd(C); S = sign(fold_angles); amp = norm(fold_angles); Rho = fold_angles; % Later, might want to project to null space of C %history.x=[]; %history.fval=[]; %searchdir = []; options=optimoptions('fmincon','Display','none','Algorithm','sqp','GradObj','off','MaxIter',thresh.fmin_relax_MaxIter,'MaxFunEvals',thresh.fmin_relax_evals*length(fold_angles),'TolFun',thresh.fmin_tolfun,'TolX',thresh.fmin_tolx);%,'OutputFcn',@outfun); %,'TypicalX',rem_fold_angles); %'GradConstr','on', [final_angles,final_tear,exitflag]=fmincon(@(fa) mintear(fa),Rho,[],[],[],[],[],[],@(fa) mycon(fa),options); %[~,final_tear_vec]=fnm_compute_CF_mex(final_angles,theta_angles,edges_at_vertex,1e-8); %final_tear = norm(final_tear_vec); if exitflag == 0 disp('relax_fmincon ran out of iterations/evaluations'); else %disp(['relax_fminunc flag = ' num2str(exitflag)]); end % % % % Internal functions %function [tear,grad] = mintear(fa) function [tear] = mintear(fa) [C,Fvec]=fnm_compute_CF(fa,theta_angles,edges_at_vertex,1e-12); %tear = norm(Fvec); %tear = sqrt(norm(Fvec)^2 + 0.5 * springs' * fa.^2) ; tear0 = norm(Fvec)^2 + 0.5 * springs' * fa.^2 ; tear = log(tear0) ; %force_int = +(C'*Fvec); %force_spr = springs .* fa; %grad0 = force_int + force_spr; %grad0 = grad0 - (grad0'*fa)*fa/norm(fa)^2; %grad = (grad0) ; %disp(grad'*fa); %disp(tear) end function [p,Rho2,gp,gRho2] = mycon(fa) Rho2 = norm(fa)- amp; gRho2 = fa/norm(Rho2); p=-1; gp=0; end function stop = outfun(x,optimValues,state) stop = false; switch state case 'init' hold on case 'iter' % Concatenate current point and objective function % value with history. x must be a row vector. history.fval = [history.fval; optimValues.fval]; history.x = [history.x; x']; % Concatenate current search direction with % searchdir. searchdir = [searchdir;... optimValues.searchdirection']; case 'done' hold off otherwise end end end