Changeset 6415


Ignore:
Timestamp:
10/25/10 11:53:59 (14 years ago)
Author:
jschierm
Message:

Addition of partition polygons to kml_mesh_write.m and reorganization into functions.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • issm/trunk/src/m/kml/kml_mesh_write.m

    r6381 r6415  
    9393        error(['Data has incorrect number of ' num2str(numel(data)) ' values.']);
    9494    end
     95end
     96
     97if exist('edata','var')
     98    if ~exist('cmin','var')
     99        cmin=min(min(edata));
     100    end
     101    if ~exist('cmax','var')
     102        cmax=max(max(edata));
     103    end
     104end
     105
     106if ~exist('alt','var')
     107    alt=10000;
    95108end
    96109
     
    193206%  write folder for mesh
    194207
     208kml_mesh_elem(fid,md,varargin{3:end});
     209
     210%  write folder for partition segments
     211
     212if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     213    md.npart
     214    kml_part_flagedges(fid,md,varargin{3:end});
     215end
     216
     217%  write folder for unshared edges
     218
     219if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     220    md.npart
     221    kml_unsh_edges(fid,md,varargin{3:end});
     222end
     223
     224%  write folder for partition elements
     225
     226if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     227    md.npart
     228    kml_part_elems(fid,md,varargin{3:end});
     229end
     230
     231%  write folder for partition edges
     232
     233if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     234    md.npart
     235    kml_part_edges(fid,md,varargin{3:end});
     236end
     237
     238%  write folder for partitions
     239
     240if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     241    md.npart
     242    kml_partitions(fid,md,varargin{3:end});
     243end
     244
     245%  write trailer data
     246
     247fprintf(fid,'  </Document>\n');
     248fprintf(fid,'</kml>\n');
     249
     250fclose(fid);
     251display('End of file successfully written.');
     252
     253end
     254
     255%%
     256%  create kml polygons for the element mesh.
     257%
     258%  []=kml_mesh_elem(fid,md,params)
     259%
     260%  where the required input is:
     261%    fid           (numeric, file ID of .kml file)
     262%    md            (model, model class object)
     263%
     264%  the optional input is:
     265%    params        (string/numeric, parameter names and values)
     266%
     267%  and the optional input is:
     268%    data          (numeric, element or nodal results data)
     269%    alt           (numeric, altitude for polygons, default 10000)
     270%    cmin          (numeric, minimum of color map)
     271%    cmax          (numeric, maximum of color map)
     272%    cmap          (char or numeric, colormap definition)
     273%
     274function []=kml_mesh_elem(varargin)
     275
     276if ~nargin
     277    help kml_mesh_elem
     278    return
     279end
     280
     281%%  process input data
     282
     283iarg=1;
     284if (nargin >= 1)
     285    fid=varargin{1};
     286end
     287if ~exist('fid','var') || isempty(fid) || (fid < 0)
     288    error('File ID ''%d'' must be open.',fid);
     289end
     290
     291iarg=iarg+1;
     292if (nargin >= 2)
     293    md=varargin{2};
     294end
     295if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     296    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     297end
     298
     299%  parameters
     300
     301iarg=iarg+1;
     302while (iarg <= nargin-1)
     303    if ischar(varargin{iarg})
     304        eval([varargin{iarg} '=varargin{iarg+1};']);
     305        if (numel(varargin{iarg+1}) <= 20)
     306            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     307        else
     308            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     309        end
     310        if strcmpi(varargin{iarg},'data')
     311            cdata=inputname(iarg+1);
     312        end
     313    else
     314        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     315    end
     316    iarg=iarg+2;
     317end
     318
     319if exist('data','var') && ~isempty(data)
     320    if     (numel(data)==md.numberofelements)
     321        edata=data;
     322    elseif (numel(data)==md.numberofgrids)
     323        ndata=data;
     324        display('Averaging nodal data to element data.');
     325        edata=zeros(1,md.numberofelements);
     326        for i=1:size(md.elements,1)
     327            for j=1:size(md.elements,2)
     328                edata(i)=edata(i)+ndata(md.elements(i,j));
     329            end
     330            edata(i)=edata(i)/size(md.elements,2);
     331        end
     332    else
     333        error(['Data has incorrect number of ' num2str(numel(data)) ' values.']);
     334    end
     335end
     336
     337%  colormap command operates on a figure, so create an invisible one
     338%  (could also directly call colormaps, e.g. jet(64), but risky)
     339
     340hfig=figure('Visible','off');
     341if exist('cmap','var')
     342    colormap(cmap)
     343end
     344cmap=colormap;
     345close(hfig)
     346   
     347if exist('edata','var')
     348    if ~exist('cmin','var')
     349        cmin=min(min(edata));
     350    end
     351    if ~exist('cmax','var')
     352        cmax=max(max(edata));
     353    end
     354end
     355
     356if ~exist('alt','var')
     357    alt=10000;
     358end
     359
     360%%  write folder for mesh
     361
    195362fprintf(fid,'    <Folder>\n');
    196363if exist('cdata','var') && ~isempty(cdata)
     
    204371
    205372%  write each element as a polygon
    206 
    207 if exist('edata','var')
    208     if ~exist('cmin','var')
    209         cmin=min(min(edata));
    210     end
    211     if ~exist('cmax','var')
    212         cmax=max(max(edata));
    213     end
    214 end
    215 
    216 if ~exist('alt','var')
    217     alt=10000;
    218 end
    219373
    220374disp(['Writing ' num2str(size(md.elements,1)) ' tria elements as KML polygons.']);
     
    256410fprintf(fid,'    </Folder>\n');
    257411
    258 %  write folder for partition segments
     412end
     413
     414%%
     415%  create kml linestrings for the flagged partition edges.
     416%
     417%  []=kml_part_flagedges(fid,md,params)
     418%
     419%  where the required input is:
     420%    fid           (char, file ID of .kml file)
     421%    md            (model, model class object)
     422%
     423%  the optional input is:
     424%    params        (string/numeric, parameter names and values)
     425%
     426%  and the optional input is:
     427%    alt           (numeric, altitude for polygons, default 10000)
     428%    prtplt        (char, 'off'/'no' for partition segment plot)
     429%
     430function []=kml_part_flagedges(varargin)
     431
     432if ~nargin
     433    help kml_part_flagedges
     434    return
     435end
     436
     437%%  process input data
     438
     439iarg=1;
     440if (nargin >= 1)
     441    fid=varargin{1};
     442end
     443if ~exist('fid','var') || isempty(fid) || (fid < 0)
     444    error('File ID ''%d'' must be open.',fid);
     445end
     446
     447iarg=iarg+1;
     448if (nargin >= 2)
     449    md=varargin{2};
     450end
     451if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     452    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     453end
     454
     455%  parameters
     456
     457iarg=iarg+1;
     458while (iarg <= nargin-1)
     459    if ischar(varargin{iarg})
     460        eval([varargin{iarg} '=varargin{iarg+1};']);
     461        if (numel(varargin{iarg+1}) <= 20)
     462            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     463        else
     464            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     465        end
     466    else
     467        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     468    end
     469    iarg=iarg+2;
     470end
     471
     472if ~exist('alt','var')
     473    alt=10000;
     474end
     475
     476%%  write folder for partition segments
    259477
    260478if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     
    292510end
    293511
    294 %  write folder for unshared edges
     512end
     513
     514%%
     515%  create kml linestrings for the unshared element edges.
     516%
     517%  []=kml_unsh_edges(fid,md,params)
     518%
     519%  where the required input is:
     520%    fid           (char, file ID of .kml file)
     521%    md            (model, model class object)
     522%
     523%  the optional input is:
     524%    params        (string/numeric, parameter names and values)
     525%
     526%  and the optional input is:
     527%    alt           (numeric, altitude for polygons, default 10000)
     528%    prtplt        (char, 'off'/'no' for partition segment plot)
     529%
     530function []=kml_unsh_edges(varargin)
     531
     532if ~nargin
     533    help kml_unsh_edges
     534    return
     535end
     536
     537%%  process input data
     538
     539iarg=1;
     540if (nargin >= 1)
     541    fid=varargin{1};
     542end
     543if ~exist('fid','var') || isempty(fid) || (fid < 0)
     544    error('File ID ''%d'' must be open.',fid);
     545end
     546
     547iarg=iarg+1;
     548if (nargin >= 2)
     549    md=varargin{2};
     550end
     551if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     552    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     553end
     554
     555%  parameters
     556
     557iarg=iarg+1;
     558while (iarg <= nargin-1)
     559    if ischar(varargin{iarg})
     560        eval([varargin{iarg} '=varargin{iarg+1};']);
     561        if (numel(varargin{iarg+1}) <= 20)
     562            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     563        else
     564            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     565        end
     566    else
     567        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     568    end
     569    iarg=iarg+2;
     570end
     571
     572if ~exist('alt','var')
     573    alt=10000;
     574end
     575
     576%%  write folder for unshared edges
    295577
    296578if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     
    334616end
    335617
    336 %  write folder for partitions
     618end
     619
     620%%
     621%  create kml polygons for the partition elements.
     622%
     623%  []=kml_part_elems(fid,md,params)
     624%
     625%  where the required input is:
     626%    fid           (char, file ID of .kml file)
     627%    md            (model, model class object)
     628%
     629%  the optional input is:
     630%    params        (string/numeric, parameter names and values)
     631%
     632%  and the optional input is:
     633%    data          (numeric, element or nodal results data)
     634%    alt           (numeric, altitude for polygons, default 10000)
     635%    cmin          (numeric, minimum of color map)
     636%    cmax          (numeric, maximum of color map)
     637%    cmap          (char or numeric, colormap definition)
     638%    prtplt        (char, 'off'/'no' for partition segment plot)
     639%
     640function []=kml_part_elems(varargin)
     641
     642if ~nargin
     643    help kml_part_elems
     644    return
     645end
     646
     647%%  process input data
     648
     649iarg=1;
     650if (nargin >= 1)
     651    fid=varargin{1};
     652end
     653if ~exist('fid','var') || isempty(fid) || (fid < 0)
     654    error('File ID ''%d'' must be open.',fid);
     655end
     656
     657iarg=iarg+1;
     658if (nargin >= 2)
     659    md=varargin{2};
     660end
     661if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     662    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     663end
     664
     665%  parameters
     666
     667iarg=iarg+1;
     668while (iarg <= nargin-1)
     669    if ischar(varargin{iarg})
     670        eval([varargin{iarg} '=varargin{iarg+1};']);
     671        if (numel(varargin{iarg+1}) <= 20)
     672            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     673        else
     674            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     675        end
     676        if strcmpi(varargin{iarg},'data')
     677            cdata=inputname(iarg+1);
     678        end
     679    else
     680        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     681    end
     682    iarg=iarg+2;
     683end
     684
     685if exist('data','var') && ~isempty(data)
     686    if     (numel(data)==md.numberofelements)
     687        edata=data;
     688    elseif (numel(data)==md.numberofgrids)
     689        ndata=data;
     690        display('Averaging nodal data to element data.');
     691        edata=zeros(1,md.numberofelements);
     692        for i=1:size(md.elements,1)
     693            for j=1:size(md.elements,2)
     694                edata(i)=edata(i)+ndata(md.elements(i,j));
     695            end
     696            edata(i)=edata(i)/size(md.elements,2);
     697        end
     698    else
     699        error(['Data has incorrect number of ' num2str(numel(data)) ' values.']);
     700    end
     701end
     702
     703%  colormap command operates on a figure, so create an invisible one
     704%  (could also directly call colormaps, e.g. jet(64), but risky)
     705
     706hfig=figure('Visible','off');
     707if exist('cmap','var')
     708    colormap(cmap)
     709end
     710cmap=colormap;
     711close(hfig)
     712   
     713if exist('edata','var')
     714    if ~exist('cmin','var')
     715        cmin=min(min(edata));
     716    end
     717    if ~exist('cmax','var')
     718        cmax=max(max(edata));
     719    end
     720end
     721
     722if ~exist('alt','var')
     723    alt=10000;
     724end
     725
     726%  write folder for partition elements
    337727
    338728if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
    339729    md.npart
    340730    fprintf(fid,'    <Folder>\n');
    341     fprintf(fid,'      <name>Partitions</name>\n');
     731    fprintf(fid,'      <name>Partition Elements</name>\n');
    342732    fprintf(fid,'      <visibility>1</visibility>\n');
    343733    fprintf(fid,'      <description>Partitions=%d, Nodes=%d</description>\n',...
     
    415805end
    416806
    417 %  write folder for partition edges
     807end
     808
     809%%
     810%  create kml linestrings for the partition edges.
     811%
     812%  []=kml_part_edges(fid,md,params)
     813%
     814%  where the required input is:
     815%    fid           (char, file ID of .kml file)
     816%    md            (model, model class object)
     817%
     818%  the optional input is:
     819%    params        (string/numeric, parameter names and values)
     820%
     821%  and the optional input is:
     822%    data          (numeric, element or nodal results data)
     823%    alt           (numeric, altitude for polygons, default 10000)
     824%    cmin          (numeric, minimum of color map)
     825%    cmax          (numeric, maximum of color map)
     826%    cmap          (char or numeric, colormap definition)
     827%    prtplt        (char, 'off'/'no' for partition segment plot)
     828%
     829function []=kml_part_edges(varargin)
     830
     831if ~nargin
     832    help kml_part_edges
     833    return
     834end
     835
     836%%  process input data
     837
     838iarg=1;
     839if (nargin >= 1)
     840    fid=varargin{1};
     841end
     842if ~exist('fid','var') || isempty(fid) || (fid < 0)
     843    error('File ID ''%d'' must be open.',fid);
     844end
     845
     846iarg=iarg+1;
     847if (nargin >= 2)
     848    md=varargin{2};
     849end
     850if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     851    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     852end
     853
     854%  parameters
     855
     856iarg=iarg+1;
     857while (iarg <= nargin-1)
     858    if ischar(varargin{iarg})
     859        eval([varargin{iarg} '=varargin{iarg+1};']);
     860        if (numel(varargin{iarg+1}) <= 20)
     861            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     862        else
     863            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     864        end
     865        if strcmpi(varargin{iarg},'data')
     866            cdata=inputname(iarg+1);
     867        end
     868    else
     869        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     870    end
     871    iarg=iarg+2;
     872end
     873
     874if exist('data','var') && ~isempty(data)
     875    if     (numel(data)==md.numberofelements)
     876        edata=data;
     877    elseif (numel(data)==md.numberofgrids)
     878        ndata=data;
     879        display('Averaging nodal data to element data.');
     880        edata=zeros(1,md.numberofelements);
     881        for i=1:size(md.elements,1)
     882            for j=1:size(md.elements,2)
     883                edata(i)=edata(i)+ndata(md.elements(i,j));
     884            end
     885            edata(i)=edata(i)/size(md.elements,2);
     886        end
     887    else
     888        error(['Data has incorrect number of ' num2str(numel(data)) ' values.']);
     889    end
     890end
     891
     892%  colormap command operates on a figure, so create an invisible one
     893%  (could also directly call colormaps, e.g. jet(64), but risky)
     894
     895hfig=figure('Visible','off');
     896if exist('cmap','var')
     897    colormap(cmap)
     898end
     899cmap=colormap;
     900close(hfig)
     901   
     902if exist('edata','var')
     903    if ~exist('cmin','var')
     904        cmin=min(min(edata));
     905    end
     906    if ~exist('cmax','var')
     907        cmax=max(max(edata));
     908    end
     909end
     910
     911if ~exist('alt','var')
     912    alt=10000;
     913end
     914
     915%%  write folder for partition edges
    418916
    419917if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     
    5101008            j=iloop(i);
    5111009            while (j < iloop(i+1))
    512 %  find which edge of element is referenced in perimeter list
     1010%  find which side of element is referenced in perimeter list
    5131011                for l=1:size(elemp,2)
    5141012                    if ((elemp(elemper(j),l)          == edgeper(j,1)) && ...
     
    5211019                end
    5221020
    523 %  check if element edge connects nodes in partition
     1021%  check if element side connects nodes in partition
    5241022                if (epartp(elemper(j),jedge)          == k) && ...
    5251023                   (epartp(elemper(j),mod(jedge,3)+1) == k)
    526 %  write out specified element edge
     1024%  write out specified element side
    5271025                    disp(['segment j=' int2str(j) ' unshared edge ' int2str(edgeper(j,1)) ' to ' int2str(edgeper(j,2)) ' on side ' int2str(jedge) ' from element ' int2str(elemper(j)) ' written.'])
     1026%  if first edge, write out first node
    5281027                    if ~elast
    5291028                        [lat(end+1),long(end+1)]=mapxy(md.x(edgeper(j,1)),md.y(edgeper(j,1)),'s');
     
    5461045
    5471046                    while 1
    548 %  if first edge, figure out direction from perimeter direction
     1047%  if first edge, figure out direction from perimeter edge direction
    5491048                        if ~nlast && ~slast
    5501049                            nlast=find(elemp(ielem,:)==edgeper(j,1));
     
    5661065
    5671066%  find how many nodes of current element are in current partition
    568 %  (1 or 2, not 3)
     1067%  (1 or 2, not 3) and handle each permutation separately
    5691068                            ipart=find(epartp(ielem,:)==k);
    5701069%  two nodes are in current partition, so cut off other node
     
    5971096                                            nlast=0;
    5981097                                    end
     1098%  other two are in the same partition, so cut them off
    5991099                                else
    600 %  other two are in the same partition, so cut them off
    6011100                                    switch ipart
    6021101                                        case nlast
     
    6161115%  last edge exited last element at node
    6171116                            if nlast
    618 %  write out first node of first edge for half-edge to midpoint
     1117%  write out first node of first side for half-edge to midpoint
    6191118                                disp(['segment j=' int2str(j) ' unshared half edge from node ' int2str(elemp(ielem,nlast)) ' (node ' int2str(nlast) ') on side ' int2str(slast) ' from element ' int2str(ielem) ' written.'])
    6201119                                [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,nlast))),...
     
    6241123                            nlast=0;
    6251124                           
    626                             if ~elast
    627 %  write out midpoint of first edge
    628                                 [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,slast))...
    629                                                                +md.x(elemp(ielem,mod(slast,3)+1)))/2.,...
    630                                                                (md.y(elemp(ielem,slast))...
    631                                                                +md.y(elemp(ielem,mod(slast,3)+1)))/2.,'s');
    632                                 fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
    633                             end
     1125%  write out midpoint of first side
     1126                            [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,slast))...
     1127                                                           +md.x(elemp(ielem,mod(slast,3)+1)))/2.,...
     1128                                                           (md.y(elemp(ielem,slast))...
     1129                                                           +md.y(elemp(ielem,mod(slast,3)+1)))/2.,'s');
     1130                            fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
    6341131                        end
    6351132
     
    6401137                                nlast=find(elemp(ielem,:)==nlast,1);
    6411138                            end
    642 %  half-edge occurs on unshared edge from current node (unique unless mesh
     1139%  half-edge occurs on unshared side from current node (unique unless mesh
    6431140%  is only attached at node)
    6441141                            switch nlast
     
    6681165                                    end
    6691166                            end
    670 %  write out half-edge from current node to midpoint of unshared edge
     1167%  write out half-edge from current node to midpoint of unshared side
    6711168                            disp(['segment j=' int2str(j) ' unshared half edge from node ' int2str(elemp(ielem,nlast)) ' (node ' int2str(nlast) ') on side ' int2str(slast) ' from element ' int2str(ielem) ' written.'])
    6721169                            [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,nlast))...
     
    6801177                        elseif slast
    6811178                            if elast
    682 %  find where last edge on previous element occurs on current element
     1179%  find where last side on previous element occurs on current element
    6831180                                slast=find(edgeadjp(ielem,:)==elast,1);
    6841181                            end
     
    6861183
    6871184%  find how many nodes of current element are in current partition
    688 %  (1 or 2, not 3)
     1185%  (1 or 2, not 3) and handle each permutation separately
    6891186                        ipart=find(epartp(ielem,:)==k);
    6901187                        if (length(ipart) == 2)
     
    7021199                               (epartp(ielem,2) ~= epartp(ielem,3)) && ...
    7031200                               (epartp(ielem,3) ~= epartp(ielem,1))
    704 %  all different, so write out centroid
     1201%  all different, so cut through centroid
    7051202                                disp(['element ielem=' int2str(ielem) ' centroid written.'])
    7061203                                [lat(end+1),long(end+1)]=mapxy(sum(md.x(elemp(ielem,:)))/3.,...
     
    7181215                            end
    7191216                        end
    720 %  write out midpoint of opposite edge
     1217%  write out midpoint of opposite side
    7211218                        disp(['segment j=' int2str(j) ' internal edge from side ' int2str(slast) ' to side ' int2str(snext) ' from element ' int2str(ielem) ' written.'])
    7221219                        [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,snext))...
     
    7281225                        nlast=0;
    7291226                        slast=snext;
    730 %  find adjacent element to opposite edge
     1227%  find adjacent element to opposite side
    7311228                        ielem=edgeadjp(elast,slast);
    732 %  if opposite edge is unshared, find it in edge perimeter list
     1229%  if opposite side is unshared, find it in edge perimeter list
    7331230                        if ~ielem
    7341231                            jlast=find(elemper(j:end)==elast)+j-1;
     
    7461243                                j=iloop(i+1)-1;
    7471244                            end
    748 %  write out half-edge from midpoint of unshared edge to node
     1245%  write out half-edge from midpoint of unshared side to node
    7491246                            if (epartp(elast,slast) == k)
    7501247                                nnext=slast;
     
    7851282end
    7861283
    787 %  write trailer data
    788 
    789 fprintf(fid,'  </Document>\n');
    790 fprintf(fid,'</kml>\n');
    791 
    792 fclose(fid);
    793 display('End of file successfully written.');
    794 
     1284end
     1285
     1286%%
     1287%  create kml polygons for the partitions.
     1288%
     1289%  []=kml_partitions(fid,md,params)
     1290%
     1291%  where the required input is:
     1292%    fid           (char, file ID of .kml file)
     1293%    md            (model, model class object)
     1294%
     1295%  the optional input is:
     1296%    params        (string/numeric, parameter names and values)
     1297%
     1298%  and the optional input is:
     1299%    data          (numeric, element or nodal results data)
     1300%    alt           (numeric, altitude for polygons, default 10000)
     1301%    cmin          (numeric, minimum of color map)
     1302%    cmax          (numeric, maximum of color map)
     1303%    cmap          (char or numeric, colormap definition)
     1304%    prtplt        (char, 'off'/'no' for partition segment plot)
     1305%
     1306function []=kml_partitions(varargin)
     1307
     1308if ~nargin
     1309    help kml_part_edges
     1310    return
     1311end
     1312
     1313%%  process input data
     1314
     1315iarg=1;
     1316if (nargin >= 1)
     1317    fid=varargin{1};
     1318end
     1319if ~exist('fid','var') || isempty(fid) || (fid < 0)
     1320    error('File ID ''%d'' must be open.',fid);
     1321end
     1322
     1323iarg=iarg+1;
     1324if (nargin >= 2)
     1325    md=varargin{2};
     1326end
     1327if ~exist('md','var') || isempty(md) || ~isa(md,'model')
     1328    error(['Model ''' inputname(iarg) ''' is unrecognized class ''' class(md) '''.']);
     1329end
     1330
     1331%  parameters
     1332
     1333iarg=iarg+1;
     1334while (iarg <= nargin-1)
     1335    if ischar(varargin{iarg})
     1336        eval([varargin{iarg} '=varargin{iarg+1};']);
     1337        if (numel(varargin{iarg+1}) <= 20)
     1338            disp([varargin{iarg} '=' any2str(varargin{iarg+1}) ';']);
     1339        else
     1340            disp([varargin{iarg} '=' string_size(varargin{iarg+1}) ' ' class(varargin{iarg+1}) ';']);
     1341        end
     1342        if strcmpi(varargin{iarg},'data')
     1343            cdata=inputname(iarg+1);
     1344        end
     1345    else
     1346        error(['''' any2str(varargin{iarg}) ''' is not a parameter name.']);
     1347    end
     1348    iarg=iarg+2;
     1349end
     1350
     1351if exist('data','var') && ~isempty(data)
     1352    if     (numel(data)==md.numberofelements)
     1353        edata=data;
     1354    elseif (numel(data)==md.numberofgrids)
     1355        ndata=data;
     1356        display('Averaging nodal data to element data.');
     1357        edata=zeros(1,md.numberofelements);
     1358        for i=1:size(md.elements,1)
     1359            for j=1:size(md.elements,2)
     1360                edata(i)=edata(i)+ndata(md.elements(i,j));
     1361            end
     1362            edata(i)=edata(i)/size(md.elements,2);
     1363        end
     1364    else
     1365        error(['Data has incorrect number of ' num2str(numel(data)) ' values.']);
     1366    end
     1367end
     1368
     1369%  colormap command operates on a figure, so create an invisible one
     1370%  (could also directly call colormaps, e.g. jet(64), but risky)
     1371
     1372hfig=figure('Visible','off');
     1373if exist('cmap','var')
     1374    colormap(cmap)
     1375end
     1376cmap=colormap;
     1377close(hfig)
     1378   
     1379if exist('edata','var')
     1380    if ~exist('cmin','var')
     1381        cmin=min(min(edata));
     1382    end
     1383    if ~exist('cmax','var')
     1384        cmax=max(max(edata));
     1385    end
     1386end
     1387
     1388if ~exist('alt','var')
     1389    alt=10000;
     1390end
     1391
     1392%%  write folder for partitions
     1393
     1394if (~exist('prtplt','var') || strncmpi(prtplt,'on' ,2) || strncmpi(prtplt,'y',1)) && ...
     1395    md.npart
     1396    fprintf(fid,'    <Folder>\n');
     1397    fprintf(fid,'      <name>Partitions</name>\n');
     1398    fprintf(fid,'      <visibility>1</visibility>\n');
     1399    fprintf(fid,'      <description>Partitions=%d, Nodes=%d</description>\n',...
     1400        md.npart,md.numberofgrids);
     1401
     1402%  write each partition loop as linestrings
     1403
     1404    disp(['Writing ' num2str(md.npart) ' partitions as KML polygons.']);
     1405    epart=md.part(md.elements)+1;
     1406    if exist('ndata','var') || exist('edata','var')
     1407        pdata=zeros(1,md.npart);
     1408        pdata(:)=NaN;
     1409    end
     1410
     1411%  loop over each partition
     1412
     1413    for k=1:md.npart
     1414        disp(['partition k=' int2str(k)])
     1415       
     1416%  for each partition, find all the included elements and determine the
     1417%  perimeter (including those shared by another partition)
     1418
     1419        [icol,irow]=find(epart'==k);
     1420        irow=unique(irow);
     1421        elemp=md.elements(irow,:);
     1422        epartp=epart(irow,:);
     1423        nodeconp=nodeconnectivity(elemp,md.numberofgrids);
     1424        [edgeadjp]=edgeadjacency(elemp,nodeconp);
     1425        [edgeper,elemper,iloop]=edgeperimeter(elemp,nodeconp,edgeadjp);
     1426        iloop(end+1)=size(edgeper,1)+1;
     1427       
     1428%  determine the data to be used for the colors (if any)
     1429
     1430        if exist('ndata','var')
     1431            pdata(k)=ndata(find(md.part+1==k,1));
     1432        elseif exist('edata','var')
     1433            for i=1:size(epartp,1)
     1434                if isempty(find(epart(i,:)~=k,1))
     1435                    pdata(k)=edata(irow(i));
     1436                    break
     1437                end
     1438            end
     1439            if isnan(pdata(k))
     1440                warning('Data for Partition %d is not defined.\n',k)
     1441            end
     1442        end
     1443       
     1444%  loop over each loop of the perimeter for the given partition
     1445
     1446        for i=1:length(iloop)-1
     1447            fprintf(fid,'      <Placemark>\n');
     1448            if (length(iloop)-1 > 1)
     1449                fprintf(fid,'        <name>Partition %d, Loop %d</name>\n',k,i);
     1450            else
     1451                fprintf(fid,'        <name>Partition %d</name>\n',k);
     1452            end
     1453            fprintf(fid,'        <visibility>1</visibility>\n');
     1454            if exist('pdata','var')
     1455                fprintf(fid,'        <description>Partition data: %g</description>\n',pdata(k));
     1456                imap = fix((pdata(k)-cmin)/(cmax-cmin)*size(cmap,1))+1;
     1457                if     (imap >= 1) && (imap <= size(cmap,1))
     1458                    fprintf(fid,'        <styleUrl>#MatlabColor%d</styleUrl>\n',imap);
     1459                elseif (pdata(k) == cmax)
     1460                    fprintf(fid,'        <styleUrl>#MatlabColor%d</styleUrl>\n',size(cmap,1));
     1461                else
     1462                    fprintf(fid,'        <styleUrl>#BlackLineEmptyPoly</styleUrl>\n');
     1463                end
     1464            else
     1465                fprintf(fid,'        <styleUrl>#BlackLineRandomPoly</styleUrl>\n');
     1466            end
     1467            fprintf(fid,'        <Polygon>\n');
     1468            fprintf(fid,'          <extrude>1</extrude>\n');
     1469            fprintf(fid,'          <altitudeMode>relativeToGround</altitudeMode>\n');
     1470            fprintf(fid,'          <outerBoundaryIs>\n');
     1471            fprintf(fid,'            <LinearRing>\n');
     1472            fprintf(fid,'              <coordinates>\n');
     1473            elast=0;
     1474            nlast=0;
     1475            slast=0;
     1476            lat=[];
     1477            long=[];
     1478           
     1479%  loop over the element edges on the loop of the partition
     1480
     1481            j=iloop(i);
     1482            while (j < iloop(i+1))
     1483%  find which side of element is referenced in perimeter list
     1484                for l=1:size(elemp,2)
     1485                    if ((elemp(elemper(j),l)          == edgeper(j,1)) && ...
     1486                        (elemp(elemper(j),mod(l,3)+1) == edgeper(j,2))) || ...
     1487                       ((elemp(elemper(j),l)          == edgeper(j,2)) && ...
     1488                        (elemp(elemper(j),mod(l,3)+1) == edgeper(j,1)))
     1489                        jedge=l;
     1490                        break
     1491                    end
     1492                end
     1493
     1494%  check if element side connects nodes in partition
     1495                if (epartp(elemper(j),jedge)          == k) && ...
     1496                   (epartp(elemper(j),mod(jedge,3)+1) == k)
     1497%  write out specified element side
     1498                    disp(['segment j=' int2str(j) ' unshared edge ' int2str(edgeper(j,1)) ' to ' int2str(edgeper(j,2)) ' on side ' int2str(jedge) ' from element ' int2str(elemper(j)) ' written.'])
     1499%  if first edge, write out first node
     1500                    if ~elast
     1501                        [lat(end+1),long(end+1)]=mapxy(md.x(edgeper(j,1)),md.y(edgeper(j,1)),'s');
     1502                        fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1503                    end
     1504                    [lat(end+1),long(end+1)]=mapxy(md.x(edgeper(j,2)),md.y(edgeper(j,2)),'s');
     1505                    fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1506                    elast=elemper(j);
     1507                    nlast=edgeper(j,2);
     1508                    slast=0;
     1509                    j=j+1;
     1510                   
     1511%  element not entirely within partition, so figure out boundary
     1512                else
     1513                    disp(['segment j=' int2str(j) ' from element ' int2str(elemper(j)) ' shared by other partitions.'])
     1514                    ielem=elemper(j);
     1515
     1516%  follow partition boundary through elements not wholly in partition
     1517%  (may include elements not in perimeter list)
     1518
     1519                    while 1
     1520%  if first edge, figure out direction from perimeter edge direction
     1521                        if ~nlast && ~slast
     1522                            nlast=find(elemp(ielem,:)==edgeper(j,1));
     1523                            nnext=find(elemp(ielem,:)==edgeper(j,2));
     1524                            if     (nlast+nnext == 3)
     1525                                slast=1;
     1526                            elseif (nlast+nnext == 5)
     1527                                slast=2;
     1528                            elseif (nlast+nnext == 4)
     1529                                slast=3;
     1530                            end
     1531                            if     (nnext+(6-nlast-nnext) == 3)
     1532                                snext=1;
     1533                            elseif (nnext+(6-nlast-nnext) == 5)
     1534                                snext=2;
     1535                            elseif (nnext+(6-nlast-nnext) == 4)
     1536                                snext=3;
     1537                            end
     1538
     1539%  find how many nodes of current element are in current partition
     1540%  (1 or 2, not 3) and handle each permutation separately
     1541                            ipart=find(epartp(ielem,:)==k);
     1542%  two nodes are in current partition, so cut off other node
     1543                            if (length(ipart) == 2)
     1544                                switch 6-sum(ipart)
     1545                                    case nlast
     1546                                        slast=6-slast-snext;
     1547                                        nlast=0;
     1548                                    case nnext
     1549                                        if (epartp(ielem,nnext) == k)
     1550                                            nlast=nnext;
     1551                                        end
     1552                                    otherwise
     1553                                        slast=6-slast-snext;
     1554                                        nlast=0;
     1555                                end
     1556%  one node is in current partition
     1557                            else
     1558%  all different, so cut through centroid
     1559                                if (epartp(ielem,1) ~= epartp(ielem,2)) && ...
     1560                                   (epartp(ielem,2) ~= epartp(ielem,3)) && ...
     1561                                   (epartp(ielem,3) ~= epartp(ielem,1))
     1562                                    switch ipart
     1563                                        case {nlast,nnext}
     1564                                            if (epartp(ielem,nnext) == k)
     1565                                                nlast=nnext;
     1566                                            end
     1567                                        otherwise
     1568                                            slast=6-slast-snext;
     1569                                            nlast=0;
     1570                                    end
     1571%  other two are in the same partition, so cut them off
     1572                                else
     1573                                    switch ipart
     1574                                        case nlast
     1575                                            if (epartp(ielem,nnext) == k)
     1576                                                nlast=nnext;
     1577                                            end
     1578                                        case nnext
     1579                                            slast=snext;
     1580                                            nlast=0;
     1581                                        otherwise
     1582                                            slast=6-slast-snext;
     1583                                            nlast=0;
     1584                                    end
     1585                                end
     1586                            end
     1587
     1588%  last edge exited last element at node
     1589                            if nlast
     1590%  write out first node of first side for half-edge to midpoint
     1591                                disp(['segment j=' int2str(j) ' unshared half edge from node ' int2str(elemp(ielem,nlast)) ' (node ' int2str(nlast) ') on side ' int2str(slast) ' from element ' int2str(ielem) ' written.'])
     1592                                [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,nlast))),...
     1593                                                               (md.y(elemp(ielem,nlast))),'s');
     1594                                fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1595                            end
     1596                            nlast=0;
     1597                           
     1598%  write out midpoint of first side
     1599                            [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,slast))...
     1600                                                           +md.x(elemp(ielem,mod(slast,3)+1)))/2.,...
     1601                                                           (md.y(elemp(ielem,slast))...
     1602                                                           +md.y(elemp(ielem,mod(slast,3)+1)))/2.,'s');
     1603                            fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1604                        end
     1605
     1606%  last edge exited last element at node
     1607                        if nlast
     1608                            if elast
     1609%  find where last node on previous element occurs on current element
     1610                                nlast=find(elemp(ielem,:)==nlast,1);
     1611                            end
     1612%  half-edge occurs on unshared side from current node (unique unless mesh
     1613%  is only attached at node)
     1614                            switch nlast
     1615                                case 1
     1616                                    if ~edgeadjp(ielem,1)
     1617                                        nnext=2;
     1618                                        slast=1;
     1619                                    else
     1620                                        nnext=3;
     1621                                        slast=3;
     1622                                    end
     1623                                case 2
     1624                                    if ~edgeadjp(ielem,2)
     1625                                        nnext=3;
     1626                                        slast=2;
     1627                                    else
     1628                                        nnext=1;
     1629                                        slast=1;
     1630                                    end
     1631                                case 3
     1632                                    if ~edgeadjp(ielem,3)
     1633                                        nnext=1;
     1634                                        slast=3;
     1635                                    else
     1636                                        nnext=2;
     1637                                        slast=2;
     1638                                    end
     1639                            end
     1640%  write out half-edge from current node to midpoint of unshared side
     1641                            disp(['segment j=' int2str(j) ' unshared half edge from node ' int2str(elemp(ielem,nlast)) ' (node ' int2str(nlast) ') on side ' int2str(slast) ' from element ' int2str(ielem) ' written.'])
     1642                            [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,nlast))...
     1643                                                           +md.x(elemp(ielem,nnext)))/2.,...
     1644                                                           (md.y(elemp(ielem,nlast))...
     1645                                                           +md.y(elemp(ielem,nnext)))/2.,'s');
     1646                            fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1647                            nlast=0;
     1648
     1649%  last edge exited last element at midpoint of side
     1650                        elseif slast
     1651                            if elast
     1652%  find where last side on previous element occurs on current element
     1653                                slast=find(edgeadjp(ielem,:)==elast,1);
     1654                            end
     1655                        end
     1656
     1657%  find how many nodes of current element are in current partition
     1658%  (1 or 2, not 3) and handle each permutation separately
     1659                        ipart=find(epartp(ielem,:)==k);
     1660                        if (length(ipart) == 2)
     1661%  two nodes are in current partition, so cut off other node
     1662                            switch 6-sum(ipart)
     1663                                case 1
     1664                                    snext=3+1-slast;
     1665                                case 2
     1666                                    snext=1+2-slast;
     1667                                case 3
     1668                                    snext=2+3-slast;
     1669                            end
     1670                        else
     1671                            if (epartp(ielem,1) ~= epartp(ielem,2)) && ...
     1672                               (epartp(ielem,2) ~= epartp(ielem,3)) && ...
     1673                               (epartp(ielem,3) ~= epartp(ielem,1))
     1674%  all different, so cut through centroid
     1675                                disp(['element ielem=' int2str(ielem) ' centroid written.'])
     1676                                [lat(end+1),long(end+1)]=mapxy(sum(md.x(elemp(ielem,:)))/3.,...
     1677                                                               sum(md.y(elemp(ielem,:)))/3.,'s');
     1678                                fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1679                            end
     1680%  one node is in current partition, so cut off other two nodes
     1681                            switch ipart
     1682                                case 1
     1683                                    snext=3+1-slast;
     1684                                case 2
     1685                                    snext=1+2-slast;
     1686                                case 3
     1687                                    snext=2+3-slast;
     1688                            end
     1689                        end
     1690%  write out midpoint of opposite side
     1691                        disp(['segment j=' int2str(j) ' internal edge from side ' int2str(slast) ' to side ' int2str(snext) ' from element ' int2str(ielem) ' written.'])
     1692                        [lat(end+1),long(end+1)]=mapxy((md.x(elemp(ielem,snext))...
     1693                                                       +md.x(elemp(ielem,mod(snext,3)+1)))/2.,...
     1694                                                       (md.y(elemp(ielem,snext))...
     1695                                                       +md.y(elemp(ielem,mod(snext,3)+1)))/2.,'s');
     1696                        fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1697                        elast=ielem;
     1698                        nlast=0;
     1699                        slast=snext;
     1700%  find adjacent element to opposite side
     1701                        ielem=edgeadjp(elast,slast);
     1702%  if opposite side is unshared, find it in edge perimeter list
     1703                        if ~ielem
     1704                            jlast=find(elemper(j:end)==elast)+j-1;
     1705                            j=0;
     1706                            for l=1:length(jlast)
     1707                                if ((elemp(elast,slast)          == edgeper(jlast(l),1)) && ...
     1708                                    (elemp(elast,mod(slast,3)+1) == edgeper(jlast(l),2))) || ...
     1709                                   ((elemp(elast,slast)          == edgeper(jlast(l),2)) && ...
     1710                                    (elemp(elast,mod(slast,3)+1) == edgeper(jlast(l),1)))
     1711                                    j=jlast(l);
     1712                                    break
     1713                                end
     1714                            end
     1715                            if ~j
     1716                                j=iloop(i+1)-1;
     1717                            end
     1718%  write out half-edge from midpoint of unshared side to node
     1719                            if (epartp(elast,slast) == k)
     1720                                nnext=slast;
     1721                            else
     1722                                nnext=mod(slast,3)+1;
     1723                            end
     1724                            disp(['segment j=' int2str(j) ' unshared half edge on side ' int2str(slast) ' to node ' int2str(elemp(elast,nnext)) ' (node ' int2str(nnext) ') from element ' int2str(elast) ' written.'])
     1725                            [lat(end+1),long(end+1)]=mapxy(md.x(elemp(elast,nnext)),...
     1726                                                           md.y(elemp(elast,nnext)),'s');
     1727                            fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(end),lat(end),alt);
     1728                            break
     1729%  if not unshared, advance perimeter list and watch for end
     1730                        else
     1731                            if (elast == elemper(j))
     1732                                if (j+1 < iloop(i+1)) && ...
     1733                                   ~isempty(find(elemper(j+1:end)~=elast,1))
     1734                                    j=j+find(elemper(j+1:end)~=elast,1);
     1735                                else
     1736                                    break
     1737                                end
     1738                            end
     1739                        end
     1740                    end
     1741                    j=j+1;
     1742                end
     1743            end
     1744%            fprintf(fid,'                %0.16g,%0.16g,%0.16g\n',long(iloop(1)),lat(iloop(1)),alt);
     1745
     1746            fprintf(fid,'              </coordinates>\n');
     1747            fprintf(fid,'            </LinearRing>\n');
     1748            fprintf(fid,'          </outerBoundaryIs>\n');
     1749            fprintf(fid,'        </Polygon>\n');
     1750            fprintf(fid,'      </Placemark>\n');
     1751        end
     1752    end
     1753    fprintf(fid,'    </Folder>\n');
     1754end
     1755
     1756end
     1757
Note: See TracChangeset for help on using the changeset viewer.