我在Web信息中心上动态添加和重新创建控件。我一直试图减少我对Page.FindControl的使用;我发现在页面上有大量动态创建的内容会很慢。
在我的尝试中,我创建了一个RegenerationManager单例,现在负责重新生成我的动态内容。每当它重新生成一个对象时,它就会将该对象存储在一个列表中。该管理器根据对象类型保留其中几个列表。
稍后,当我需要通过ID获取对象时,我会转到我的再生管理器来检索该对象。
E.G:
public class RegenerationManager
{
private static readonly ILog Logger = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
private static readonly RegenerationManager instance = new RegenerationManager();
private RegenerationManager() { }
public static RegenerationManager Instance
{
get { return instance; }
}
public List<CormantRadPane> RegeneratedPanes = new List<CormantRadPane>();
public List<CormantRadDockZone> RegeneratedDockZones = new List<CormantRadDockZone>();
/// <summary>
/// Recreates all the dynamically made DockZones.
/// </summary>
public void RegenerateDockZones()
{
Logger.Info("Regenerating dock zones.");
foreach (KeyValuePair<string, RadDockZoneSetting> dockZoneState in RadControlManager.GetStates<SerializableDictionary<string, RadDockZoneSetting>>())
{
try
{
RadDockZoneSetting dockZoneSetting = dockZoneState.Value as RadDockZoneSetting;
Logger.Info(String.Format("Loading state data for dock zone with setting ID: {0}", dockZoneSetting.ID));
CormantRadDockZone dockZone = new CormantRadDockZone(dockZoneSetting);
RegeneratedDockZones.Add(dockZone);
CormantRadPane pane = RegeneratedPanes.First(regeneratedPane => regeneratedPane.ID == dockZoneSetting.ParentID);
pane.Controls.Add(dockZone);
}
catch (Exception exception)
{
Logger.ErrorFormat("Error regenerating dock zones. Reason: {0}", exception.Message);
}
}
}
}
/// <summary>
/// Creates the RadDock + Contents when dropping a graph onto the page.
/// </summary>
/// <param name="sender"> The RadListBox with an element being dropped from inside it. </param>
/// <param name="e"> Information about the drop such as target and what is being dropped. </param>
protected void RadListBox_Dropped(object sender, RadListBoxDroppedEventArgs e)
{
CormantRadDockZone dockZoneOld = Utilities.FindControlRecursive(Page, e.HtmlElementID) as CormantRadDockZone;
CormantRadDockZone dockZone = RegenerationManager.Instance.RegeneratedDockZones.First(regeneratedDockZone => regeneratedDockZone.ID == e.HtmlElementID);
if (!object.Equals(dockZone, null) && !dockZone.Docks.Any())
{
RadSlidingPane slidingPane = ((sender as RadListBox).Parent as RadSlidingPane);
CormantReport report = new CormantReport(int.Parse(e.SourceDragItems[0].Value), e.SourceDragItems[0].Text, slidingPane.Title);
CormantRadDock dock = new CormantRadDock(report);
dock.CreateContent();
dockZone.Controls.Add(dock);
}
}
现在,我认为这是一个非常好的解决方案,但经过测试,我发现添加到dockZone的CormantRadDock没有显示在我的网络仪表板上,但是如果我将它添加到dockZoneOld那就是它。
看看这两个对象,我没有注意到这两个对象有什么不同,但显然有一些东西。
我的想法是否可以实施?
编辑:我怀疑问题出在Telerik的控件上。我有个想法,我会稍微报告一下。 编辑:这确实是一个Telerik的事情。我需要浏览他们的RadDockLayout.RegisteredDockZone列表,而不是保留我自己的托管列表。答案 0 :(得分:0)
这里要做的关键是调试你的代码并在这一行上设置一个断点:
CormantRadDockZone dockZone = RegenerationManager.Instance.RegeneratedDockZones.First(regeneratedDockZone =>regeneratedDockZone.ID == e.HtmlElementID);`
然后对RegenerationManager.Instance.RegeneratedDockZones
的内容进行快速监视,看看该列表中是否包含任何元素。所以我们在这里检查基础知识 - 列表中是否包含任何项目?
如果有项目,你需要弄清楚为什么你要查找的特定元素不在列表中。该列表必须正常工作,因为其中有项目,但尚未添加此特定元素。
如果您100%将元素添加到列表中,那么它可能与您使用的单例模式有关。老实说,它看起来不错,但我不是单身设计模式的专家。
抱歉,我无法提供更多帮助。
编辑:
可能有所帮助的一点是重构一下课程:
private IList<CormantRadPane> _regeneratedPanes;
private IList<CormantRadDockZone> _regeneratedDockZones;
public IList<CormantRadPane> RegeneratedPanes
{
get
{
if(_regeneratedPanes == null)
{
_regeneratedPanes = new List<CormantRadPane>()
}
return _regeneratedPanes
}
}
public IList<CormantRadDockZone> RegeneratedDockZones
{
get
{
if(_regeneratedDockZones == null)
{
_regeneratedDockZones = new List<CormantRadDockZone>()
}
return _regeneratedDockZones
}
}
这里我使用属性返回列表,而不是让人们直接访问列表成员。
这可以帮助您调试代码。