Mercurial > repos > IBBoard.WarFoundry.API
annotate api/Factories/Xml/WarFoundryXmlFactory.cs @ 151:1d13820b3d96
Fixes #176: Bug when saving recently edited army
* Add loaded file cleanup to AbstractWarFoundryFactory
* Add override of method with Zip reference closing to WarFoundryXmlFactory
WarFoundry now no longer ends up with trailing handles to files, although why they only caused problems in some situations is unknown
Also:
* Some line ending fixes (curse cross-platform development and different line terminators!)
author | IBBoard <dev@ibboard.co.uk> |
---|---|
date | Sat, 26 Sep 2009 18:48:36 +0000 |
parents | a37cdcbcad14 |
children | 70ba3bee0c2e |
rev | line source |
---|---|
104
2f3cafb69799
Re #121: Migrate to AGPL license
IBBoard <dev@ibboard.co.uk>
parents:
82
diff
changeset
|
1 // This file (WarFoundryXmlFactory.cs) is a part of the IBBoard.WarFoundry.API project and is copyright 2007, 2008, 2009 IBBoard. |
0 | 2 // |
104
2f3cafb69799
Re #121: Migrate to AGPL license
IBBoard <dev@ibboard.co.uk>
parents:
82
diff
changeset
|
3 // The file and the library/program it is in are licensed and distributed, without warranty, under the GNU Affero GPL license, either version 3 of the License or (at your option) any later version. Please see COPYING for more information and the full license. |
0 | 4 |
5 using System; | |
82 | 6 using System.IO; |
0 | 7 using System.Xml; |
8 using System.Xml.Schema; | |
34 | 9 using System.Xml.XPath; |
0 | 10 using System.Collections.Generic; |
11 using System.Text; | |
12 using IBBoard; | |
13 using IBBoard.IO; | |
14 using IBBoard.Lang; | |
15 using IBBoard.Logging; | |
16 using IBBoard.Xml; | |
17 using IBBoard.WarFoundry.API.Requirements; | |
18 using IBBoard.WarFoundry.API.Objects; | |
82 | 19 using ICSharpCode.SharpZipLib.Zip; |
20 | |
21 namespace IBBoard.WarFoundry.API.Factories.Xml | |
22 { | |
23 /// <summary> | |
24 /// The WarFoundryXmlFactory loads WarFoundry classes from the native "XML in a zip" file format. Files are validated using the schema for the file type, so structurally invalid files should be identified at initial load. | |
25 /// </summary> | |
26 public class WarFoundryXmlFactory : AbstractNativeWarFoundryFactory | |
0 | 27 { |
17
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
28 private static WarFoundryXmlFactory factory; |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
29 private WarFoundryXmlGameSystemFactory gameSystemFactory; |
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
30 private WarFoundryXmlRaceFactory raceFactory; |
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
31 private WarFoundryXmlArmyFactory armyFactory; |
0 | 32 |
17
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
33 public static AbstractNativeWarFoundryFactory GetFactory() |
0 | 34 { |
17
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
35 if (factory == null) |
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
36 { |
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
37 factory = new WarFoundryXmlFactory(); |
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
38 } |
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
39 |
a99d3b8466ba
Change "CreateFactory" method to "GetFactory" method to allow for caching
IBBoard <dev@ibboard.co.uk>
parents:
15
diff
changeset
|
40 return factory; |
0 | 41 } |
42 | |
82 | 43 private WarFoundryXmlFactory() : base() |
0 | 44 { |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
45 gameSystemFactory = new WarFoundryXmlGameSystemFactory(this); |
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
46 raceFactory = new WarFoundryXmlRaceFactory(this); |
82 | 47 armyFactory = new WarFoundryXmlArmyFactory(); |
0 | 48 } |
49 | |
50 protected override bool CheckCanFindArmyFileContent(ZipFile file) | |
51 { | |
52 return file.FindEntry("data.armyx", true) > -1; | |
53 } | |
54 | |
55 protected override bool CheckCanFindSystemFileContent(ZipFile file) | |
56 { | |
57 return file.FindEntry("data.systemx", true) > -1; | |
58 } | |
59 | |
60 protected override bool CheckCanFindRaceFileContent(ZipFile file) | |
61 { | |
62 return file.FindEntry("data.racex", true) > -1; | |
63 } | |
64 | |
50
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
65 protected override Stream GetArmyDataStream(ZipFile file) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
66 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
67 return file.GetInputStream(file.FindEntry("data.armyx", true)); |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
68 } |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
69 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
70 protected override Army CreateArmyFromStream (ZipFile file, Stream dataStream) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
71 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
72 XmlElement elem = GetRootElementFromStream(dataStream, WarFoundryXmlElementName.ARMY_ELEMENT); |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
73 return armyFactory.CreateArmyFromElement(file, elem); |
50
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
74 } |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
75 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
76 private XmlElement GetRootElementFromStream(Stream stream, WarFoundryXmlElementName elementName) |
0 | 77 { |
135 | 78 XmlDocument doc = WarFoundryXmlFactoryUtils.CreateXmlDocumentFromStream(stream); |
126
d5fec0698026
Fixes #113: XML loader doesn't close stream
IBBoard <dev@ibboard.co.uk>
parents:
104
diff
changeset
|
79 stream.Close(); |
0 | 80 XmlElement elem = (XmlElement)doc.LastChild; |
81 | |
43
d0812d7de39d
Re #49 - Resolve namespace issues
IBBoard <dev@ibboard.co.uk>
parents:
42
diff
changeset
|
82 if (!elem.LocalName.Equals(elementName.Value)) |
0 | 83 { |
84 throw new InvalidFileException(String.Format("Root element of XML was not valid. Expected {0} but got {1}", elementName.Value, elem.Name)); | |
85 } | |
86 | |
87 return elem; | |
88 } | |
50
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
89 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
90 protected override Stream GetGameSystemDataStream (ZipFile file) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
91 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
92 return file.GetInputStream(file.FindEntry("data.systemx", true)); |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
93 } |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
94 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
95 protected override GameSystem CreateGameSystemFromStream (ZipFile file, Stream dataStream) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
96 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
97 XmlElement elem = GetRootElementFromStream(dataStream, WarFoundryXmlElementName.SYSTEM_ELEMENT); |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
98 LogNotifier.Debug(GetType(), "Create GameSystem"); |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
99 return gameSystemFactory.CreateSystemFromElement(file, elem); |
50
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
100 } |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
101 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
102 protected override Stream GetRaceDataStream (ZipFile file) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
103 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
104 return file.GetInputStream(file.FindEntry("data.racex", true)); |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
105 } |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
106 |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
107 protected override Race CreateRaceFromStream (ZipFile file, Stream dataStream) |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
108 { |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
109 XmlElement elem = GetRootElementFromStream(dataStream, WarFoundryXmlElementName.RACE_ELEMENT); |
bb6b993b98bf
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
49
diff
changeset
|
110 LogNotifier.Debug(GetType(), "Create Race"); |
151
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
111 return raceFactory.CreateRaceFromElement(file, elem); |
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
112 } |
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
113 |
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
114 protected override void CleanUpFileAsSupportedType(ZipFile typedFile) |
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
115 { |
1d13820b3d96
Fixes #176: Bug when saving recently edited army
IBBoard <dev@ibboard.co.uk>
parents:
135
diff
changeset
|
116 typedFile.Close(); |
49
9d31d063b194
Re #10 - Refactor source code for readability
IBBoard <dev@ibboard.co.uk>
parents:
48
diff
changeset
|
117 } |
48
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
118 |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
119 public override void CompleteLoading(IWarFoundryStagedLoadObject obj) |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
120 { |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
121 LogNotifier.DebugFormat(GetType(), "Complete loading of {0} with ID {1}", obj.GetType().Name, obj.ID); |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
122 |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
123 if (obj is GameSystem) |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
124 { |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
125 gameSystemFactory.CompleteLoading((GameSystem)obj); |
48
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
126 } |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
127 else if (obj is Race) |
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
128 { |
52
64ef178c18aa
Re #10 - Refactor for readability
IBBoard <dev@ibboard.co.uk>
parents:
51
diff
changeset
|
129 raceFactory.CompleteLoading((Race)obj); |
48
b49372dd8afa
Re #50 - Complete loading of XML files
IBBoard <dev@ibboard.co.uk>
parents:
47
diff
changeset
|
130 } |
47
85f2b9c3609c
Re #13 - Use XPath for file loading
IBBoard <dev@ibboard.co.uk>
parents:
45
diff
changeset
|
131 } |
82 | 132 } |
0 | 133 } |