📄 objistrxml.cpp
字号:
CloseTag(type->GetName());}bool CObjectIStreamXml::WillHaveName(TTypeInfo elementType){ while ( elementType->GetName().empty() ) { if ( elementType->GetTypeFamily() != eTypeFamilyPointer ) return false; elementType = CTypeConverter<CPointerTypeInfo>::SafeCast( elementType)->GetPointedType(); } // found named type return true;}bool CObjectIStreamXml::HasAttlist(void){ if (InsideTag()) { return !IsEndOfTagChar( SkipWS() ); } return false;}bool CObjectIStreamXml::NextIsTag(void){ BeginData(); return SkipWSAndComments() == '<' && m_Input.PeekChar(1) != '/';}bool CObjectIStreamXml::NextTagIsClosing(void){ BeginData(); return SkipWSAndComments() == '<' && m_Input.PeekChar(1) == '/';}bool CObjectIStreamXml::ThisTagIsSelfClosed(void){ if (InsideOpeningTag()) { return EndOpeningTagSelfClosed(); } return false;}void CObjectIStreamXml::BeginContainer(const CContainerTypeInfo* containerType){ if (!x_IsStdXml()) { OpenTagIfNamed(containerType); }}void CObjectIStreamXml::EndContainer(void){ if (!x_IsStdXml()) { CloseTagIfNamed(TopFrame().GetTypeInfo()); }}bool CObjectIStreamXml::BeginContainerElement(TTypeInfo elementType){ if (!HasMoreElements(elementType)) { return false; } if ( !WillHaveName(elementType) ) { BeginArrayElement(elementType); } return true;}void CObjectIStreamXml::EndContainerElement(void){ if ( !WillHaveName(TopFrame().GetTypeInfo()) ) { EndArrayElement(); }}#ifdef VIRTUAL_MID_LEVEL_IOvoid CObjectIStreamXml::ReadContainer(const CContainerTypeInfo* containerType, TObjectPtr containerPtr){ if ( containerType->GetName().empty() ) { ReadContainerContents(containerType, containerPtr); } else { BEGIN_OBJECT_FRAME2(eFrameArray, containerType); OpenTag(containerType); ReadContainerContents(containerType, containerPtr); CloseTag(containerType); END_OBJECT_FRAME(); }}void CObjectIStreamXml::SkipContainer(const CContainerTypeInfo* containerType){ if ( containerType->GetName().empty() ) { SkipContainerContents(containerType); } else { BEGIN_OBJECT_FRAME2(eFrameArray, containerType); OpenTag(containerType); SkipContainerContents(containerType); CloseTag(containerType); END_OBJECT_FRAME(); }}bool CObjectIStreamXml::HasAnyContent(const CClassTypeInfoBase* classType){ const CItemsInfo& items = classType->GetItems(); if (items.Size() == 1) { const CItemInfo* itemInfo = items.GetItemInfo( items.FirstIndex()); if (itemInfo->GetId().HasAnyContent()) { return true; } } return false;}bool CObjectIStreamXml::HasMoreElements(TTypeInfo elementType){ if (ThisTagIsSelfClosed() || NextTagIsClosing()) { m_LastPrimitive.erase(); return false; } if (x_IsStdXml()) { CLightString tagName; TTypeInfo type = elementType; // this is to handle STL containers of primitive types if (GetRealTypeFamily(type) == eTypeFamilyPrimitive) { if (!m_RejectedTag.empty()) { m_LastPrimitive = m_RejectedTag; return true; } else { tagName = ReadName(BeginOpeningTag()); UndoClassMember(); bool res = (tagName == m_LastPrimitive); if (!res) { m_LastPrimitive.erase(); } return res; } } if (type->GetTypeFamily() == eTypeFamilyPointer) { const CPointerTypeInfo* ptr = dynamic_cast<const CPointerTypeInfo*>(type); if (ptr) { type = ptr->GetPointedType(); } } const CClassTypeInfoBase* classType = dynamic_cast<const CClassTypeInfoBase*>(type); if (classType) { if (m_RejectedTag.empty()) { tagName = ReadName(BeginOpeningTag()); } else { tagName = RejectedName(); } UndoClassMember(); if (classType->GetName().empty()) { return classType->GetItems().FindDeep(tagName) != kInvalidMember || HasAnyContent(classType); } return tagName == classType->GetName(); } } return true;}TMemberIndex CObjectIStreamXml::FindDeep(TTypeInfo type, const CLightString& name) const{ for (;;) { if (type->GetTypeFamily() == eTypeFamilyContainer) { const CContainerTypeInfo* cont = dynamic_cast<const CContainerTypeInfo*>(type); if (cont) { type = cont->GetElementType(); } } else if (type->GetTypeFamily() == eTypeFamilyPointer) { const CPointerTypeInfo* ptr = dynamic_cast<const CPointerTypeInfo*>(type); if (ptr) { type = ptr->GetPointedType(); } } else { break; } } const CClassTypeInfoBase* classType = dynamic_cast<const CClassTypeInfoBase*>(type); if (classType) { TMemberIndex i = classType->GetItems().FindDeep(name); if (i != kInvalidMember) { return i; } } return kInvalidMember;}void CObjectIStreamXml::BeginArrayElement(TTypeInfo elementType){ if (x_IsStdXml() && GetRealTypeFamily(elementType) != eTypeFamilyPrimitive) { TopFrame().SetNotag(); } else { OpenStackTag(0); }}void CObjectIStreamXml::EndArrayElement(void){ if (TopFrame().GetNotag()) { TopFrame().SetNotag(false); } else { CloseStackTag(0); }}void CObjectIStreamXml::ReadContainerContents(const CContainerTypeInfo* cType, TObjectPtr containerPtr){ int count = 0; TTypeInfo elementType = cType->GetElementType(); if ( !WillHaveName(elementType) ) { BEGIN_OBJECT_FRAME2(eFrameArrayElement, elementType); CContainerTypeInfo::CIterator iter; bool old_element = cType->InitIterator(iter, containerPtr); while ( HasMoreElements(elementType) ) { BeginArrayElement(elementType); do { if ( old_element ) { elementType->ReadData(*this, cType->GetElementPtr(iter)); old_element = cType->NextElement(iter); } else { cType->AddElement(containerPtr, *this); } } while (!m_RejectedTag.empty() && FindDeep(elementType,m_RejectedTag) != kInvalidMember); EndArrayElement(); ++count; } if ( old_element ) { cType->EraseAllElements(iter); } END_OBJECT_FRAME(); } else { CContainerTypeInfo::CIterator iter; bool old_element = cType->InitIterator(iter, containerPtr); while ( HasMoreElements(elementType) ) { if ( old_element ) { elementType->ReadData(*this, cType->GetElementPtr(iter)); old_element = cType->NextElement(iter); } else { cType->AddElement(containerPtr, *this); } ++count; } if ( old_element ) { cType->EraseAllElements(iter); } } if (count == 0) { const TFrame& frame = FetchFrameFromTop(0); if (frame.GetFrameType() == CObjectStackFrame::eFrameNamed) { const CClassTypeInfo* clType = dynamic_cast<const CClassTypeInfo*>(frame.GetTypeInfo()); if (clType && clType->Implicit() && clType->IsImplicitNonEmpty()) { ThrowError(fFormatError, "container is empty"); } } }}void CObjectIStreamXml::SkipContainerContents(const CContainerTypeInfo* cType){ TTypeInfo elementType = cType->GetElementType(); if ( !WillHaveName(elementType) ) { BEGIN_OBJECT_FRAME2(eFrameArrayElement, elementType); while ( HasMoreElements(elementType) ) { BeginArrayElement(elementType); SkipObject(elementType); EndArrayElement(); } END_OBJECT_FRAME(); } else { while ( HasMoreElements(elementType) ) { SkipObject(elementType); } }}#endifvoid CObjectIStreamXml::BeginNamedType(TTypeInfo namedTypeInfo){ const CClassTypeInfo* classType = dynamic_cast<const CClassTypeInfo*>(namedTypeInfo); if (classType) { CheckStdXml(classType); } OpenTag(namedTypeInfo);}void CObjectIStreamXml::EndNamedType(void){ CloseTag(TopFrame().GetTypeInfo()->GetName());}#ifdef VIRTUAL_MID_LEVEL_IOvoid CObjectIStreamXml::ReadNamedType(TTypeInfo namedTypeInfo, TTypeInfo typeInfo, TObjectPtr object){ BEGIN_OBJECT_FRAME2(eFrameNamed, namedTypeInfo); BeginNamedType(namedTypeInfo); ReadObject(object, typeInfo); EndNamedType(); END_OBJECT_FRAME();}#endifvoid CObjectIStreamXml::CheckStdXml(const CClassTypeInfoBase* classType){ if (m_EnforcedStdXml) { m_StdXml = false; return; } TMemberIndex first = classType->GetItems().FirstIndex(); m_StdXml = classType->GetItems().GetItemInfo(first)->GetId().HaveNoPrefix();}ETypeFamily CObjectIStreamXml::GetRealTypeFamily(TTypeInfo typeInfo){ ETypeFamily type = typeInfo->GetTypeFamily(); if (type == eTypeFamilyPointer) { const CPointerTypeInfo* ptr = dynamic_cast<const CPointerTypeInfo*>(typeInfo); if (ptr) { type = ptr->GetPointedType()->GetTypeFamily(); } } return type;}ETypeFamily CObjectIStreamXml::GetContainerElementTypeFamily(TTypeInfo typeInfo){ if (typeInfo->GetTypeFamily() == eTypeFamilyPointer) { const CPointerTypeInfo* ptr = dynamic_cast<const CPointerTypeInfo*>(typeInfo); if (ptr) { typeInfo = ptr->GetPointedType(); } } _ASSERT(typeInfo->GetTypeFamily() == eTypeFamilyContainer); const CContainerTypeInfo* ptr = dynamic_cast<const CContainerTypeInfo*>(typeInfo); return GetRealTypeFamily(ptr->GetElementType());}void CObjectIStreamXml::BeginClass(const CClassTypeInfo* classInfo){ CheckStdXml(classInfo); if (x_IsStdXml()) { if (m_Attlist || HasAttlist()) { TopFrame().SetNotag(); } else { OpenTagIfNamed(classInfo); } } else { OpenTagIfNamed(classInfo); }}void CObjectIStreamXml::EndClass(void){ if (TopFrame().GetNotag()) { TopFrame().SetNotag(false); } else { CloseTagIfNamed(TopFrame().GetTypeInfo()); } x_EndTypeNamespace();}void CObjectIStreamXml::UnexpectedMember(const CLightString& id, const CItemsInfo& items){ string message = "\""+string(id)+"\": unexpected member, should be one of: "; for ( CItemsInfo::CIterator i(items); i.Valid(); ++i ) { message += '\"' + items.GetItemInfo(i)->GetId().ToString() + "\" "; } ThrowError(fFormatError, message);}TMemberIndexCObjectIStreamXml::BeginClassMember(const CClassTypeInfo* classType){ CLightString tagName; bool more; do { more = false; if (m_RejectedTag.empty()) { if (m_Attlist && InsideTag()) { if (HasAttlist()) { tagName = ReadName(SkipWS()); } else { return kInvalidMember; } } else { if ( NextTagIsClosing() ) return kInvalidMember; tagName = ReadName(BeginOpeningTag()); } } else { tagName = RejectedName(); } TMemberIndex ind = classType->GetMembers().Find(tagName); if ( ind != kInvalidMember ) { if (x_IsStdXml()) { return ind; } }// if it is an attribute list, but the tag is unrecognized - just skip it if (m_Attlist) { string value; ReadAttributeValue(value); m_Input.SkipChar(); more = true; } } while (more); CLightString id = SkipStackTagName(tagName, 1, '_'); TMemberIndex index = classType->GetMembers().Find(id); if ( index == kInvalidMember ) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -