53 #include <boost/tokenizer.hpp>
54 #include <boost/utility.hpp>
61 #include "OgIAttribute.h"
62 #include "OgIDataset.h"
64 #include "OgOAttribute.h"
65 #include "OgODataset.h"
90 const std::string k_mappingStr(
"mapping");
91 const std::string k_partitionName(
"partition");
92 const std::string k_versionAttrName(
"version_number");
93 const std::string k_classNameAttrName(
"class_name");
94 const std::string k_mappingTypeAttrName(
"mapping_type");
102 int k_minFileVersion[2] = { 0, 0 };
106 std::vector<std::string> makeUnique(std::vector<std::string> vec)
108 std::vector<string> ret;
109 std::sort(vec.begin(), vec.end());
110 std::vector<std::string>::iterator newEnd =
111 std::unique(vec.begin(), vec.end());
112 ret.resize(std::distance(vec.begin(), newEnd));
113 std::copy(vec.begin(), newEnd, ret.begin());
121 class print : std::unary_function<T, void>
127 void operator()(
const T& x)
const
129 for (
int i = 0; i < indent; i++)
131 std::cout << x << std::endl;
143 void checkFile(
const std::string &filename)
147 throw NoSuchFileException(filename);
153 bool isSupportedFileVersion(
const int fileVersion[3],
154 const int minVersion[2])
156 stringstream currentVersionStr;
157 currentVersionStr << k_currentFileVersion[0] <<
"."
158 << k_currentFileVersion[1] <<
"."
159 << k_currentFileVersion[2];
160 stringstream fileVersionStr;
161 fileVersionStr << fileVersion[0] <<
"."
162 << fileVersion[1] <<
"."
164 stringstream minVersionStr;
165 minVersionStr << minVersion[0] <<
"."
168 if (fileVersion[0] > k_currentFileVersion[0] ||
169 (fileVersion[0] == k_currentFileVersion[0] &&
170 fileVersion[1] > k_currentFileVersion[1])) {
172 " is higher than the current version " +
173 currentVersionStr.str());
177 if (fileVersion[0] < minVersion[0] ||
178 (fileVersion[0] == minVersion[0] &&
179 fileVersion[1] < minVersion[1])) {
181 " is lower than the minimum supported version " +
182 minVersionStr.str());
195 mappingGroup.findAttribute<
string>(k_mappingTypeAttrName);
196 if (!mappingAttr.isValid()) {
201 const std::string className = mappingAttr.value();
238 return io->write(layerGroup, field);
247 template <
class Data_T>
249 readField(
const std::string &className,
const OgIGroup &layerGroup,
250 const std::string &filename,
const std::string &layerPath)
263 OgDataType typeEnum = OgawaTypeTraits<Data_T>::typeEnum();
264 FieldBase::Ptr field = io->read(layerGroup, filename, layerPath, typeEnum);
272 FieldPtr result = field_dynamic_cast<Field<Data_T> >(field);
283 bool readMeta(
const OgIGroup &group,
FieldMetadata &metadata)
286 std::vector<std::string> attrs = group.attributeNames();
288 for (
size_t i = 0, end = attrs.size(); i < end; ++i) {
292 if (attr.isValid()) {
299 if (attr.isValid()) {
306 if (attr.isValid()) {
313 if (attr.isValid()) {
320 if (attr.isValid()) {
343 std::string Partition::className()
const
345 return k_partitionName;
351 Partition::addLayer(
const Layer &layer)
353 m_layers.push_back(layer);
359 Partition::layer(
const std::string &name)
const
361 for (LayerList::const_iterator i = m_layers.begin();
362 i != m_layers.end(); ++i) {
363 if (i->name == name) {
373 Partition::getLayerNames(std::vector<std::string> &names)
const
377 for (LayerList::const_iterator i = m_layers.begin();
378 i != m_layers.end(); ++i) {
379 names.push_back(i->name);
385 OgOGroup& Partition::group()
const
392 void Partition::setGroup(boost::shared_ptr<OgOGroup> ptr)
423 const std::string & ,
427 for (PartitionList::const_iterator i =
m_partitions.begin();
430 if ((**i).mapping->isIdentical(field->mapping())) {
455 if ((**i).name == partitionName)
467 for (PartitionList::const_iterator i =
m_partitions.begin();
469 if ((**i).name == partitionName)
481 size_t pos = partitionName.rfind(
".");
482 if (pos == partitionName.npos) {
483 return partitionName;
485 return partitionName.substr(0, pos);
501 vector<string> tempNames;
503 for (PartitionList::const_iterator i =
m_partitions.begin();
508 names = makeUnique(tempNames);
515 const string &partitionName)
const
518 m_hdf5Base->getScalarLayerNames(names, partitionName);
530 part->getLayerNames(names);
533 names = makeUnique(names);
540 const string &partitionName)
const
543 m_hdf5Base->getVectorLayerNames(names, partitionName);
555 part->getLayerNames(names);
558 names = makeUnique(names);
568 for (PartitionList::const_iterator i =
m_partitions.begin();
570 names.push_back((**i).name);
578 const string &intPartitionName)
const
591 part->getLayerNames(names);
598 const string &intPartitionName)
const
611 part->getLayerNames(names);
648 for (PartitionList::const_iterator i =
m_partitions.begin();
650 string name = (**i).name;
651 size_t pos = name.rfind(
".");
652 if (pos != name.npos) {
653 if (name.substr(0, pos) == partitionName) {
668 return partitionName +
"." + boost::lexical_cast<std::string>(i);
681 GroupMembershipMap::const_iterator i = groupMembers.begin();
682 GroupMembershipMap::const_iterator end = groupMembers.end();
684 for (; i != end; ++i) {
685 GroupMembershipMap::iterator foundGroupIter =
729 m_archive.reset(
new Alembic::Ogawa::IArchive(filename));
735 if (
m_hdf5->open(filename)) {
739 throw NoSuchFileException(filename);
750 if (!version.isValid()) {
751 throw OgIAttributeException(
"Missing version attribute.");
753 int fileVersion[3] = { version.value()[0],
755 version.value()[2] };
756 if (!isSupportedFileVersion(fileVersion, k_minFileVersion)) {
757 stringstream versionStr;
758 versionStr << fileVersion[0] <<
"."
759 << fileVersion[1] <<
"."
761 throw UnsupportedVersionException(versionStr.str());
764 catch (OgIAttributeException &e) {
771 const OgIGroup metadataGroup =
m_root->findGroup(
"field3d_global_metadata");
772 if (metadataGroup.isValid()) {
778 "Unknown error when reading file metadata ");
787 catch (MissingGroupException &e) {
789 throw BadFileHierarchyException(filename);
791 catch (ReadMappingException &e) {
794 throw BadFileHierarchyException(filename);
799 throw BadFileHierarchyException(filename);
803 "Unknown error when reading file hierarchy. ");
804 throw BadFileHierarchyException(filename);
807 catch (NoSuchFileException &e) {
809 +
string(e.what()) );
812 catch (MissingAttributeException &e) {
814 "In file: " + filename +
" - "
815 +
string(e.what()) );
818 catch (UnsupportedVersionException &e) {
820 "In file: " + filename +
" - File version can not be read: "
824 catch (BadFileHierarchyException &) {
826 "In file: " + filename +
" - Bad file hierarchy. ");
829 catch (runtime_error &e) {
833 if (
m_hdf5->open(filename)) {
838 "In file: " + filename +
": " +
string(e.what()));
844 "In file: " + filename +
" Unknown exception ");
860 std::vector<std::string> groups =
m_root->groupNames();
864 for (std::vector<std::string>::const_iterator i = groups.begin(),
865 end = groups.end(); i != end; ++i) {
867 const std::string &name = *i;
869 if (name ==
"field3d_global_metadata") {
883 const std::string &name = (**i).name;
885 const OgIGroup partitionGroup =
m_root->findGroup(name);
886 if (!partitionGroup.isValid()) {
890 const OgIGroup mappingGroup = partitionGroup.findGroup(k_mappingStr);
891 if (!mappingGroup.isValid()) {
899 throw ReadMappingException((**i).name);
903 (**i).mapping = mapping;
908 for (PartitionList::const_iterator i =
m_partitions.begin();
911 const std::string &partitionName = (**i).name;
913 const OgIGroup partitionGroup =
m_root->findGroup(partitionName);
914 if (!partitionGroup.isValid()) {
919 groups = partitionGroup.groupNames();
920 for (std::vector<std::string>::const_iterator l = groups.begin(),
921 lEnd = groups.end(); l != lEnd; ++l) {
923 const std::string layerName = *l;
925 if (layerName == k_mappingStr) {
931 layer.
parent = partitionName;
933 partition(partitionName)->addLayer(layer);
945 return readMeta(metadataGroup, field->metadata());
952 return readMeta(metadataGroup,
metadata());
993 m_archive.reset(
new Alembic::Ogawa::OArchive(filename));
1006 k_currentFileVersion);
1017 const std::string className = mapping->className();
1021 OgOGroup mappingGroup(partitionGroup, k_mappingStr);
1033 return io->write(mappingGroup, mapping);
1036 catch (OgOGroupException &e) {
1038 throw WriteMappingException(k_mappingStr);
1049 FieldMetadata::StrMetadata::const_iterator i =
1050 field->metadata().strMetadata().begin();
1051 FieldMetadata::StrMetadata::const_iterator end =
1052 field->metadata().strMetadata().end();
1053 for (; i != end; ++i) {
1057 catch (OgOAttributeException &e) {
1066 FieldMetadata::IntMetadata::const_iterator i =
1067 field->metadata().intMetadata().begin();
1068 FieldMetadata::IntMetadata::const_iterator end =
1069 field->metadata().intMetadata().end();
1070 for (; i != end; ++i) {
1074 catch (OgOAttributeException &e) {
1083 FieldMetadata::FloatMetadata::const_iterator i =
1084 field->metadata().floatMetadata().begin();
1085 FieldMetadata::FloatMetadata::const_iterator end =
1086 field->metadata().floatMetadata().end();
1087 for (; i != end; ++i) {
1091 catch (OgOAttributeException &e) {
1100 FieldMetadata::VecIntMetadata::const_iterator i =
1101 field->metadata().vecIntMetadata().begin();
1102 FieldMetadata::VecIntMetadata::const_iterator end =
1103 field->metadata().vecIntMetadata().end();
1104 for (; i != end; ++i) {
1108 catch (OgOAttributeException &e) {
1117 FieldMetadata::VecFloatMetadata::const_iterator i =
1118 field->metadata().vecFloatMetadata().begin();
1119 FieldMetadata::VecFloatMetadata::const_iterator end =
1120 field->metadata().vecFloatMetadata().end();
1121 for (; i != end; ++i) {
1125 catch (OgOAttributeException &e) {
1143 FieldMetadata::StrMetadata::const_iterator i =
1145 FieldMetadata::StrMetadata::const_iterator end =
1147 for (; i != end; ++i) {
1151 catch (OgOAttributeException &e) {
1160 FieldMetadata::IntMetadata::const_iterator i =
1162 FieldMetadata::IntMetadata::const_iterator end =
1164 for (; i != end; ++i) {
1168 catch (OgOAttributeException &e) {
1177 FieldMetadata::FloatMetadata::const_iterator i =
1179 FieldMetadata::FloatMetadata::const_iterator end =
1181 for (; i != end; ++i) {
1185 catch (OgOAttributeException &e) {
1194 FieldMetadata::VecIntMetadata::const_iterator i =
1196 FieldMetadata::VecIntMetadata::const_iterator end =
1198 for (; i != end; ++i) {
1202 catch (OgOAttributeException &e) {
1211 FieldMetadata::VecFloatMetadata::const_iterator i =
1213 FieldMetadata::VecFloatMetadata::const_iterator end =
1215 for (; i != end; ++i) {
1219 catch (OgOAttributeException &e) {
1237 return m_hdf5->writeGlobalMetadata();
1240 OgOGroup ogMetadata(*
m_root,
"field3d_global_metadata");
1255 return m_hdf5->writeGroupMembership();
1262 using namespace std;
1271 "Error creating field3d_group_membership group.");
1275 if (!
writeAttribute(group,
"is_field3d_group_membership",
"1")) {
1277 "Failed to write field3d_group_membership attribute.");
1281 std::map<std::string, std::string>::const_iterator iter =
1283 std::map<std::string, std::string>::const_iterator iEnd =
1286 for (; iter != iEnd; ++iter) {
1289 "Failed to write groupMembership string: "+ iter->first);
1323 for (PartitionList::const_iterator i =
m_partitions.begin();
1325 cout <<
"Name: " << (**i).name << endl;
1327 cout <<
" Mapping: " << (**i).mapping->className() << endl;
1329 cout <<
" Mapping: NULL" << endl;
1330 cout <<
" Layers: " << endl;
1331 vector<string> names;
1332 (**i).getLayerNames(names);
1333 for_each(names.begin(), names.end(), print<string>(4));
1344 struct __stat64 statbuf;
1345 return (_stat64(filename.c_str(), &statbuf) != -1);
1347 struct stat statbuf;
1348 return (stat(filename.c_str(), &statbuf) != -1);
1356 const std::string & ,
1359 using namespace Exc;
1362 newPart->name = partitionName;
1364 boost::shared_ptr<OgOGroup> ogPartition(
new OgOGroup(*
m_root, newPart->name));
1365 newPart->setGroup(ogPartition);
1376 "writeMapping returned false for an unknown reason ");
1380 catch (WriteMappingException &e) {
1387 "Unknown error when writing mapping for partition: "
1395 part->mapping = field->mapping();
1408 template <
class Data_T>
1410 const std::string &layerName,
1418 "Called writeLayer with null pointer. Ignoring...");
1425 "Attempting to write layer without opening file first.");
1430 string partitionName =
intPartitionName(userPartitionName, layerName, field);
1446 "Couldn't add layer \"" + layerName +
"\" to partition \""
1447 + partitionName +
"\" because the layer's mapping is null.");
1452 if (part->layer(layerName)) {
1465 if (!part->mapping) {
1472 if (!field->
mapping()->isIdentical(part->mapping)) {
1474 +
"\" to partition \"" + partitionName
1475 +
"\" because mapping doesn't match");
1481 OgOGroup &ogPartition = part->group();
1486 layer.
name = layerName;
1487 layer.
parent = partitionName;
1491 OgOGroup ogLayer(ogPartition, layerName);
1497 OgOGroup ogMetadata(ogLayer,
"metadata");
1507 part->addLayer(layer);
1514 template <
class Data_T>
1517 const std::string &layerName)
const
1532 const File::Layer *layer = part->layer(layerName);
1540 if (!partitionGroup.isValid()) {
1547 const OgIGroup layerGroup = partitionGroup.findGroup(layerName);
1548 if (!layerGroup.isValid()) {
1555 string layerPath = layer->
parent +
"/" + layer->
name;
1558 className = layerGroup.findAttribute<
string>(
"class_name").value();
1560 catch (OgIAttributeException &e) {
1569 FieldPtr cachedField = cache.
getCachedField(m_filename, layerPath);
1578 field = readField<Data_T>(className, layerGroup, m_filename, layerPath);
1586 const OgIGroup metadataGroup = layerGroup.findGroup(
"metadata");
1587 if (metadataGroup.isValid()) {
1588 readMetadata(metadataGroup, field);
1598 cache.
cacheField(field, m_filename, layerPath);
1606 template <
class Data_T>
1617 std::vector<std::string> parts;
1620 for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
1621 vector<std::string> layers;
1623 for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
1625 if ((name.length() == 0) || (*l == name)) {
1626 FieldPtr mf = readLayer<Data_T>(*p, *l);
1639 template <
class Data_T>
1642 const std::string &layerName)
const
1644 using namespace std;
1651 if ((layerName.length() == 0) || (partitionName.length() == 0))
1654 std::vector<std::string> parts;
1657 for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
1658 std::vector<std::string> layers;
1661 for (vector<string>::iterator l = layers.begin();
1662 l != layers.end(); ++l) {
1664 if (*l == layerName) {
1665 FieldPtr mf = readLayer<Data_T>(*p, *l);
1678 template <
class Data_T>
1681 const std::string &name,
1682 const std::string &attribute,
1685 using namespace boost;
1686 using namespace std;
1690 const std::string extentsMinStr(
"extents_min");
1691 const std::string extentsMaxStr(
"extents_max");
1692 const std::string dataWindowMinStr(
"data_window_min");
1693 const std::string dataWindowMaxStr(
"data_window_max");
1695 Box3i extents, dataW;
1700 location.findAttribute<
veci32_t>(extentsMinStr);
1702 location.findAttribute<
veci32_t>(extentsMaxStr);
1703 if (!extMinAttr.isValid()) {
1704 throw MissingAttributeException(
"Couldn't find attribute " +
1707 if (!extMaxAttr.isValid()) {
1708 throw MissingAttributeException(
"Couldn't find attribute " +
1712 extents.min = extMinAttr.value();
1713 extents.max = extMaxAttr.value();
1718 location.findAttribute<
veci32_t>(dataWindowMinStr);
1720 location.findAttribute<
veci32_t>(dataWindowMaxStr);
1721 if (!dwMinAttr.isValid()) {
1722 throw MissingAttributeException(
"Couldn't find attribute " +
1725 if (!dwMaxAttr.isValid()) {
1726 throw MissingAttributeException(
"Couldn't find attribute " +
1730 dataW.min = dwMinAttr.value();
1731 dataW.max = dwMaxAttr.value();
1735 field->
setSize(extents, dataW);
1738 OgIGroup metadataGroup = location.findGroup(
"metadata");
1739 if (metadataGroup.isValid()) {
1740 readMetadata(metadataGroup, field);
1753 template <
class Data_T>
1756 const std::string &layerName,
1757 bool isVectorLayer)
const
1759 using namespace boost;
1760 using namespace std;
1764 return m_hdf5->readProxyLayer<Data_T>(partitionName, layerName,
1771 if ((layerName.length() == 0) || (partitionName.length() == 0))
1774 std::vector<std::string> parts, layers;
1777 bool foundPartition =
false;
1779 for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
1781 foundPartition =
true;
1782 if (isVectorLayer) {
1787 for (vector<string>::iterator l = layers.begin();
1788 l != layers.end(); ++l) {
1789 if (*l == layerName) {
1798 if (isVectorLayer) {
1799 layer = part->layer(layerName);
1801 layer = part->layer(layerName);
1808 string layerPath = layer->
parent +
"/" + layer->
name;
1810 if (!parent.isValid()) {
1812 + layerPath +
" in .f3d file ");
1815 OgIGroup layerGroup = parent.findGroup(layer->
name);
1816 if (!layerGroup.isValid()) {
1818 + layerPath +
" in .f3d file ");
1824 readProxyLayer<Data_T>(layerGroup, partitionName, layerName,
1829 OgIGroup mipGroup = layerGroup.findGroup(
"mip_levels");
1830 if (mipGroup.isValid()) {
1832 mipGroup.findAttribute<uint32_t>(
"levels");
1833 if (levelsAttr.isValid()) {
1834 numLevels = levelsAttr.value();
1840 output.push_back(field);
1846 if (!foundPartition) {
1856 template <
class Data_T>
1860 using namespace std;
1863 typedef std::vector<FieldPtr> FieldList;
1867 std::vector<std::string> parts;
1870 for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
1871 std::vector<std::string> layers;
1873 for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
1875 if ((name.length() == 0) || (*l == name)) {
1876 FieldList f = readProxyLayer<Data_T>(*p, *l,
false);
1877 for (
typename FieldList::iterator i = f.begin(); i != f.end(); ++i) {
1891 template <
class Data_T>
1895 using namespace std;
1898 typedef std::vector<FieldPtr> FieldList;
1902 std::vector<std::string> parts;
1905 for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
1906 std::vector<std::string> layers;
1908 for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
1910 if ((name.length() == 0) || (*l == name)) {
1911 FieldList f = readProxyLayer<Data_T>(*p, *l,
true);
1912 for (
typename FieldList::iterator i = f.begin(); i != f.end(); ++i) {
1928 #define FIELD3D_INSTANTIATION_WRITELAYER(type) \
1930 FIELD3D_API bool Field3DOutputFile::writeLayer<type> \
1931 (const std::string &, const std::string &, Field<type>::Ptr ); \
1944 #define FIELD3D_INSTANTIATION_READLAYER(type) \
1946 FIELD3D_API Field<type>::Ptr \
1947 Field3DInputFile::readLayer<type> \
1948 (const std::string &, const std::string &) const; \
1950 FIELD3D_INSTANTIATION_READLAYER(
float16_t);
1951 FIELD3D_INSTANTIATION_READLAYER(
float32_t);
1952 FIELD3D_INSTANTIATION_READLAYER(
float64_t);
1953 FIELD3D_INSTANTIATION_READLAYER(
vec16_t);
1954 FIELD3D_INSTANTIATION_READLAYER(
vec32_t);
1955 FIELD3D_INSTANTIATION_READLAYER(
vec64_t);
1961 #define FIELD3D_INSTANTIATION_READLAYERS1(type) \
1963 FIELD3D_API Field<type>::Vec \
1964 Field3DInputFile::readLayers<type>(const std::string &name) const; \
1975 #define FIELD3D_INSTANTIATION_READLAYERS2(type) \
1977 FIELD3D_API Field<type>::Vec \
1978 Field3DInputFile::readLayers<type>(const std::string &partitionName, \
1979 const std::string &layerName) const; \
1990 #define FIELD3D_INSTANTIATION_READPROXYLAYER(type) \
1992 FIELD3D_API EmptyField<type>::Vec \
1993 Field3DInputFile::readProxyLayer<type>(const std::string &partitionName, \
1994 const std::string &layerName, \
1995 bool isVectorLayer) const \
2006 #define FIELD3D_INSTANTIATION_READPROXYSCALARLAYER(type) \
2008 FIELD3D_API EmptyField<type>::Vec \
2009 Field3DInputFile::readProxyScalarLayers<type> \
2010 (const std::string &name) const \
2021 #define FIELD3D_INSTANTIATION_READPROXYVECTORLAYER(type) \
2023 FIELD3D_API EmptyField<type>::Vec \
2024 Field3DInputFile::readProxyVectorLayers<type> \
2025 (const std::string &name) const \