Browse Source

Added patch by Christian Hornung. DesignerResourceService now complies with the SDK documentation and serves resource readers/writers at any time in any order. Localised resources now saved correctly.

git-svn-id: svn://svn.sharpdevelop.net/sharpdevelop/trunk@757 1ccf3a8d-04fe-1044-b7c0-cef0b8235c61
shortcuts
Matt Ward 20 years ago
parent
commit
f779d51cd1
  1. 7
      src/AddIns/DisplayBindings/FormDesigner/Project/Src/FormDesigner/FormDesignerViewContent.cs
  2. 178
      src/AddIns/DisplayBindings/FormDesigner/Project/Src/FormDesigner/Services/DesignerResourceService.cs

7
src/AddIns/DisplayBindings/FormDesigner/Project/Src/FormDesigner/FormDesignerViewContent.cs

@ -50,8 +50,7 @@ namespace ICSharpCode.FormDesigner
protected bool failedDesignerInitialize; protected bool failedDesignerInitialize;
protected IViewContent viewContent; protected IViewContent viewContent;
protected Hashtable resources = new Hashtable(); protected Dictionary<string, DesignerResourceService.ResourceStorage> resources = new Dictionary<string, DesignerResourceService.ResourceStorage>();
protected ITextEditorControlProvider textAreaControlProvider; protected ITextEditorControlProvider textAreaControlProvider;
Panel p = new Panel(); Panel p = new Panel();
@ -60,7 +59,7 @@ namespace ICSharpCode.FormDesigner
IDesignerLoaderProvider loaderProvider; IDesignerLoaderProvider loaderProvider;
IDesignerGenerator generator; IDesignerGenerator generator;
DesignerResourceService designerResourceService; DesignerResourceService designerResourceService;
public override Control Control { public override Control Control {
get { get {
return p; return p;
@ -221,9 +220,7 @@ namespace ICSharpCode.FormDesigner
} }
bool isDirty = viewContent.IsDirty; bool isDirty = viewContent.IsDirty;
LoggingService.Info("Merging form changes..."); LoggingService.Info("Merging form changes...");
designerResourceService.SerializationStarted(true);
designSurface.Flush(); designSurface.Flush();
designerResourceService.SerializationEnded(true);
LoggingService.Info("Finished merging form changes"); LoggingService.Info("Finished merging form changes");
viewContent.IsDirty = isDirty; viewContent.IsDirty = isDirty;
} }

178
src/AddIns/DisplayBindings/FormDesigner/Project/Src/FormDesigner/Services/DesignerResourceService.cs

@ -9,6 +9,8 @@ using System;
using System.Drawing; using System.Drawing;
using System.IO; using System.IO;
using System.Collections; using System.Collections;
using System.Collections.Generic;
using System.Globalization;
using System.Resources; using System.Resources;
using System.Text; using System.Text;
using System.Collections.Specialized; using System.Collections.Specialized;
@ -26,40 +28,101 @@ namespace ICSharpCode.FormDesigner.Services
IDesignerHost host; IDesignerHost host;
public string FileName = String.Empty; public string FileName = String.Empty;
public string NameSpace = String.Empty;
public string RootType = String.Empty;
protected IProject project; protected IProject project;
protected Hashtable Writers = new Hashtable();
#region ResourceStorage #region ResourceStorage
public class ResourceStorage public class ResourceStorage
{ {
public MemoryStream stream = null; MemoryStream stream;
public byte[] storage = null; IResourceWriter writer;
public IProject project = null; public IProject project = null;
string fileName;
byte[] buffer;
public ResourceStorage(MemoryStream stream) /// <summary>
{ /// true, if the currently stored resource is not empty.
this.stream = stream; /// Note that this property is only valid after at least one
/// of GetReader, GetWriter or Save has been called.
/// </summary>
public bool ContainsData {
get {
return this.buffer != null;
}
} }
public ResourceStorage(ResourceStorage rs) public ResourceStorage(string fileName, IProject project)
{ {
this.storage = (byte []) rs.storage.Clone(); this.project = project;
this.stream = new MemoryStream(this.storage); this.fileName = fileName;
} }
public void Dispose() public void Dispose()
{ {
this.storage = null; if (this.stream != null) {
this.stream.Close(); this.writer.Dispose();
this.stream.Dispose();
}
this.buffer = null;
}
/// <summary>
/// Writes the byte array containing the most recent version of the resource
/// represented by this instance into the private field "buffer" and returns it.
/// Returns null, if this resource has not been written to yet.
/// </summary>
byte[] GetBuffer()
{
if (this.stream != null) {
byte[] buffer = this.stream.ToArray();
if (buffer.Length > 0) {
this.writer.Close();
this.writer.Dispose();
this.buffer = this.stream.ToArray();
this.writer = null;
this.stream.Dispose();
this.stream = null;
}
}
return this.buffer;
}
/// <summary>
/// Returns a new resource reader for this resource based on the most recent
/// version available (either in memory or on disk).
/// </summary>
public IResourceReader GetReader()
{
if (this.GetBuffer() == null) {
if (File.Exists(this.fileName)) {
return CreateResourceReader(this.fileName, GetResourceType(this.fileName));
} else {
return null;
}
} else {
return CreateResourceReader(new MemoryStream(this.buffer, false), GetResourceType(this.fileName));
}
}
/// <summary>
/// Returns a new resource writer for this resource.
/// According to the SDK documentation of IResourceService.GetResourceWriter,
/// a new writer needs to be returned every time one is requested, discarding any
/// data written by previously returned writers.
/// </summary>
public IResourceWriter GetWriter()
{
this.stream = new MemoryStream();
this.writer = CreateResourceWriter(this.stream, GetResourceType(this.fileName));
return this.writer;
} }
public void Save(string fileName) public void Save(string fileName)
{ {
File.WriteAllBytes(fileName, storage); if (this.GetBuffer() != null) {
File.WriteAllBytes(fileName, this.buffer);
}
} }
} }
#endregion #endregion
@ -78,8 +141,8 @@ namespace ICSharpCode.FormDesigner.Services
// Memory streams are cleared, when WriteSerialization will start // Memory streams are cleared, when WriteSerialization will start
// or File in the editor will be reloaded from the disc and of // or File in the editor will be reloaded from the disc and of
// course in Dispose of the service // course in Dispose of the service
protected Hashtable resources = null; protected Dictionary<string, ResourceStorage> resources = null;
public Hashtable Resources public Dictionary<string, ResourceStorage> Resources
{ {
get { get {
return resources; return resources;
@ -97,7 +160,7 @@ namespace ICSharpCode.FormDesigner.Services
} }
} }
public DesignerResourceService(Hashtable resources) public DesignerResourceService(Dictionary<string, ResourceStorage> resources)
{ {
project = ProjectService.CurrentProject; project = ProjectService.CurrentProject;
this.resources = resources; this.resources = resources;
@ -107,16 +170,15 @@ namespace ICSharpCode.FormDesigner.Services
public System.Resources.IResourceWriter GetResourceWriter(System.Globalization.CultureInfo info) public System.Resources.IResourceWriter GetResourceWriter(System.Globalization.CultureInfo info)
{ {
try { try {
IResourceWriter resourceWriter = (IResourceWriter)Writers[info]; LoggingService.Debug("ResourceWriter requested for culture: "+info.ToString());
string fileName = CalcResourceFileName(info); string fileName = CalcResourceFileName(info);
if (resourceWriter == null) { ResourceStorage resourceStorage;
ResourceStorage resourceStorage = new ResourceStorage(new MemoryStream()); if (resources.ContainsKey(fileName)) {
resources[fileName] = resourceStorage; resourceStorage = resources[fileName];
resourceWriter = CreateResourceWriter(resourceStorage.stream, GetResourceType(fileName)); } else {
Writers[info] = resourceWriter; resourceStorage = new ResourceStorage(fileName, project); resources[fileName] = resourceStorage;
resourceStorage.project = project;
} }
return resourceWriter; return resourceStorage.GetWriter();
} catch (Exception e) { } catch (Exception e) {
MessageService.ShowError(e); MessageService.ShowError(e);
return null; return null;
@ -126,16 +188,16 @@ namespace ICSharpCode.FormDesigner.Services
public System.Resources.IResourceReader GetResourceReader(System.Globalization.CultureInfo info) public System.Resources.IResourceReader GetResourceReader(System.Globalization.CultureInfo info)
{ {
try { try {
LoggingService.Debug("ResourceReader requested for culture: "+info.ToString());
string fileName = CalcResourceFileName(info); string fileName = CalcResourceFileName(info);
IResourceReader resourceReader = null; ResourceStorage resourceStorage;
if (resources != null && resources[fileName] != null) { if (resources != null && resources.ContainsKey(fileName)) {
MemoryStream stream = new MemoryStream(((ResourceStorage)resources[fileName]).storage); resourceStorage = resources[fileName];
resourceReader = CreateResourceReader(stream, GetResourceType(fileName)); } else {
} else if (File.Exists(fileName)) { resourceStorage = new ResourceStorage(fileName, project);
resourceReader = CreateResourceReader(fileName, GetResourceType(fileName)); resources[fileName] = resourceStorage;
} }
return resourceStorage.GetReader();
return resourceReader;
} catch (Exception e) { } catch (Exception e) {
MessageService.ShowError(e); MessageService.ShowError(e);
return null; return null;
@ -146,12 +208,12 @@ namespace ICSharpCode.FormDesigner.Services
public void Save() public void Save()
{ {
if (resources != null) { if (resources != null) {
foreach (DictionaryEntry entry in resources) { foreach (KeyValuePair<string, ResourceStorage> entry in resources) {
string resourceFileName = (string)entry.Key; string resourceFileName = entry.Key;
FileUtility.ObservedSave(new NamedFileOperationDelegate(((ResourceStorage)entry.Value).Save), resourceFileName, FileErrorPolicy.Inform); FileUtility.ObservedSave(new NamedFileOperationDelegate(entry.Value.Save), resourceFileName, FileErrorPolicy.Inform);
// Add this resource file to the project // Add this resource file to the project
if (project != null && !project.IsFileInProject(resourceFileName)) { if (entry.Value.ContainsData && project != null && !project.IsFileInProject(resourceFileName)) {
PadDescriptor pd = WorkbenchSingleton.Workbench.GetPad(typeof(ProjectBrowserPad)); PadDescriptor pd = WorkbenchSingleton.Workbench.GetPad(typeof(ProjectBrowserPad));
FileNode formFileNode = ((ProjectBrowserPad)pd.PadContent).ProjectBrowserControl.FindFileNode(FileName); FileNode formFileNode = ((ProjectBrowserPad)pd.PadContent).ProjectBrowserControl.FindFileNode(FileName);
if (formFileNode != null) { if (formFileNode != null) {
@ -197,43 +259,6 @@ namespace ICSharpCode.FormDesigner.Services
return resourceFileName.ToString(); return resourceFileName.ToString();
} }
public void SerializationStarted(bool serialize)
{
if (serialize == true) {
if (resources == null) {
resources = new Hashtable();
}
foreach (ResourceStorage storage in resources.Values) {
storage.storage = null;
storage.stream.Close();
}
resources.Clear();
} else {
if (resources != null) {
foreach (ResourceStorage storage in resources.Values) {
storage.stream = new MemoryStream(storage.storage);
}
}
}
}
public void SerializationEnded(bool serialize)
{
foreach (IResourceWriter resourceWriter in Writers.Values) {
if (resourceWriter != null) {
resourceWriter.Close();
resourceWriter.Dispose();
}
}
Writers.Clear();
if (serialize == true && resources != null) {
foreach (ResourceStorage storage in Resources.Values) {
storage.storage = storage.stream.ToArray();
}
}
}
public void Dispose() public void Dispose()
{ {
@ -243,7 +268,6 @@ namespace ICSharpCode.FormDesigner.Services
} }
resources.Clear(); resources.Clear();
} }
SerializationEnded(false);
} }
static ResourceType GetResourceType(string fileName) static ResourceType GetResourceType(string fileName)

Loading…
Cancel
Save