@@ -155,6 +155,17 @@ UserContainerLoaders<ElementLoader> GetLoaders<ElementLoader>(Loaders loaders, K
155155 where ElementLoader : Loader ;
156156 }
157157
158+ class UserEmptyEntry : IUserContainerEntry
159+ {
160+ public void Initialize ( Debugger debugger , string name ) { }
161+ public UserContainerLoaders < ElementLoader > GetLoaders < ElementLoader > ( Loaders loaders , Kind elementKind ,
162+ Debugger debugger , string name )
163+ where ElementLoader : Loader
164+ {
165+ return null ;
166+ }
167+ }
168+
158169 class UserContainerEntry : IUserContainerEntry
159170 {
160171 public UserContainerEntry ( string strContainerName )
@@ -415,12 +426,12 @@ class UserPolygon : PolygonLoader
415426 {
416427 public UserPolygon ( string id ,
417428 ClassScopeExpression exprOuter ,
418- ClassScopeExpression exprInnerContainer ,
429+ IUserContainerEntry innersContEntry ,
419430 int innersOffset )
420431 {
421432 this . id = id ;
422433 this . exprOuter = exprOuter ;
423- this . exprInnerContainer = exprInnerContainer ;
434+ this . innersContEntry = innersContEntry ;
424435 this . innersOffset = innersOffset ;
425436 }
426437
@@ -432,7 +443,8 @@ public override void Initialize(Debugger debugger, string name)
432443 {
433444 string type = ExpressionParser . GetValueType ( debugger , name ) ;
434445 exprOuter . Initialize ( debugger , name , type ) ;
435- exprInnerContainer . Initialize ( debugger , name , type ) ;
446+ // TODO: GetValueType() called internally second time
447+ innersContEntry . Initialize ( debugger , name ) ;
436448 }
437449
438450 public override void Load ( Loaders loaders , MemoryReader mreader , Debugger debugger ,
@@ -451,45 +463,40 @@ public override void Load(Loaders loaders, MemoryReader mreader, Debugger debugg
451463 if ( outerLoader == null )
452464 return ;
453465
454- string innersName = exprInnerContainer . GetString ( name ) ;
455- string innersType = ExpressionParser . GetValueType ( debugger , innersName ) ;
456- ContainerLoader innersLoader = loaders . FindByType ( ExpressionLoader . Kind . Container ,
457- innersName , innersType ) as ContainerLoader ;
458- if ( innersLoader == null )
459- return ;
460-
461- string innerType = innersLoader . ElementType ( innersType ) ;
462- LoaderR < ExpressionDrawer . Ring > innerLoader = outerLoader ;
463- if ( innerType != outerType )
464- {
465- string innerName = innersLoader . ElementName ( innersName , innerType ) ;
466- innerLoader = loaders . FindByType ( ExpressionLoader . Kind . Ring ,
467- innerName , innerType ) as LoaderR < ExpressionDrawer . Ring > ;
468- if ( innerLoader == null )
469- return ;
470- }
471-
472466 ExpressionDrawer . Ring outer = null ;
473467 outerLoader . Load ( loaders , mreader , debugger , outerName , outerType ,
474468 out traits , out outer ,
475469 callback ) ;
476470 if ( outer == null )
477471 return ;
478472
473+ UserContainerLoaders < LoaderR < ExpressionDrawer . Ring > > innersLoaders
474+ = innersContEntry . GetLoaders < LoaderR < ExpressionDrawer . Ring > > ( loaders , ExpressionLoader . Kind . Ring ,
475+ debugger , name ) ;
476+ // If there is no definition of inner rings, return
477+ if ( innersLoaders == null )
478+ {
479+ result = new ExpressionDrawer . Polygon ( outer , new List < Geometry . Ring > ( ) ) ;
480+ return ;
481+ }
482+
483+ // However if inner rings are defined then load them and return
484+ // them only if they are properly loaded.
479485 int i = 0 ;
480486 Geometry . Traits t = null ;
481487 List < Geometry . Ring > inners = new List < Geometry . Ring > ( ) ;
482- bool ok = innersLoader . ForEachElement (
483- debugger , innersName ,
488+ bool ok = innersLoaders . ContainerLoader . ForEachElement (
489+ debugger , innersLoaders . ContainerName ,
484490 delegate ( string elName )
485491 {
486492 if ( i ++ < innersOffset )
487493 return true ;
488494
489495 ExpressionDrawer . Ring inner = null ;
490- innerLoader . Load ( loaders , mreader , debugger , elName , innerType ,
491- out t , out inner ,
492- callback ) ;
496+ innersLoaders . ElementLoader . Load ( loaders , mreader , debugger ,
497+ elName , innersLoaders . ElementType ,
498+ out t , out inner ,
499+ callback ) ;
493500 if ( inner == null )
494501 return false ;
495502 inners . Add ( inner ) ;
@@ -506,7 +513,7 @@ public override void Load(Loaders loaders, MemoryReader mreader, Debugger debugg
506513
507514 string id ;
508515 ClassScopeExpression exprOuter ;
509- ClassScopeExpression exprInnerContainer ;
516+ IUserContainerEntry innersContEntry ;
510517 int innersOffset ;
511518 }
512519
@@ -650,29 +657,24 @@ private static bool ReloadUserTypes(Loaders loaders,
650657 }
651658 else if ( elDrawable . Name == "Polygon" )
652659 {
653- // TODO: optional interior rings
654- // arrays as container
660+ // TODO: Allow container of Points as outer ring
655661
656- var elOuter = Util . GetXmlElementByTagName ( elDrawable , "ExteriorRing" ) ;
657- var elInners = Util . GetXmlElementByTagName ( elDrawable , "InteriorRings" ) ;
658- if ( elOuter != null && elInners != null )
662+ var elOuterName = Util . GetXmlElementByTagNames ( elDrawable , "ExteriorRing" , "Name" ) ;
663+ if ( elOuterName != null )
659664 {
660- var elOuterName = Util . GetXmlElementByTagName ( elOuter , "Name" ) ;
661- var elCont = Util . GetXmlElementByTagName ( elInners , "Container" ) ;
662- if ( elOuterName != null && elCont != null )
663- {
664- var elInnersName = Util . GetXmlElementByTagName ( elCont , "Name" ) ;
665- if ( elInnersName != null )
666- {
667- var elInnersOffset = Util . GetXmlElementByTagName ( elCont , "Offset" ) ;
668- int innersOffset = 0 ;
669- if ( elInnersOffset != null )
670- Util . TryParseInt ( elInnersOffset . InnerText , out innersOffset ) ;
671- ClassScopeExpression classExprOuter = new ClassScopeExpression ( elOuterName . InnerText ) ;
672- ClassScopeExpression classExprInners = new ClassScopeExpression ( elInnersName . InnerText ) ;
673- loaders . Add ( new UserPolygon ( id , classExprOuter , classExprInners , innersOffset ) ) ;
674- }
675- }
665+ ClassScopeExpression classExprOuter = new ClassScopeExpression ( elOuterName . InnerText ) ;
666+ IUserContainerEntry innersContEntry = GetContainerEntry ( elDrawable , "InteriorRings" ) ;
667+ if ( innersContEntry == null )
668+ innersContEntry = new UserEmptyEntry ( ) ;
669+ // TODO: InteriorRings searched the second time
670+ var elInners = Util . GetXmlElementByTagName ( elDrawable , "InteriorRings" ) ;
671+ var elInnersOffset = Util . GetXmlElementByTagName ( elInners , "Offset" ) ;
672+
673+ int innersOffset = 0 ;
674+ if ( elInnersOffset != null )
675+ Util . TryParseInt ( elInnersOffset . InnerText , out innersOffset ) ;
676+
677+ loaders . Add ( new UserPolygon ( id , classExprOuter , innersContEntry , innersOffset ) ) ;
676678 }
677679 }
678680 else if ( elDrawable . Name == "MultiPolygon" )
@@ -694,14 +696,10 @@ static IUserContainerEntry GetContainerEntry(System.Xml.XmlElement elDrawable,
694696 var elElements = Util . GetXmlElementByTagName ( elDrawable , elementsKind ) ;
695697 if ( elElements != null )
696698 {
697- var elCont = Util . GetXmlElementByTagName ( elElements , "Container" ) ;
698- if ( elCont != null )
699+ var elContName = Util . GetXmlElementByTagNames ( elElements , "Container" , "Name ") ;
700+ if ( elContName != null )
699701 {
700- var elName = Util . GetXmlElementByTagName ( elCont , "Name" ) ;
701- if ( elName != null )
702- {
703- return new UserContainerEntry ( elName . InnerText ) ;
704- }
702+ return new UserContainerEntry ( elContName . InnerText ) ;
705703 }
706704 else
707705 {
0 commit comments