Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #include "mitkPropertyListSerializer.h"
00020 #include "mitkBasePropertySerializer.h"
00021
00022 #include <tinyxml.h>
00023
00024 #include "mitkStandardFileLocations.h"
00025 #include <itksys/SystemTools.hxx>
00026
00027 mitk::PropertyListSerializer::PropertyListSerializer()
00028 : m_FilenameHint("unnamed")
00029 , m_WorkingDirectory("")
00030 {
00031 }
00032
00033 mitk::PropertyListSerializer::~PropertyListSerializer()
00034 {
00035 }
00036
00037 std::string mitk::PropertyListSerializer::Serialize()
00038 {
00039 m_FailedProperties = PropertyList::New();
00040
00041 if ( m_PropertyList.IsNull() && m_PropertyList->IsEmpty() )
00042 {
00043 MITK_ERROR << "Not serializing NULL or empty PropertyList";
00044 return "";
00045 }
00046
00047
00048 static unsigned long count = 1;
00049 unsigned long n = count++;
00050 std::ostringstream name;
00051 for (int i = 0; i < 6; ++i)
00052 {
00053 name << char('a' + (n % 26));
00054 n /= 26;
00055 }
00056 std::string filename;
00057 filename.append(name.str());
00058
00059 std::string fullname(m_WorkingDirectory);
00060 fullname += "/";
00061 fullname += filename;
00062 fullname = itksys::SystemTools::ConvertToOutputPath(fullname.c_str());
00063
00064 TiXmlDocument document;
00065 TiXmlDeclaration* decl = new TiXmlDeclaration( "1.0", "", "" );
00066 document.LinkEndChild( decl );
00067
00068 TiXmlElement* version = new TiXmlElement("Version");
00069 version->SetAttribute("Writer", __FILE__ );
00070 version->SetAttribute("Revision", "$Revision: 17055 $" );
00071 version->SetAttribute("FileVersion", 1 );
00072 document.LinkEndChild(version);
00073
00074
00075 const PropertyList::PropertyMap* propmap = m_PropertyList->GetMap();
00076 for ( PropertyList::PropertyMap::const_iterator iter = propmap->begin();
00077 iter != propmap->end();
00078 ++iter )
00079 {
00080 std::string key = iter->first;
00081 const BaseProperty* property = iter->second.first;
00082 TiXmlElement* element = SerializeOneProperty( key, property );
00083 if (element)
00084 {
00085 document.LinkEndChild( element );
00086
00087 }
00088 else
00089 {
00090 m_FailedProperties->ReplaceProperty( key, const_cast<BaseProperty*>(property) );
00091 }
00092 }
00093
00094
00095 if ( !document.SaveFile( fullname ) )
00096 {
00097 MITK_ERROR << "Could not write PropertyList to " << fullname << "\nTinyXML reports '" << document.ErrorDesc() << "'";
00098 return "";
00099 }
00100
00101 return filename;
00102 }
00103
00104 TiXmlElement* mitk::PropertyListSerializer::SerializeOneProperty( const std::string& key, const BaseProperty* property )
00105 {
00106 TiXmlElement* keyelement = new TiXmlElement("property");
00107 keyelement->SetAttribute("key", key);
00108 keyelement->SetAttribute("type", property->GetNameOfClass());
00109
00110
00111 std::string serializername(property->GetNameOfClass());
00112 serializername += "Serializer";
00113
00114 std::list<itk::LightObject::Pointer> allSerializers = itk::ObjectFactoryBase::CreateAllInstance(serializername.c_str());
00115 if (allSerializers.size() < 1)
00116 {
00117 MITK_ERROR << "No serializer found for " << property->GetNameOfClass() << ". Skipping object";
00118 m_FailedProperties->ReplaceProperty( key, const_cast<BaseProperty*>(property) );
00119 }
00120 if (allSerializers.size() > 1)
00121 {
00122 MITK_WARN << "Multiple serializers found for " << property->GetNameOfClass() << "Using arbitrarily the first one.";
00123 }
00124
00125 for ( std::list<itk::LightObject::Pointer>::iterator iter = allSerializers.begin();
00126 iter != allSerializers.end();
00127 ++iter )
00128 {
00129 if (BasePropertySerializer* serializer = dynamic_cast<BasePropertySerializer*>( iter->GetPointer() ) )
00130 {
00131 serializer->SetProperty(property);
00132 try
00133 {
00134 TiXmlElement* valueelement = serializer->Serialize();
00135 if (valueelement)
00136 {
00137 keyelement->LinkEndChild( valueelement );
00138
00139 }
00140 else
00141 {
00142 m_FailedProperties->ReplaceProperty( key, const_cast<BaseProperty*>(property) );
00143 }
00144 }
00145 catch (std::exception& e)
00146 {
00147 MITK_ERROR << "Serializer " << serializer->GetNameOfClass() << " failed: " << e.what();
00148 m_FailedProperties->ReplaceProperty( key, const_cast<BaseProperty*>(property) );
00149
00150 }
00151 break;
00152 }
00153 }
00154 return keyelement;
00155 }
00156
00157 mitk::PropertyList* mitk::PropertyListSerializer::GetFailedProperties()
00158 {
00159 if (m_FailedProperties.IsNotNull() && !m_FailedProperties->IsEmpty())
00160 {
00161 return m_FailedProperties;
00162 }
00163 else
00164 {
00165 return NULL;
00166 }
00167 }