Browse Source

Bookmarks (and breakpoints) are saved in the project preferences.

git-svn-id: svn://svn.sharpdevelop.net/sharpdevelop/trunk@145 1ccf3a8d-04fe-1044-b7c0-cef0b8235c61
shortcuts
Daniel Grunwald 20 years ago
parent
commit
a1c667f5f1
  1. 20
      src/Libraries/ICSharpCode.TextEditor/Project/Src/Document/BookmarkManager/Bookmark.cs
  2. 2
      src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj
  3. 2
      src/Main/Base/Project/Src/Commands/FileCommands.cs
  4. 30
      src/Main/Base/Project/Src/Gui/IMementoCapable.cs
  5. 13
      src/Main/Base/Project/Src/Gui/Workbench/DefaultWorkbench.cs
  6. 23
      src/Main/Base/Project/Src/Project/AbstractProject.cs
  7. 3
      src/Main/Base/Project/Src/Project/IProject.cs
  8. 34
      src/Main/Base/Project/Src/Services/ProjectService/ProjectService.cs
  9. 2
      src/Main/Base/Project/Src/TextEditor/Bookmarks/Bookmark.cs
  10. 73
      src/Main/Base/Project/Src/TextEditor/Bookmarks/BookmarkConverter.cs
  11. 11
      src/Main/Base/Project/Src/TextEditor/Bookmarks/BookmarkManager.cs
  12. 28
      src/Main/Base/Project/Src/TextEditor/Bookmarks/Pad/Nodes/BookmarkFolderNode.cs
  13. 32
      src/Main/Base/Project/Src/TextEditor/Bookmarks/Pad/Nodes/BookmarkNode.cs
  14. 2
      src/Main/Core/Project/Src/AddInTree/AddIn/AddIn.cs
  15. 119
      src/Main/Core/Project/Src/Services/PropertyService/Properties.cs

20
src/Libraries/ICSharpCode.TextEditor/Project/Src/Document/BookmarkManager/Bookmark.cs

@ -25,7 +25,19 @@ namespace ICSharpCode.TextEditor.Document
return document; return document;
} }
set { set {
document = value; if (document != value) {
document = value;
OnDocumentChanged(EventArgs.Empty);
}
}
}
public event EventHandler DocumentChanged;
protected virtual void OnDocumentChanged(EventArgs e)
{
if (DocumentChanged != null) {
DocumentChanged(this, e);
} }
} }
@ -35,8 +47,10 @@ namespace ICSharpCode.TextEditor.Document
} }
set { set {
isEnabled = value; isEnabled = value;
document.RequestUpdate(new TextAreaUpdate(TextAreaUpdateType.SingleLine, lineNumber)); if (document != null) {
document.CommitUpdate(); document.RequestUpdate(new TextAreaUpdate(TextAreaUpdateType.SingleLine, lineNumber));
document.CommitUpdate();
}
} }
} }

2
src/Main/Base/Project/ICSharpCode.SharpDevelop.csproj

@ -132,7 +132,6 @@
<Compile Include="Src\Internal\Auswerter\WindowOpenAuswerter.cs" /> <Compile Include="Src\Internal\Auswerter\WindowOpenAuswerter.cs" />
<Compile Include="Src\Internal\Templates\Project\ProjectDescriptor.cs" /> <Compile Include="Src\Internal\Templates\Project\ProjectDescriptor.cs" />
<Compile Include="Src\Internal\Templates\Project\CombineDescriptor.cs" /> <Compile Include="Src\Internal\Templates\Project\CombineDescriptor.cs" />
<Compile Include="Src\Gui\IMementoCapable.cs" />
<Compile Include="Src\Gui\IProgressMonitor.cs" /> <Compile Include="Src\Gui\IProgressMonitor.cs" />
<Compile Include="Src\Gui\IViewContent.cs" /> <Compile Include="Src\Gui\IViewContent.cs" />
<Compile Include="Src\Gui\IWorkbench.cs" /> <Compile Include="Src\Gui\IWorkbench.cs" />
@ -662,6 +661,7 @@
<Compile Include="Src\Gui\BrowserDisplayBinding\ExtendedWebBrowser.cs"> <Compile Include="Src\Gui\BrowserDisplayBinding\ExtendedWebBrowser.cs">
<SubType>Component</SubType> <SubType>Component</SubType>
</Compile> </Compile>
<Compile Include="Src\TextEditor\Bookmarks\BookmarkConverter.cs" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ProjectReference Include="..\..\..\Libraries\DockPanel_Src\WinFormsUI\WinFormsUI.csproj"> <ProjectReference Include="..\..\..\Libraries\DockPanel_Src\WinFormsUI\WinFormsUI.csproj">

2
src/Main/Base/Project/Src/Commands/FileCommands.cs

@ -67,7 +67,7 @@ namespace ICSharpCode.SharpDevelop.Commands
ProjectService.MarkFileDirty(window.ViewContent.FileName); ProjectService.MarkFileDirty(window.ViewContent.FileName);
FileUtility.ObservedSave(new FileOperationDelegate(window.ViewContent.Save), window.ViewContent.FileName); FileUtility.ObservedSave(new FileOperationDelegate(window.ViewContent.Save), window.ViewContent.FileName, FileErrorPolicy.ProvideAlternative);
} }
} }
} }

30
src/Main/Base/Project/Src/Gui/IMementoCapable.cs

@ -1,30 +0,0 @@
// <file>
// <copyright see="prj:///doc/copyright.txt"/>
// <license see="prj:///doc/license.txt"/>
// <owner name="Mike Krüger" email="mike@icsharpcode.net"/>
// <version value="$version"/>
// </file>
using ICSharpCode.Core;
namespace ICSharpCode.SharpDevelop.Gui
{
/// <summary>
/// This interface flags an object beeing "mementocapable". This means that the
/// state of the object could be saved to an <see cref="Properties"/> object
/// and set from a object from the same class.
/// This is used to save and restore the state of GUI objects.
/// </summary>
public interface IMementoCapable
{
/// <summary>
/// Creates a new memento from the state.
/// </summary>
Properties CreateMemento();
/// <summary>
/// Sets the state to the given memento.
/// </summary>
void SetMemento(Properties memento);
}
}

13
src/Main/Base/Project/Src/Gui/Workbench/DefaultWorkbench.cs

@ -276,7 +276,7 @@ namespace ICSharpCode.SharpDevelop.Gui
string fullFileName = Path.Combine(directory, fileName); string fullFileName = Path.Combine(directory, fileName);
if (FileUtility.IsValidFileName(fullFileName)) { if (FileUtility.IsValidFileName(fullFileName)) {
FileUtility.ObservedSave(new NamedFileOperationDelegate(memento.Save), fullFileName, FileErrorPolicy.ProvideAlternative); FileUtility.ObservedSave(new NamedFileOperationDelegate(memento.Save), fullFileName, FileErrorPolicy.Inform);
} }
} }
@ -371,8 +371,6 @@ namespace ICSharpCode.SharpDevelop.Gui
{ {
base.OnClosing(e); base.OnClosing(e);
ProjectService.SaveSolutionPreferences();
while (WorkbenchSingleton.Workbench.ViewContentCollection.Count > 0) { while (WorkbenchSingleton.Workbench.ViewContentCollection.Count > 0) {
IViewContent content = WorkbenchSingleton.Workbench.ViewContentCollection[0]; IViewContent content = WorkbenchSingleton.Workbench.ViewContentCollection[0];
content.WorkbenchWindow.CloseWindow(false); content.WorkbenchWindow.CloseWindow(false);
@ -382,15 +380,6 @@ namespace ICSharpCode.SharpDevelop.Gui
} }
} }
ProjectService.CloseSolution(); ProjectService.CloseSolution();
// TODO : Dirty Files Dialog
// foreach (IViewContent content in ViewContentCollection) {
// if (content.IsDirty) {
// ICSharpCode.SharpDevelop.Gui.DirtyFilesDialog dfd = new ICSharpCode.SharpDevelop.Gui.DirtyFilesDialog();
// e.Cancel = dfd.ShowDialog(ICSharpCode.SharpDevelop.Gui.WorkbenchSingleton.MainForm) == DialogResult.Cancel;
// return;
// }
// }
} }
protected override void OnClosed(EventArgs e) protected override void OnClosed(EventArgs e)

23
src/Main/Base/Project/Src/Project/AbstractProject.cs

@ -362,5 +362,28 @@ namespace ICSharpCode.SharpDevelop.Project
{ {
return null; return null;
} }
/// <summary>
/// Saves project preferences (currently opened files, bookmarks etc.) to the
/// a property container.
/// </summary>
public virtual Properties CreateMemento()
{
Properties properties = new Properties();
properties.Set<ICSharpCode.SharpDevelop.Bookmarks.SDBookmark[]>("bookmarks", ICSharpCode.SharpDevelop.Bookmarks.BookmarkManager.GetProjectBookmarks(this).ToArray());
return properties;
}
/// <summary>
/// Loads project preferences (currently opened files, bookmarks etc.).
/// </summary>
public virtual void SetMemento(Properties properties)
{
foreach (ICSharpCode.SharpDevelop.Bookmarks.SDBookmark mark in properties.Get<ICSharpCode.SharpDevelop.Bookmarks.SDBookmark[]>("bookmarks", new ICSharpCode.SharpDevelop.Bookmarks.SDBookmark[0])) {
ICSharpCode.SharpDevelop.Bookmarks.BookmarkManager.AddMark(mark);
}
}
} }
} }

3
src/Main/Base/Project/Src/Project/IProject.cs

@ -1,6 +1,7 @@
using System; using System;
using System.CodeDom.Compiler; using System.CodeDom.Compiler;
using System.Collections.Generic; using System.Collections.Generic;
using ICSharpCode.Core;
namespace ICSharpCode.SharpDevelop.Project namespace ICSharpCode.SharpDevelop.Project
{ {
@ -11,7 +12,7 @@ namespace ICSharpCode.SharpDevelop.Project
Module Module
}; };
public interface IProject : ISolutionFolder, IDisposable public interface IProject : ISolutionFolder, IDisposable, IMementoCapable
{ {
PropertyGroup BaseConfiguration { PropertyGroup BaseConfiguration {
get; get;

34
src/Main/Base/Project/Src/Services/ProjectService/ProjectService.cs

@ -137,6 +137,16 @@ namespace ICSharpCode.SharpDevelop.Project
{ {
openSolution = Solution.Load(fileName); openSolution = Solution.Load(fileName);
OnSolutionLoaded(new SolutionEventArgs(openSolution)); OnSolutionLoaded(new SolutionEventArgs(openSolution));
try {
foreach (IProject project in openSolution.Projects) {
string file = GetPreferenceFileName(project);
if (FileUtility.IsValidFileName(file) && File.Exists(file)) {
project.SetMemento(Properties.Load(file));
}
}
} catch (Exception ex) {
MessageService.ShowError(ex);
}
} }
public static void SaveSolution() public static void SaveSolution()
@ -150,9 +160,30 @@ namespace ICSharpCode.SharpDevelop.Project
} }
} }
static string GetPreferenceFileName(IProject project)
{
string directory = PropertyService.ConfigDirectory + "preferences";
string fileName = project.FileName.Substring(3).Replace('/', '.').Replace('\\', '.').Replace(Path.DirectorySeparatorChar, '.');
string fullFileName = Path.Combine(directory, fileName + ".xml");
return fullFileName;
}
public static void SaveSolutionPreferences() public static void SaveSolutionPreferences()
{ {
// TODO: string directory = PropertyService.ConfigDirectory + "preferences";
if (!Directory.Exists(directory)) {
Directory.CreateDirectory(directory);
}
foreach (IProject project in OpenSolution.Projects) {
Properties memento = project.CreateMemento();
if (memento == null) continue;
string fullFileName = GetPreferenceFileName(project);
if (FileUtility.IsValidFileName(fullFileName)) {
FileUtility.ObservedSave(new NamedFileOperationDelegate(memento.Save), fullFileName, FileErrorPolicy.Inform);
}
}
} }
public static void CloseSolution() public static void CloseSolution()
@ -160,6 +191,7 @@ namespace ICSharpCode.SharpDevelop.Project
if (openSolution != null) { if (openSolution != null) {
OnSolutionClosing(new SolutionEventArgs(openSolution)); OnSolutionClosing(new SolutionEventArgs(openSolution));
SaveSolutionPreferences();
openSolution.Dispose(); openSolution.Dispose();
openSolution = null; openSolution = null;

2
src/Main/Base/Project/Src/TextEditor/Bookmarks/Bookmark.cs

@ -6,6 +6,7 @@
// </file> // </file>
using System; using System;
using System.ComponentModel;
using System.Collections; using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Drawing; using System.Drawing;
@ -19,6 +20,7 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
/// <summary> /// <summary>
/// Description of Bookmark. /// Description of Bookmark.
/// </summary> /// </summary>
[TypeConverter(typeof(BookmarkConverter))]
public class SDBookmark : Bookmark public class SDBookmark : Bookmark
{ {
string fileName; string fileName;

73
src/Main/Base/Project/Src/TextEditor/Bookmarks/BookmarkConverter.cs

@ -0,0 +1,73 @@
// <file>
// <copyright see="prj:///doc/copyright.txt"/>
// <license see="prj:///doc/license.txt"/>
// <owner name="Daniel Grunwald" email="daniel@danielgrunwald.de"/>
// <version value="$version"/>
// </file>
using System;
using System.ComponentModel;
using System.Text;
using System.Globalization;
using ICSharpCode.Core;
using ICSharpCode.TextEditor.Document;
namespace ICSharpCode.SharpDevelop.Bookmarks
{
public sealed class BookmarkConverter : TypeConverter
{
public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
{
if (sourceType == typeof(string)) {
return true;
} else {
return base.CanConvertFrom(context, sourceType);
}
}
public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
{
if (value is string) {
string[] v = ((string)value).Split('|');
string fileName = v[1];
int lineNumber = int.Parse(v[2], culture);
SDBookmark bookmark;
switch (v[0]) {
case "Breakpoint":
bookmark = new Breakpoint(null, fileName, lineNumber).Bookmark;
break;
default:
bookmark = new SDBookmark(fileName, null, lineNumber);
break;
}
bookmark.IsEnabled = bool.Parse(v[3]);
return bookmark;
} else {
return base.ConvertFrom(context, culture, value);
}
}
public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
{
SDBookmark bookmark = value as SDBookmark;
if (destinationType == typeof(string) && bookmark != null) {
StringBuilder b = new StringBuilder();
if (bookmark is BreakpointBookmark) {
b.Append("Breakpoint");
} else {
b.Append("Bookmark");
}
b.Append('|');
b.Append(bookmark.FileName);
b.Append('|');
b.Append(bookmark.LineNumber);
b.Append('|');
b.Append(bookmark.IsEnabled.ToString());
return b.ToString();
} else {
return base.ConvertTo(context, culture, value, destinationType);
}
}
}
}

11
src/Main/Base/Project/Src/TextEditor/Bookmarks/BookmarkManager.cs

@ -60,6 +60,17 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
} }
} }
public static List<SDBookmark> GetProjectBookmarks(ICSharpCode.SharpDevelop.Project.IProject project)
{
List<SDBookmark> projectBookmarks = new List<SDBookmark>();
foreach (SDBookmark mark in bookmarks) {
if (mark.FileName != null && project.IsFileInProject(mark.FileName)) {
projectBookmarks.Add(mark);
}
}
return projectBookmarks;
}
public static event BookmarkEventHandler Removed; public static event BookmarkEventHandler Removed;
public static event BookmarkEventHandler Added; public static event BookmarkEventHandler Added;
} }

28
src/Main/Base/Project/Src/TextEditor/Bookmarks/Pad/Nodes/BookmarkFolderNode.cs

@ -1,4 +1,5 @@
using System; using System;
using System.IO;
using System.Drawing; using System.Drawing;
using System.Collections.Generic; using System.Collections.Generic;
using System.Windows.Forms; using System.Windows.Forms;
@ -15,6 +16,7 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
{ {
List<SDBookmark> marks = new List<SDBookmark>(); List<SDBookmark> marks = new List<SDBookmark>();
string fileName; string fileName;
string fileNameText;
string occurences; string occurences;
Image icon; Image icon;
@ -28,6 +30,7 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
{ {
drawDefault = false; drawDefault = false;
this.fileName = fileName; this.fileName = fileName;
fileNameText = Path.GetFileName(fileName) + " in " + Path.GetDirectoryName(fileName);
icon = IconService.GetBitmap(IconService.GetImageForFile(fileName)); icon = IconService.GetBitmap(IconService.GetImageForFile(fileName));
Nodes.Add(new TreeNode()); Nodes.Add(new TreeNode());
} }
@ -39,13 +42,13 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
} else { } else {
occurences = " (" + marks.Count + " bookmarks)"; occurences = " (" + marks.Count + " bookmarks)";
} }
this.Text = fileName + occurences; this.Text = fileNameText + occurences;
} }
protected override int MeasureItemWidth(DrawTreeNodeEventArgs e) protected override int MeasureItemWidth(DrawTreeNodeEventArgs e)
{ {
Graphics g = e.Graphics; Graphics g = e.Graphics;
int x = MeasureTextWidth(g, fileName, Font); int x = MeasureTextWidth(g, fileNameText, Font);
x += MeasureTextWidth(g, occurences, ItalicFont); x += MeasureTextWidth(g, occurences, ItalicFont);
if (icon != null) { if (icon != null) {
x += icon.Width; x += icon.Width;
@ -60,17 +63,30 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
g.DrawImage(icon, x, e.Bounds.Y, icon.Width, icon.Height); g.DrawImage(icon, x, e.Bounds.Y, icon.Width, icon.Height);
x += icon.Width; x += icon.Width;
} }
DrawText(g, fileName, Brushes.Black, Font, ref x, e.Bounds.Y); DrawText(g, fileNameText, Brushes.Black, Font, ref x, e.Bounds.Y);
DrawText(g, occurences, Brushes.Gray, ItalicFont, ref x, e.Bounds.Y); DrawText(g, occurences, Brushes.Gray, ItalicFont, ref x, e.Bounds.Y);
} }
public void AddMark(SDBookmark mark) public void AddMark(SDBookmark mark)
{ {
marks.Add(mark); int index = -1;
for (int i = 0; i < marks.Count; ++i) {
if (mark.LineNumber < marks[i].LineNumber) {
index = i;
break;
}
}
if (index < 0)
marks.Add(mark);
else
marks.Insert(index, mark);
if (isInitialized) { if (isInitialized) {
BookmarkNode newNode = new BookmarkNode(mark); BookmarkNode newNode = new BookmarkNode(mark);
Nodes.Add(newNode); if (index < 0)
Nodes.Add(newNode);
else
Nodes.Insert(index, newNode);
newNode.EnsureVisible(); newNode.EnsureVisible();
} }
SetText(); SetText();
@ -95,7 +111,7 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
Nodes.Clear(); Nodes.Clear();
if (marks.Count > 0) { if (marks.Count > 0) {
IDocument document = marks[0].Document; IDocument document = marks[0].Document;
if (document.HighlightingStrategy == null) { if (document != null && document.HighlightingStrategy == null) {
document.HighlightingStrategy = HighlightingStrategyFactory.CreateHighlightingStrategyForFile(fileName); document.HighlightingStrategy = HighlightingStrategyFactory.CreateHighlightingStrategyForFile(fileName);
} }
foreach (SDBookmark mark in marks) { foreach (SDBookmark mark in marks) {

32
src/Main/Base/Project/Src/TextEditor/Bookmarks/Pad/Nodes/BookmarkNode.cs

@ -37,15 +37,37 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
Checked = bookmark.IsEnabled; Checked = bookmark.IsEnabled;
positionText = "(" + (bookmark.LineNumber + 1) + ") "; positionText = "(" + (bookmark.LineNumber + 1) + ") ";
line = bookmark.Document.GetLineSegment(bookmark.LineNumber); bookmark.DocumentChanged += BookmarkDocumentChanged;
Text = positionText + bookmark.Document.GetText(line); bookmark.LineNumberChanged += BookmarkLineNumberChanged;
if (bookmark.Document != null) {
line = bookmark.Document.GetLineSegment(bookmark.LineNumber);
Text = positionText + bookmark.Document.GetText(line);
} else {
Text = positionText;
}
}
void BookmarkDocumentChanged(object sender, EventArgs e)
{
if (bookmark.Document != null) {
line = bookmark.Document.GetLineSegment(bookmark.LineNumber);
Text = positionText + bookmark.Document.GetText(line);
}
}
void BookmarkLineNumberChanged(object sender, EventArgs e)
{
positionText = "(" + (bookmark.LineNumber + 1) + ") ";
BookmarkDocumentChanged(sender, e);
} }
protected override int MeasureItemWidth(DrawTreeNodeEventArgs e) protected override int MeasureItemWidth(DrawTreeNodeEventArgs e)
{ {
Graphics g = e.Graphics; Graphics g = e.Graphics;
int x = MeasureTextWidth(g, positionText, BoldMonospacedFont); int x = MeasureTextWidth(g, positionText, BoldMonospacedFont);
x += MeasureTextWidth(g, bookmark.Document.GetText(line).Replace("\t", " "), BoldMonospacedFont); if (line != null) {
x += MeasureTextWidth(g, bookmark.Document.GetText(line).Replace("\t", " "), BoldMonospacedFont);
}
return x; return x;
} }
@ -57,7 +79,9 @@ namespace ICSharpCode.SharpDevelop.Bookmarks
spaceSize = g.MeasureString("-", Font, new PointF(0, 0), StringFormat.GenericTypographic); spaceSize = g.MeasureString("-", Font, new PointF(0, 0), StringFormat.GenericTypographic);
DrawLine(g, line, e.Bounds.Y, x); if (line != null) {
DrawLine(g, line, e.Bounds.Y, x);
}
} }
public override void ActivateItem() public override void ActivateItem()

2
src/Main/Core/Project/Src/AddInTree/AddIn/AddIn.cs

@ -23,7 +23,7 @@ namespace ICSharpCode.Core
return o; return o;
} }
} }
return null; throw new ArgumentException("Cannot create object: " + className);
} }
public List<Runtime> Runtimes { public List<Runtime> Runtimes {

119
src/Main/Core/Project/Src/Services/PropertyService/Properties.cs

@ -2,11 +2,31 @@ using System;
using System.IO; using System.IO;
using System.ComponentModel; using System.ComponentModel;
using System.Text; using System.Text;
using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Xml; using System.Xml;
namespace ICSharpCode.Core namespace ICSharpCode.Core
{ {
/// <summary>
/// This interface flags an object beeing "mementocapable". This means that the
/// state of the object could be saved to an <see cref="Properties"/> object
/// and set from a object from the same class.
/// This is used to save and restore the state of GUI objects.
/// </summary>
public interface IMementoCapable
{
/// <summary>
/// Creates a new memento from the state.
/// </summary>
Properties CreateMemento();
/// <summary>
/// Sets the state to the given memento.
/// </summary>
void SetMemento(Properties memento);
}
/// <summary> /// <summary>
/// Description of PropertyGroup. /// Description of PropertyGroup.
/// </summary> /// </summary>
@ -23,21 +43,6 @@ namespace ICSharpCode.Core
} }
} }
public T Get<T>(string property, T defaultValue)
{
if (!properties.ContainsKey(property)) {
properties.Add(property, defaultValue);
return defaultValue;
}
object o = properties[property];
if (o is System.String && typeof(T) != typeof(System.String)) {
TypeConverter c = TypeDescriptor.GetConverter(typeof(T));
return (T)c.ConvertFromInvariantString(o.ToString());
}
return (T)o;
}
public object Get(string property) public object Get(string property)
{ {
if (!properties.ContainsKey(property)) { if (!properties.ContainsKey(property)) {
@ -118,6 +123,9 @@ namespace ICSharpCode.Core
Properties p = new Properties(); Properties p = new Properties();
p.ReadProperties(reader, "Properties"); p.ReadProperties(reader, "Properties");
properties[propertyName] = p; properties[propertyName] = p;
} else if (propertyName == "Array") {
propertyName = reader.GetAttribute(0);
properties[propertyName] = ReadArray(reader);
} else { } else {
properties[propertyName] = reader.HasAttributes ? reader.GetAttribute(0) : null; properties[propertyName] = reader.HasAttributes ? reader.GetAttribute(0) : null;
} }
@ -126,23 +134,59 @@ namespace ICSharpCode.Core
} }
} }
ArrayList ReadArray(XmlTextReader reader)
{
ArrayList l = new ArrayList();
while (reader.Read()) {
switch (reader.NodeType) {
case XmlNodeType.EndElement:
if (reader.LocalName == "Array") {
return l;
}
break;
case XmlNodeType.Element:
l.Add(reader.HasAttributes ? reader.GetAttribute(0) : null);
break;
}
}
return l;
}
public void WriteProperties(XmlTextWriter writer) public void WriteProperties(XmlTextWriter writer)
{ {
foreach (KeyValuePair<string, object> entry in properties) { foreach (KeyValuePair<string, object> entry in properties) {
object val = entry.Value;
if (entry.Value is Properties) { if (val is Properties) {
writer.WriteStartElement("Properties"); writer.WriteStartElement("Properties");
writer.WriteAttributeString("name", entry.Key); writer.WriteAttributeString("name", entry.Key);
((Properties)entry.Value).WriteProperties(writer); ((Properties)val).WriteProperties(writer);
writer.WriteEndElement();
} else if (val is Array) {
writer.WriteStartElement("Array");
writer.WriteAttributeString("name", entry.Key);
foreach (object o in (Array)val) {
writer.WriteStartElement("Element");
WriteValue(writer, o);
writer.WriteEndElement();
}
writer.WriteEndElement();
} else {
writer.WriteStartElement(entry.Key);
WriteValue(writer, val);
writer.WriteEndElement(); writer.WriteEndElement();
continue;
} }
}
}
writer.WriteStartElement(entry.Key); void WriteValue(XmlTextWriter writer, object val)
if (entry.Value != null) { {
writer.WriteAttributeString("value", entry.Value.ToString()); if (val != null) {
if (val is string) {
writer.WriteAttributeString("value", val.ToString());
} else {
TypeConverter c = TypeDescriptor.GetConverter(val.GetType());
writer.WriteAttributeString("value", c.ConvertToInvariantString(val));
} }
writer.WriteEndElement();
} }
} }
@ -184,6 +228,35 @@ namespace ICSharpCode.Core
} }
return null; return null;
} }
public T Get<T>(string property, T defaultValue)
{
if (!properties.ContainsKey(property)) {
properties.Add(property, defaultValue);
return defaultValue;
}
object o = properties[property];
if (o is string && typeof(T) != typeof(string)) {
TypeConverter c = TypeDescriptor.GetConverter(typeof(T));
o = c.ConvertFromInvariantString(o.ToString());
properties[property] = o; // store for future look up
} else if (o is ArrayList && typeof(T).IsArray) {
ArrayList list = (ArrayList)o;
Type elementType = typeof(T).GetElementType();
Array arr = System.Array.CreateInstance(elementType, list.Count);
TypeConverter c = TypeDescriptor.GetConverter(elementType);
for (int i = 0; i < arr.Length; ++i) {
if (list[i] != null) {
arr.SetValue(c.ConvertFromInvariantString(list[i].ToString()), i);
}
}
o = arr;
properties[property] = o; // store for future look up
}
return (T)o;
}
protected virtual void OnPropertyChanged(PropertyChangedEventArgs e) protected virtual void OnPropertyChanged(PropertyChangedEventArgs e)
{ {
if (PropertyChanged != null) { if (PropertyChanged != null) {

Loading…
Cancel
Save