ng_write_opt

PURPOSE ^

NG_WRITE_OPT Write an ng.opt file in current directory

SYNOPSIS ^

function opt = ng_write_opt(varargin)

DESCRIPTION ^

NG_WRITE_OPT Write an ng.opt file in current directory
  NG_WRITE_OPT, without inputs, creates a default ng.opt

  NG_WRITE_OPT(OPTSTRUCT) creates uses options as specified in OPTSTRUCT

  NG_WRITE_OPT('sec.option',val,...) offers an alternative interface to
  modify specific options

  NG_WRITE_OPT(OPTSTR,...) where OPTSTR is one of 'very_coarse', 'coarse',
  'moderate', 'fine', and 'very_fine', based on the corresponding defaults
  in Netgen 5.0. Any additional inputs modify selected fields of that
  default. NG_WRITE_OPT('moderate',...) is equivalent to
  NG_WRITE_OPT(...).

  OPTSTRUCT = NG_WRITE_OPT(...) returns a struct with the options.
  No file is written.

  NG_WRITE_OPT(PATH) copies the file specified in PATH as ng.opt to the
  current directory.

 
  Note: some options only take effect when meshoptions.fineness is 6
  (custom).

  BEWARE: NG_WRITE_OPT will overwrite any existing ng.opt file in the current
  directory. 
 
  Example:
  ng_write_opt('meshoptions.fineness',6,'options.minmeshsize',20);
  call_netgen(...)
  delete('ng.opt'); % clean up

 To specify a volume for refinement, specify
  ng_write_opt('MSZPOINTS', [list of x,y,z,maxh])
   or
  ng_write_opt('MSZBRICK', [xmin, xmax, ymin, ymax, zmin, zmax, maxh])
   or
  ng_write_opt('MSZSPHERE', [xctr, yctr, zctr, radius, maxh])
  ng_write_opt('MSZCYLINDER', [x1, y1, z1, x2, y2, z2, radius, maxh])
     where (x1,y1,z1) and (x2,y2,z2) are the limits on the axis

  See also CALL_NETGEN

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SUBFUNCTIONS ^

SOURCE CODE ^

0001 function opt = ng_write_opt(varargin)
0002 %NG_WRITE_OPT Write an ng.opt file in current directory
0003 %  NG_WRITE_OPT, without inputs, creates a default ng.opt
0004 %
0005 %  NG_WRITE_OPT(OPTSTRUCT) creates uses options as specified in OPTSTRUCT
0006 %
0007 %  NG_WRITE_OPT('sec.option',val,...) offers an alternative interface to
0008 %  modify specific options
0009 %
0010 %  NG_WRITE_OPT(OPTSTR,...) where OPTSTR is one of 'very_coarse', 'coarse',
0011 %  'moderate', 'fine', and 'very_fine', based on the corresponding defaults
0012 %  in Netgen 5.0. Any additional inputs modify selected fields of that
0013 %  default. NG_WRITE_OPT('moderate',...) is equivalent to
0014 %  NG_WRITE_OPT(...).
0015 %
0016 %  OPTSTRUCT = NG_WRITE_OPT(...) returns a struct with the options.
0017 %  No file is written.
0018 %
0019 %  NG_WRITE_OPT(PATH) copies the file specified in PATH as ng.opt to the
0020 %  current directory.
0021 %
0022 %
0023 %  Note: some options only take effect when meshoptions.fineness is 6
0024 %  (custom).
0025 %
0026 %  BEWARE: NG_WRITE_OPT will overwrite any existing ng.opt file in the current
0027 %  directory.
0028 %
0029 %  Example:
0030 %  ng_write_opt('meshoptions.fineness',6,'options.minmeshsize',20);
0031 %  call_netgen(...)
0032 %  delete('ng.opt'); % clean up
0033 %
0034 % To specify a volume for refinement, specify
0035 %  ng_write_opt('MSZPOINTS', [list of x,y,z,maxh])
0036 %   or
0037 %  ng_write_opt('MSZBRICK', [xmin, xmax, ymin, ymax, zmin, zmax, maxh])
0038 %   or
0039 %  ng_write_opt('MSZSPHERE', [xctr, yctr, zctr, radius, maxh])
0040 %  ng_write_opt('MSZCYLINDER', [x1, y1, z1, x2, y2, z2, radius, maxh])
0041 %     where (x1,y1,z1) and (x2,y2,z2) are the limits on the axis
0042 %
0043 %  See also CALL_NETGEN
0044 
0045 % (C) 2012 Bartlomiej Grychtol. License: GPL version 2 or version 3
0046 % $Id: ng_write_opt.m 6464 2022-12-10 15:28:57Z aadler $
0047 
0048 %TODO:
0049 % 1. Check which options require meshoptions.fineness = 6 and enforce it
0050 
0051 % if input is 'UNIT_TEST', run tests
0052 if nargin == 1 && ischar(varargin{1}) && strcmp(varargin{1},'UNIT_TEST') 
0053    do_unit_test; return; end
0054 
0055 if nargin == 1 && ischar(varargin{1}) &&  exist(varargin{1},'file') % a path
0056    copyfile(varargin{1},'ng.opt');
0057    return
0058 end
0059 
0060 nargs = nargin;
0061 
0062 str = {};
0063 % modify as per user input
0064 if nargs >= 1 && ischar(varargin{1}) && ~any(varargin{1} == '.')  ...
0065               && isempty(strfind(varargin{1},'MSZ'))
0066    str = varargin(1);
0067    varargin(1) = [];
0068    nargs = nargs - 1;
0069 end
0070 
0071 % get default options
0072 opt = default_opt(str{:});
0073 
0074 if nargs == 0
0075     usr = struct;
0076 end
0077 % modify as per user input
0078 if nargs == 1 && isstruct(varargin{1})
0079    usr = varargin{1};
0080 end
0081 if nargs > 1 % string value pairs
0082    usr = process_input(varargin{:}); 
0083 end
0084 opt = copy_field(opt,usr);
0085 
0086 if nargout == 1 % do not write a file if output was requested
0087    return
0088 end
0089 
0090 % write the file
0091 write_ng_file(opt);
0092 
0093 function opt = process_input(varargin)
0094 if mod(nargin,2)~=0
0095    error('EIDORS:WrongInput','Even number of inputs expected');
0096 end
0097 for i = 1:nargin/2
0098    idx = (i-1)*2 +1;
0099    val = varargin{idx+1};
0100    switch varargin{idx}
0101 %  ng_write_opt('MSZPOINTS', [list of x,y,z,maxh])
0102    case 'MSZPOINTS'
0103     %  ng_write_opt('MSZPOINTS', [list of x,y,z,maxh])
0104        tmpname = write_tmp_mszfile( val );
0105        opt.options.meshsizefilename = tmpname;
0106    case 'MSZBRICK'
0107        val = msz_brick(val);
0108        tmpname = write_tmp_mszfile( val );
0109        opt.options.meshsizefilename = tmpname;
0110    case 'MSZSPHERE'
0111        val = msz_sphere(val);
0112        tmpname = write_tmp_mszfile( val );
0113        opt.options.meshsizefilename = tmpname;
0114    case 'MSZCYLINDER'
0115        val = msz_cylinder(val);
0116        tmpname = write_tmp_mszfile( val );
0117        opt.options.meshsizefilename = tmpname;
0118    otherwise
0119        eval(sprintf('opt.%s = val;',varargin{idx}));
0120    end
0121 end
0122 
0123 function val = msz_brick(val)
0124 %  ng_write_opt('MSZBRICK', [xmin, xmax, ymin, ymax, zmin, zmax, maxh])
0125     maxh = val(7);
0126     xpts= floor(abs(diff(val(1:2))/maxh))+1;
0127     ypts= floor(abs(diff(val(3:4))/maxh))+1;
0128     zpts= floor(abs(diff(val(5:6))/maxh))+1;
0129     xsp= linspace(val(1),val(2), xpts);
0130     ysp= linspace(val(3),val(4), ypts);
0131     zsp= linspace(val(5),val(6), zpts);
0132     [xsp,ysp,zsp] = ndgrid(xsp,ysp,zsp);
0133     val = [xsp(:),ysp(:),zsp(:), maxh+0*xsp(:)];
0134 
0135 function val = msz_sphere(val)
0136 %  ng_write_opt('MSZSPHERE', [xctr, yctr, zctr, radius, maxh])
0137     maxh = val(5);
0138     radius = val(4);
0139     npts= floor(2*radius/maxh)+1;
0140     xsp= linspace(val(1) - radius, val(1) + radius, npts);
0141     ysp= linspace(val(2) - radius, val(2) + radius, npts);
0142     zsp= linspace(val(3) - radius, val(3) + radius, npts);
0143     [xsp,ysp,zsp] = ndgrid(xsp,ysp,zsp);
0144     s_idx = ((xsp-val(1)).^2 + ...
0145              (ysp-val(2)).^2 + ...
0146              (zsp-val(3)).^2) < radius^2;
0147     s_idx = s_idx(:);
0148     val = [xsp(s_idx),ysp(s_idx),zsp(s_idx), maxh+0*xsp(s_idx)];
0149 
0150 % space points around zero with spacing maxh
0151 function pts = space_around_zero(lim,maxh);
0152     pts = 0:maxh:lim;
0153     pts = [-fliplr(pts(2:end)),pts];
0154 
0155 function val = msz_cylinder(val)
0156     % [x1, y1, z1, x2, y2, z2, radius, maxh])
0157     len2= norm(val(1:3) - val(4:6))/2;
0158     ctr =     (val(1:3) + val(4:6))/2;
0159     maxh = val(8);
0160     radius = val(7);
0161     xsp= space_around_zero(radius, maxh);
0162     ysp= space_around_zero(radius, maxh);
0163     zsp= space_around_zero(len2, maxh);
0164     [xsp,ysp,zsp] = ndgrid(xsp,ysp,zsp);
0165     s_idx = (xsp.^2 + ysp.^2) < radius^2;
0166     xsp = xsp(s_idx(:));
0167     ysp = ysp(s_idx(:));
0168     zsp = zsp(s_idx(:));
0169 % Rotate:
0170 % https://math.stackexchange.com/questions/180418/calculate-rotation-matrix-to-align-vector-a-to-vector-b-in-3d/897677#897677
0171     ab = [0;0;2*len2] + [val(4:6)-val(1:3)]';
0172     R=2*ab*ab'/(ab'*ab) - eye(3);
0173     val = [xsp,ysp,zsp]*R + ctr;
0174     val(:,4) = maxh;
0175 
0176 function fname = write_tmp_mszfile( mszpoints )
0177    % From Documentation: Syntax is
0178    % np
0179    % x1 y1 z1 h1
0180    % x2 y2 z2 h2
0181    n_pts_elecs=  size(mszpoints,1);
0182    fname = [tempname,'.msz'];
0183    fname = strrep(fname,'\','/'); % needs unix-style path on windows
0184    fid=fopen(fname,'w');
0185    fprintf(fid,'%d\n',n_pts_elecs);
0186 %  for i = 1:size(mszpoints,1)
0187 %     fprintf(fid,'%10f %10f %10f %10f\n', mszpoints(i,:));
0188 %  end
0189 %  vectorize to speed up
0190    fprintf(fid,'%10f %10f %10f %10f\n', mszpoints');
0191    fprintf(fid,'0\n'); % lines
0192    fclose(fid); % ptsfn
0193 
0194 % copy all fields from usr to opt
0195 % check that the fields exist in opt
0196 function opt = copy_field(opt,usr)
0197 optnms = fieldnames(opt);
0198 usrnms = fieldnames(usr);
0199 for i = 1:length(usrnms)
0200    % check if field exist
0201    if ~ismember(usrnms{i},optnms)
0202      error('Unsupported option %s',usrnms{i});
0203    end
0204    if isstruct(usr.(usrnms{i})) % recurse
0205       opt.(usrnms{i}) = copy_field(opt.(usrnms{i}), usr.(usrnms{i}) );
0206    else
0207       opt.(usrnms{i}) = usr.(usrnms{i});
0208    end
0209 end
0210 
0211 
0212 % write the ng.opt file
0213 function write_ng_file(opt)
0214 fid = fopen('ng.opt','w');
0215 flds = fieldnames(opt);
0216 write_field(fid,opt,[]);
0217 fclose(fid);
0218 
0219 
0220 % recurses over fields and prints to file
0221 function write_field(fid,s,str)
0222 if isstruct(s)
0223    if isempty(str)
0224       str = '';
0225    else
0226       str = [str '.'];
0227    end
0228    flds = fieldnames(s);
0229    for i = 1:length(flds)
0230       write_field(fid,s.(flds{i}),[str flds{i}]);
0231    end
0232 elseif ischar(s)
0233    fprintf(fid,'%s  %s\n', str, s);
0234 elseif round(s) == s
0235    fprintf(fid,'%s  %d\n', str, s);
0236 else
0237    fprintf(fid,'%s  %f\n', str, s);
0238 end
0239 
0240 
0241 function opt = default_opt(varargin)
0242 if nargin == 0
0243     str = 'moderate';
0244 else
0245     str = varargin{1};
0246 end
0247 switch str
0248     case 'very_coarse'
0249         % fineness 1
0250         v = [6, 1.0, 0.3, 0.7, 0.25, 0.8, 0.20, 0.5, 0.25, 1.0];
0251     case 'coarse'
0252         % fineness 2
0253         v = [6, 1.5, 0.5, 0.5, 0.50, 1.0, 0.35, 1.0, 0.50, 1.5];
0254     case 'moderate'
0255         % fineness 3
0256         v = [6, 2.0, 1.0, 0.3, 1.00, 1.5, 0.50, 2.0, 1.00, 2.0];
0257     case 'fine'
0258         % fineness 4
0259         v = [6, 3.0, 2.0, 0.2, 1.50, 2.0, 1.50, 3.5, 1.50, 3.0];
0260     case 'very_fine'
0261         % fineness 5
0262         v = [6, 5.0, 3.0, 0.1, 3.00, 5.0, 3.00, 5.0, 3.00, 5.0];
0263     otherwise % use moderate
0264         % this is called if some other ng_write_opt is used, like MSZBRICK
0265         v = [6, 2.0, 1.0, 0.3, 1.00, 1.5, 0.50, 2.0, 1.00, 2.0];
0266 end
0267 
0268 opt.dirname = '.';
0269 opt.loadgeomtypevar = '"All Geometry types (*.stl,*.stlb,*.step,*.stp,...)"';
0270 opt.exportfiletype = '"Neutral Format"';
0271 opt.meshoptions.fineness = v(1);
0272 opt.meshoptions.firststep = 'ag';
0273 opt.meshoptions.laststep = 'ov';
0274 opt.options.localh = 1;
0275 opt.options.delaunay = 1;
0276 opt.options.checkoverlap = 1;
0277 opt.options.checkchartboundary = 1;
0278 opt.options.startinsurface = 0;
0279 opt.options.blockfill = 1;
0280 opt.options.debugmode = 0;
0281 opt.options.dooptimize = 1;
0282 opt.options.parthread = 1;
0283 opt.options.elsizeweight = 0.2;
0284 opt.options.secondorder = 0;
0285 opt.options.elementorder = 1;
0286 opt.options.quad = 0;
0287 opt.options.inverttets = 0;
0288 opt.options.inverttrigs = 0;
0289 opt.options.autozrefine = 0;
0290 opt.options.meshsize = 1000;
0291 opt.options.minmeshsize = 0;
0292 opt.options.curvaturesafety = v(2);
0293 opt.options.segmentsperedge = v(3);
0294 opt.options.meshsizefilename = '';
0295 opt.options.badellimit = 175;
0296 opt.options.optsteps2d = 3;
0297 opt.options.optsteps3d = 5;
0298 opt.options.opterrpow = 2;
0299 opt.options.grading = v(4);
0300 opt.options.printmsg = 2;
0301 opt.geooptions.drawcsg = 1;
0302 opt.geooptions.detail = 0.001;
0303 opt.geooptions.accuracy = 1e-6;
0304 opt.geooptions.facets = 20;
0305 opt.geooptions.minx = -1000;
0306 opt.geooptions.miny = -1000;
0307 opt.geooptions.minz = -1000;
0308 opt.geooptions.maxx = 1000;
0309 opt.geooptions.maxy = 1000;
0310 opt.geooptions.maxz = 1000;
0311 opt.viewoptions.specpointvlen = 0.3;
0312 opt.viewoptions.light.amb = 0.3;
0313 opt.viewoptions.light.diff = 0.7;
0314 opt.viewoptions.light.spec = 1;
0315 opt.viewoptions.light.locviewer = 0;
0316 opt.viewoptions.mat.shininess = 50;
0317 opt.viewoptions.mat.transp = 0.3;
0318 opt.viewoptions.colormeshsize = 0;
0319 opt.viewoptions.whitebackground = 1;
0320 opt.viewoptions.drawcolorbar = 1;
0321 opt.viewoptions.drawcoordinatecross = 1;
0322 opt.viewoptions.drawnetgenlogo = 1;
0323 opt.viewoptions.stereo = 0;
0324 opt.viewoptions.drawfilledtrigs = 1;
0325 opt.viewoptions.drawedges = 0;
0326 opt.viewoptions.drawbadels = 0;
0327 opt.viewoptions.centerpoint = 0;
0328 opt.viewoptions.drawelement = 0;
0329 opt.viewoptions.drawoutline = 1;
0330 opt.viewoptions.drawtets = 0;
0331 opt.viewoptions.drawprisms = 0;
0332 opt.viewoptions.drawpyramids = 0;
0333 opt.viewoptions.drawhexes = 0;
0334 opt.viewoptions.drawidentified = 0;
0335 opt.viewoptions.drawpointnumbers = 0;
0336 opt.viewoptions.drawededges = 1;
0337 opt.viewoptions.drawedpoints = 1;
0338 opt.viewoptions.drawedpointnrs = 0;
0339 opt.viewoptions.drawedtangents = 0;
0340 opt.viewoptions.shrink = 1;
0341 opt.stloptions.showtrias = 0;
0342 opt.stloptions.showfilledtrias = 1;
0343 opt.stloptions.showedges = 1;
0344 opt.stloptions.showmarktrias = 0;
0345 opt.stloptions.showactivechart = 0;
0346 opt.stloptions.yangle = 30;
0347 opt.stloptions.contyangle = 20;
0348 opt.stloptions.edgecornerangle = 60;
0349 opt.stloptions.chartangle = 15;
0350 opt.stloptions.outerchartangle = 70;
0351 opt.stloptions.usesearchtree = 0;
0352 opt.stloptions.chartnumber = 1;
0353 opt.stloptions.charttrignumber = 1;
0354 opt.stloptions.chartnumberoffset = 0;
0355 opt.stloptions.atlasminh = 0.1;
0356 opt.stloptions.resthsurfcurvfac = v(5);
0357 opt.stloptions.resthsurfcurvenable = 0;
0358 opt.stloptions.resthatlasfac = 2;
0359 opt.stloptions.resthatlasenable = 1;
0360 opt.stloptions.resthchartdistfac = v(6);
0361 opt.stloptions.resthchartdistenable = 0;
0362 opt.stloptions.resthlinelengthfac = v(7);
0363 opt.stloptions.resthlinelengthenable = 1;
0364 opt.stloptions.resthcloseedgefac = v(8);
0365 opt.stloptions.resthcloseedgeenable = 1;
0366 opt.stloptions.resthedgeanglefac = v(9);
0367 opt.stloptions.resthedgeangleenable = 0;
0368 opt.stloptions.resthsurfmeshcurvfac = v(10);
0369 opt.stloptions.resthsurfmeshcurvenable = 0;
0370 opt.stloptions.recalchopt = 1;
0371 opt.visoptions.subdivisions = 1;
0372 
0373 function do_unit_test
0374    test_main_options()
0375    unit_test_MSZ()
0376    test_caching()
0377 
0378 function test_caching()
0379    for test=0:10; switch test
0380       case 0; fclose(fopen('ng.opt','w')); %exist!
0381               delete('ng.opt');
0382               eidors_cache clear
0383               nel_ = 1599;
0384       case 1; ng_write_opt('moderate'); % default
0385               nel_ = 1599;
0386       case 2; ng_write_opt('coarse');
0387               nel_ = 570;
0388       case 3; ng_write_opt('MSZCYLINDER',[0,0,.1,0,0,.2,1,0.05]);
0389               nel_ = 43861;
0390       otherwise; break;
0391       end
0392       fmdl= ng_mk_cyl_models(1,[2,0.5],0.1);
0393       nel = num_elems(fmdl);
0394       show_fem(fmdl); title(sprintf('Nel=%d',nel))
0395       unit_test_cmp(sprintf( ...
0396            'Cache: ng.opt #%d',test), nel, nel_);
0397    end
0398 
0399 function test_main_options()
0400 opt.meshoptions.fineness = 6;
0401 ng_write_opt(opt);
0402 fid = fopen('ng.opt','r'); str= fread(fid,[1,inf],'uint8=>char'); fclose(fid);
0403 unit_test_cmp('fineness=6',isempty( ...
0404     strfind(str, 'meshoptions.fineness  6')), 0);
0405 
0406 ng_write_opt('meshoptions.fineness',4,'meshoptions.firststep','aaa');
0407 fid = fopen('ng.opt','r'); str= fread(fid,[1,inf],'uint8=>char'); fclose(fid);
0408 unit_test_cmp('firststep=aaa',isempty( ...
0409     strfind(str, 'meshoptions.firststep  aaa')), 0);
0410 
0411 % the last one will not be written since output was requested
0412 opt = ng_write_opt('meshoptions.fineness',4,'meshoptions.firststep','bbb');
0413 fid = fopen('ng.opt','r'); str= fread(fid,[1,inf],'uint8=>char'); fclose(fid);
0414 unit_test_cmp('firststep=bbb',isempty( ...
0415     strfind(str, 'meshoptions.firststep  bbb')), 1);
0416 
0417 function unit_test_MSZ
0418    shape_str =  ...
0419      'solid mainobj = orthobrick(-9,-9,-9;9,9,9);';
0420    i=0; while(true); i=i+1; switch i
0421        case 1; n_exp = 8;
0422            ng_write_opt('very_coarse');
0423        case 2; n_exp = 22;
0424            ng_write_opt('fine');
0425        case 3; n_exp = 59;
0426            ng_write_opt('very_fine');
0427        case 4; n_exp = 8;
0428            ng_write_opt('moderate');
0429        case 5; n_exp = 746;
0430            ng_write_opt('MSZSPHERE',[5,5,5,4,1]);
0431        case 6; n_exp = 106;
0432            ng_write_opt('MSZBRICK',[5,5,5,9,9,9,1]);
0433        case 7; n_exp = 544;
0434            ng_write_opt('MSZCYLINDER',[5,5,5,8,8,8,5,1]);
0435        case 8; n_exp = 23;
0436            ng_write_opt('MSZCYLINDER',[5,5,5,8,8,8,5,5]);
0437          
0438        otherwise; break
0439        end
0440        eidors_cache clear
0441        fmdl = ng_mk_gen_models(shape_str,[],[],'');
0442        unit_test_cmp('opt:', num_nodes(fmdl), n_exp)
0443 %      show_fem(fmdl); disp(num_nodes(fmdl))
0444    end

Generated on Fri 30-Dec-2022 19:44:54 by m2html © 2005