using FastReport.Table; using FastReport.Utils; using System; using System.Collections; using System.Collections.Generic; namespace FastReport.Preview { internal class Dictionary { private SortedList names; //private SortedDictionary FNames; private Hashtable baseNames; private PreparedPages preparedPages; private void AddBaseName(string name) { for (int i = 0; i < name.Length; i++) { if (name[i] >= '0' && name[i] <= '9') { string baseName = name.Substring(0, i); int num = int.Parse(name.Substring(i)); if (baseNames.ContainsKey(baseName)) { int maxNum = (int)baseNames[baseName]; if (num < maxNum) num = maxNum; } baseNames[baseName] = num; return; } } } public string CreateUniqueName(string baseName) { int num = 1; if (baseNames.ContainsKey(baseName)) num = (int)baseNames[baseName] + 1; baseNames[baseName] = num; return baseName + num.ToString(); } private void Add(string name, string sourceName, Base obj) { names.Add(name, new DictionaryItem(sourceName, obj)); } public string AddUnique(string baseName, string sourceName, Base obj) { string result = CreateUniqueName(baseName); Add(result, sourceName, obj); return result; } public Base GetObject(string name) { DictionaryItem item; if (names.TryGetValue(name, out item)) { // return item.CloneObject(name); if (item.OriginalComponent != null) item.OriginalComponent.SetReport(this.preparedPages.Report); Base result = item.CloneObject(name); //result.SetReport(this); return result; } else return null; //int i = FNames.IndexOfKey(name); //if (i == -1) // return null; //return FNames.Values[i].CloneObject(name); } public Base GetOriginalObject(string name) { DictionaryItem item; if (names.TryGetValue(name, out item)) return item.OriginalComponent; else return null; // int i = FNames.IndexOfKey(name); //if (i == -1) // return null; //return FNames.Values[i].OriginalComponent; } public void Clear() { names.Clear(); baseNames.Clear(); } public void Save(XmlItem rootItem) { rootItem.Clear(); foreach (KeyValuePair pair in names) { XmlItem xi = rootItem.Add(); xi.Name = pair.Key; xi.ClearProps(); xi.SetProp("name", pair.Value.SourceName); //xi.Text = String.Concat("name=\"", pair.Value.SourceName, "\""); } //for (int i = 0; i < FNames.Count; i++) //{ // XmlItem xi = rootItem.Add(); // xi.Name = FNames.Keys[i]; // xi.Text = "name=\"" + FNames.Values[i].SourceName + "\""; //} } public void Load(XmlItem rootItem) { Clear(); for (int i = 0; i < rootItem.Count; i++) { // rootItem[i].Name is 's1', rootItem[i].Text is 'name="Page0.Shape1"' string sourceName = rootItem[i].GetProp("name"); // split to Page0, Shape1 string[] objName = sourceName.Split('.'); // get page number int pageN = int.Parse(objName[0].Substring(4)); // get the object Base obj = null; if (objName.Length == 2) obj = preparedPages.SourcePages[pageN].FindObject(objName[1]); else obj = preparedPages.SourcePages[pageN]; // add s1, Page0.Shape1, object string name = rootItem[i].Name; Add(name, sourceName, obj); AddBaseName(name); } } public Dictionary(PreparedPages preparedPages) { this.preparedPages = preparedPages; names = new SortedList(); //FNames = new SortedDictionary(); baseNames = new Hashtable(); } private sealed class DictionaryItem { private readonly string sourceName; private readonly Base originalComponent; public string SourceName { get { return sourceName; } } public Base OriginalComponent { get { return originalComponent; } } public Base CloneObject(string alias) { Base result = null; Type type = originalComponent.GetType(); // try frequently used objects first. The CreateInstance method is very slow. if (type == typeof(TextObject)) result = new TextObject(); else if (type == typeof(TableCell)) result = new TableCell(); else if (type == typeof(DataBand)) result = new DataBand(); else result = Activator.CreateInstance(type) as Base; result.Assign(originalComponent); result.OriginalComponent = originalComponent; result.Alias = alias; result.SetName(originalComponent.Name); if (result is ReportComponentBase) (result as ReportComponentBase).AssignPreviewEvents(originalComponent); return result; } public DictionaryItem(string name, Base obj) { sourceName = name; originalComponent = obj; } } } }