aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs')
-rw-r--r--OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs289
1 files changed, 289 insertions, 0 deletions
diff --git a/OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs b/OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs
new file mode 100644
index 0000000..7d9d247
--- /dev/null
+++ b/OpenSim/Region/Framework/Scenes/SceneXmlLoader.cs
@@ -0,0 +1,289 @@
1/*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSim Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27
28using System;
29using System.Collections.Generic;
30using System.IO;
31using System.Reflection;
32using System.Xml;
33using OpenMetaverse;
34using log4net;
35using OpenSim.Framework;
36using OpenSim.Region.Physics.Manager;
37
38namespace OpenSim.Region.Framework.Scenes
39{
40 /// <summary>
41 /// Static methods to serialize and deserialize scene objects to and from XML
42 /// </summary>
43 public class SceneXmlLoader
44 {
45 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
46
47 public static void LoadPrimsFromXml(Scene scene, string fileName, bool newIDS, Vector3 loadOffset)
48 {
49 XmlDocument doc = new XmlDocument();
50 XmlNode rootNode;
51
52 if (fileName.StartsWith("http:") || File.Exists(fileName))
53 {
54 XmlTextReader reader = new XmlTextReader(fileName);
55 reader.WhitespaceHandling = WhitespaceHandling.None;
56 doc.Load(reader);
57 reader.Close();
58 rootNode = doc.FirstChild;
59 foreach (XmlNode aPrimNode in rootNode.ChildNodes)
60 {
61 SceneObjectGroup obj = new SceneObjectGroup(aPrimNode.OuterXml, true);
62
63 if (newIDS)
64 {
65 obj.ResetIDs();
66 }
67 //if we want this to be a import method then we need new uuids for the object to avoid any clashes
68 //obj.RegenerateFullIDs();
69
70 scene.AddNewSceneObject(obj, true);
71 }
72 }
73 else
74 {
75 throw new Exception("Could not open file " + fileName + " for reading");
76 }
77 }
78
79 public static void SavePrimsToXml(Scene scene, string fileName)
80 {
81 FileStream file = new FileStream(fileName, FileMode.Create);
82 StreamWriter stream = new StreamWriter(file);
83 int primCount = 0;
84 stream.WriteLine("<scene>\n");
85
86 List<EntityBase> EntityList = scene.GetEntities();
87
88 foreach (EntityBase ent in EntityList)
89 {
90 if (ent is SceneObjectGroup)
91 {
92 stream.WriteLine(((SceneObjectGroup) ent).ToXmlString());
93 primCount++;
94 }
95 }
96 stream.WriteLine("</scene>\n");
97 stream.Close();
98 file.Close();
99 }
100
101 public static string SaveGroupToXml2(SceneObjectGroup grp)
102 {
103 return grp.ToXmlString2();
104 }
105
106 public static SceneObjectGroup DeserializeGroupFromXml2(string xmlString)
107 {
108 XmlDocument doc = new XmlDocument();
109 XmlNode rootNode;
110
111 XmlTextReader reader = new XmlTextReader(new StringReader(xmlString));
112 reader.WhitespaceHandling = WhitespaceHandling.None;
113 doc.Load(reader);
114 reader.Close();
115 rootNode = doc.FirstChild;
116
117 // This is to deal with neighbouring regions that are still surrounding the group xml with the <scene>
118 // tag. It should be possible to remove the first part of this if statement once we go past 0.5.9 (or
119 // when some other changes forces all regions to upgrade).
120 // This might seem rather pointless since prim crossing from this revision to an earlier revision remains
121 // broken. But it isn't much work to accomodate the old format here.
122 if (rootNode.LocalName.Equals("scene"))
123 {
124 foreach (XmlNode aPrimNode in rootNode.ChildNodes)
125 {
126 // There is only ever one prim. This oddity should be removeable post 0.5.9
127 return new SceneObjectGroup(aPrimNode.OuterXml);
128 }
129
130 return null;
131 }
132 else
133 {
134 return new SceneObjectGroup(rootNode.OuterXml);
135 }
136 }
137
138 /// <summary>
139 /// Load prims from the xml2 format
140 /// </summary>
141 /// <param name="scene"></param>
142 /// <param name="fileName"></param>
143 public static void LoadPrimsFromXml2(Scene scene, string fileName)
144 {
145 LoadPrimsFromXml2(scene, new XmlTextReader(fileName), false);
146 }
147
148 /// <summary>
149 /// Load prims from the xml2 format
150 /// </summary>
151 /// <param name="scene"></param>
152 /// <param name="reader"></param>
153 /// <param name="startScripts"></param>
154 public static void LoadPrimsFromXml2(Scene scene, TextReader reader, bool startScripts)
155 {
156 LoadPrimsFromXml2(scene, new XmlTextReader(reader), startScripts);
157 }
158
159 /// <summary>
160 /// Load prims from the xml2 format. This method will close the reader
161 /// </summary>
162 /// <param name="scene"></param>
163 /// <param name="reader"></param>
164 /// <param name="startScripts"></param>
165 protected static void LoadPrimsFromXml2(Scene scene, XmlTextReader reader, bool startScripts)
166 {
167 XmlDocument doc = new XmlDocument();
168 reader.WhitespaceHandling = WhitespaceHandling.None;
169 doc.Load(reader);
170 reader.Close();
171 XmlNode rootNode = doc.FirstChild;
172
173 ICollection<SceneObjectGroup> sceneObjects = new List<SceneObjectGroup>();
174 foreach (XmlNode aPrimNode in rootNode.ChildNodes)
175 {
176 SceneObjectGroup obj = CreatePrimFromXml2(scene, aPrimNode.OuterXml);
177 if (obj != null && startScripts)
178 sceneObjects.Add(obj);
179 }
180
181 foreach (SceneObjectGroup sceneObject in sceneObjects)
182 {
183 sceneObject.CreateScriptInstances(0, true, scene.DefaultScriptEngine, 0);
184 }
185 }
186
187 /// <summary>
188 /// Create a prim from the xml2 representation.
189 /// </summary>
190 /// <param name="scene"></param>
191 /// <param name="xmlData"></param>
192 /// <returns>The scene object created. null if the scene object already existed</returns>
193 protected static SceneObjectGroup CreatePrimFromXml2(Scene scene, string xmlData)
194 {
195 SceneObjectGroup obj = new SceneObjectGroup(xmlData);
196
197 if (scene.AddRestoredSceneObject(obj, true, false))
198 return obj;
199 else
200 return null;
201 }
202
203 public static void SavePrimsToXml2(Scene scene, string fileName)
204 {
205 List<EntityBase> EntityList = scene.GetEntities();
206
207 SavePrimListToXml2(EntityList, fileName);
208 }
209
210 public static void SavePrimsToXml2(Scene scene, TextWriter stream, Vector3 min, Vector3 max)
211 {
212 List<EntityBase> EntityList = scene.GetEntities();
213
214 SavePrimListToXml2(EntityList, stream, min, max);
215 }
216
217 public static void SaveNamedPrimsToXml2(Scene scene, string primName, string fileName)
218 {
219 m_log.InfoFormat(
220 "[SERIALISER]: Saving prims with name {0} in xml2 format for region {1} to {2}",
221 primName, scene.RegionInfo.RegionName, fileName);
222
223 List<EntityBase> entityList = scene.GetEntities();
224 List<EntityBase> primList = new List<EntityBase>();
225
226 foreach (EntityBase ent in entityList)
227 {
228 if (ent is SceneObjectGroup)
229 {
230 if (ent.Name == primName)
231 {
232 primList.Add(ent);
233 }
234 }
235 }
236
237 SavePrimListToXml2(primList, fileName);
238 }
239
240 public static void SavePrimListToXml2(List<EntityBase> entityList, string fileName)
241 {
242 FileStream file = new FileStream(fileName, FileMode.Create);
243 try
244 {
245 StreamWriter stream = new StreamWriter(file);
246 try
247 {
248 SavePrimListToXml2(entityList, stream, Vector3.Zero, Vector3.Zero);
249 }
250 finally
251 {
252 stream.Close();
253 }
254 }
255 finally
256 {
257 file.Close();
258 }
259 }
260
261 public static void SavePrimListToXml2(List<EntityBase> entityList, TextWriter stream, Vector3 min, Vector3 max)
262 {
263 int primCount = 0;
264 stream.WriteLine("<scene>\n");
265
266 foreach (EntityBase ent in entityList)
267 {
268 if (ent is SceneObjectGroup)
269 {
270 SceneObjectGroup g = (SceneObjectGroup)ent;
271 if (!min.Equals(Vector3.Zero) || !max.Equals(Vector3.Zero))
272 {
273 Vector3 pos = g.RootPart.GetWorldPosition();
274 if (min.X > pos.X || min.Y > pos.Y || min.Z > pos.Z)
275 continue;
276 if (max.X < pos.X || max.Y < pos.Y || max.Z < pos.Z)
277 continue;
278 }
279
280 stream.WriteLine(g.ToXmlString2());
281 primCount++;
282 }
283 }
284 stream.WriteLine("</scene>\n");
285 stream.Flush();
286 }
287
288 }
289}