XdmfItemFactory.cpp 8.35 KB
Newer Older
Kenneth Leiter's avatar
Kenneth Leiter committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
/*****************************************************************************/
/*                                    XDMF                                   */
/*                       eXtensible Data Model and Format                    */
/*                                                                           */
/*  Id : XdmfItemFactory.cpp                                                 */
/*                                                                           */
/*  Author:                                                                  */
/*     Kenneth Leiter                                                        */
/*     kenneth.leiter@arl.army.mil                                           */
/*     US Army Research Laboratory                                           */
/*     Aberdeen Proving Ground, MD                                           */
/*                                                                           */
/*     Copyright @ 2011 US Army Research Laboratory                          */
/*     All Rights Reserved                                                   */
/*     See Copyright.txt for details                                         */
/*                                                                           */
/*     This software is distributed WITHOUT ANY WARRANTY; without            */
/*     even the implied warranty of MERCHANTABILITY or FITNESS               */
/*     FOR A PARTICULAR PURPOSE.  See the above copyright notice             */
/*     for more information.                                                 */
/*                                                                           */
/*****************************************************************************/

24
#include <cctype>
25
#include <boost/tokenizer.hpp>
26
#include "XdmfAttribute.hpp"
27
#include "XdmfCurvilinearGrid.hpp"
28 29
#include "XdmfDomain.hpp"
#include "XdmfGeometry.hpp"
30
#include "XdmfGeometryType.hpp"
31
#include "XdmfGridCollection.hpp"
32
#include "XdmfInformation.hpp"
33
#include "XdmfItemFactory.hpp"
34
#include "XdmfMap.hpp"
35 36
#include "XdmfRectilinearGrid.hpp"
#include "XdmfRegularGrid.hpp"
37
#include "XdmfSet.hpp"
38
#include "XdmfTime.hpp"
39
#include "XdmfTopology.hpp"
40
#include "XdmfUnstructuredGrid.hpp"
41

42
shared_ptr<XdmfItemFactory>
43
XdmfItemFactory::New()
44
{
45
  shared_ptr<XdmfItemFactory> p(new XdmfItemFactory());
46
  return p;
47 48
}

49 50 51 52 53 54 55 56
XdmfItemFactory::XdmfItemFactory()
{
}

XdmfItemFactory::~XdmfItemFactory()
{
}

57
shared_ptr<XdmfItem>
58 59
XdmfItemFactory::createItem(const std::string & itemTag,
                            const std::map<std::string, std::string> & itemProperties,
60
                            const std::vector<shared_ptr<XdmfItem> > & childItems) const
61
{
62
  shared_ptr<XdmfItem> newItem =
63
    XdmfCoreItemFactory::createItem(itemTag, itemProperties, childItems);
64

65 66 67
  if(newItem) {
    return newItem;
  }
68

69 70 71 72 73 74 75 76 77 78 79 80
  if(itemTag.compare(XdmfAttribute::ItemTag) == 0) {
    return XdmfAttribute::New();
  }
  else if(itemTag.compare(XdmfDomain::ItemTag) == 0) {
    return XdmfDomain::New();
  }
  else if(itemTag.compare(XdmfGeometry::ItemTag) == 0) {
    std::map<std::string, std::string>::const_iterator type =
      itemProperties.find("Type");
    if(type == itemProperties.end()) {
      type = itemProperties.find("GeometryType");
    }
81

82
    if(type != itemProperties.end()) {
83
      const std::string & typeVal = type->second;
84 85
      if(typeVal.compare("ORIGIN_DXDY") == 0 ||
         typeVal.compare("ORIGIN_DXDYDZ") == 0) {
86 87
        shared_ptr<XdmfArray> origin = shared_ptr<XdmfArray>();
        shared_ptr<XdmfArray> brickSize = shared_ptr<XdmfArray>();
88
        for(std::vector<shared_ptr<XdmfItem> >::const_iterator iter =
89 90 91
              childItems.begin();
            iter != childItems.end();
            ++iter) {
92 93
          if(shared_ptr<XdmfArray> array = 
             shared_dynamic_cast<XdmfArray>(*iter)) {
94 95 96 97 98 99 100 101 102 103 104
            if(!origin) {
              origin = array;
            }
            else if(!brickSize) {
              brickSize = array;
              break;
            }
          }
        }
        if(origin && brickSize) {
          return XdmfRegularGrid::New(brickSize,
105
                                      shared_ptr<XdmfArray>(),
106 107
                                      origin);
        }
108
        return shared_ptr<XdmfItem>();
109 110 111
      }
      else if(typeVal.compare("VXVY") == 0 ||
              typeVal.compare("VXVYVZ") == 0) {
112 113
        std::vector<shared_ptr<XdmfArray> > coordinateValues;
        for(std::vector<shared_ptr<XdmfItem> >::const_iterator iter =
114 115 116
              childItems.begin();
            iter != childItems.end();
            ++iter) {
117 118
          if(shared_ptr<XdmfArray> array = 
             shared_dynamic_cast<XdmfArray>(*iter)) {
119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137
            coordinateValues.push_back(array);
          }
        }
        return XdmfRectilinearGrid::New(coordinateValues);
      }
    }
    return XdmfGeometry::New();
  }
  else if(itemTag.compare(XdmfGrid::ItemTag) == 0) {
    // For backwards compatibility with the old format, this tag can
    // correspond to multiple XdmfItems.
    std::map<std::string, std::string>::const_iterator gridType =
      itemProperties.find("GridType");
    if(gridType != itemProperties.end() &&
       gridType->second.compare("Collection") == 0) {
      return XdmfGridCollection::New();
    }
    else {
      // Find out what kind of grid we have
138
      for(std::vector<shared_ptr<XdmfItem> >::const_iterator iter =
139 140 141
            childItems.begin();
          iter != childItems.end();
          ++iter) {
142 143
        if(shared_ptr<XdmfCurvilinearGrid> curvilinear =
           shared_dynamic_cast<XdmfCurvilinearGrid>(*iter)) {
144 145
          return XdmfCurvilinearGrid::New(0, 0);
        }
146 147
        else if(shared_ptr<XdmfRegularGrid> regularGrid =
                shared_dynamic_cast<XdmfRegularGrid>(*iter)) {
148 149
          return XdmfRegularGrid::New(0, 0, 0, 0, 0, 0);
        }
150 151 152
        else if(shared_ptr<XdmfRectilinearGrid> rectilinearGrid =
                shared_dynamic_cast<XdmfRectilinearGrid>(*iter)) {
          std::vector<shared_ptr<XdmfArray> > coordinateValues;
153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176
          return XdmfRectilinearGrid::New(coordinateValues);
        }
      }
      return XdmfUnstructuredGrid::New();
    }
  }
  else if(itemTag.compare(XdmfInformation::ItemTag) == 0) {
    return XdmfInformation::New();
  }
  else if(itemTag.compare(XdmfMap::ItemTag) == 0) {
    return XdmfMap::New();
  }
  else if(itemTag.compare(XdmfSet::ItemTag) == 0) {
    return XdmfSet::New();
  }
  else if(itemTag.compare(XdmfTime::ItemTag) == 0) {
    return XdmfTime::New();
  }
  else if(itemTag.compare(XdmfTopology::ItemTag) == 0) {
    std::map<std::string, std::string>::const_iterator type =
      itemProperties.find("Type");
    if(type == itemProperties.end()) {
      type = itemProperties.find("TopologyType");
    }
177

178 179 180 181 182 183 184 185 186 187
    if(type != itemProperties.end()) {
      std::string typeVal = type->second;
      std::transform(typeVal.begin(),
                     typeVal.end(),
                     typeVal.begin(),
                     (int(*)(int))toupper);
      if(typeVal.compare("2DCORECTMESH") == 0 ||
         typeVal.compare("3DCORECTMESH") == 0 ||
         typeVal.compare("2DSMESH") == 0 ||
         typeVal.compare("3DSMESH") == 0) {
188
        shared_ptr<XdmfArray> dimensionsArray = XdmfArray::New();
189 190 191 192 193 194 195 196 197 198 199 200 201 202
        std::string dimensionsString = "";
        std::map<std::string, std::string>::const_iterator dimensions =
          itemProperties.find("Dimensions");
        if(dimensions != itemProperties.end()) {
          dimensionsString = dimensions->second;
        }
        boost::tokenizer<> tokens(dimensionsString);
        for(boost::tokenizer<>::const_iterator iter = tokens.begin();
            iter != tokens.end();
            ++iter) {
          dimensionsArray->pushBack<unsigned int>(atoi((*iter).c_str()));
        }
        if(typeVal.compare("2DCORECTMESH") == 0 ||
           typeVal.compare("3DCORECTMESH") == 0) {
203
          return XdmfRegularGrid::New(shared_ptr<XdmfArray>(),
204
                                      dimensionsArray,
205
                                      shared_ptr<XdmfArray>());
206 207 208 209 210 211 212
        }
        else {
          return XdmfCurvilinearGrid::New(dimensionsArray);
        }
      }
      else if(typeVal.compare("2DRECTMESH") == 0 ||
              typeVal.compare("3DRECTMESH") == 0) {
213
        std::vector<shared_ptr<XdmfArray> > coordinateValues;
214 215
        return XdmfRectilinearGrid::New(coordinateValues);
      }
216

217 218 219
    }
    return XdmfTopology::New();
  }
220
  return shared_ptr<XdmfItem>();
221
}