我正在编写一个应用程序,在阅读并遵循许多示例后,我实现了一个基本的MVP模式。在简单的维护屏幕上,它工作得很好;但是在更复杂的屏幕上,模式并不是那么好。
这是一个带有接口的短代码块,以及通过LINQ获取一些数据的第一种方法。演示者都与模型分开,每个模型POCO都是通过EF-codefirst生成的。
public interface ILocnMastView
{
int LocnMastID { get; set; }
Int16 LocnSubTypeID { get; set; }
event EventHandler<EventArgs> FetchLocnMasts;
//Event to fire a 'fetch' of a row of data
event EventHandler<EventArgs> RefreshLocnMast;
}
public interface ILocnMastData : ILocnMastView
{
//Event to fire a record INSERT
event EventHandler<EventArgs> InsertLocnMast;
//Event to fire a record UPDATE
event EventHandler<EventArgs> UpdateLocnMast;
}
public class PresenterLocnMast
{
#region Member Variables
private ILocnMastView _viewfetch; //The view (form) instance that this presenter interface will use
private ILocnMastData _viewdata; //The view (form) instance that this inherited interface will use
private LOCNMast _obj = new LOCNMast(); //A single row of data to be returned out of this class
private List<LOCNMast> _data = null; //List of supplycodes to be returned out of this class
private List<LocnMastObject> _dataobject; //List of contacts joined to persontype table in a specialised class object
private string _message = string.Empty;
#endregion Member Variables
#region Member Properties
public string Message
{
get { return _message; }
set { _message = value; }
}
public LOCNMast Locnmast
{
get { return _obj; }
set { _obj = value; }
}
public List<LOCNMast> LocnMasts
{
get { return _data; }
set { _data = value; }
}
public List<LocnMastObject> LocnMastObjects
{
get { return _dataobject; }
set { _dataobject = value; }
}
#endregion Member Properties
#region Member Objects
public class LocnMastObject
{
public int ID { get; set; }
public string combinedtext { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public string LocationType { get; set; }
public string Warehouse { get; set; }
public string Category { get; set; }
public DateTime LastEditedDate { get; set; }
public string LastEditedBy { get; set; }
public Boolean Active { get; set; }
}
#endregion Member Objects
#region Init
public PresenterLocnMast(ILocnMastView viewfetch, ILocnMastData viewdata)
{
this._viewfetch = viewfetch;
this._viewdata = viewdata;
this.Initialise();
}
private void Initialise()
{
if (_viewdata != null)
{
this._viewdata.UpdateLocnMast += new EventHandler<EventArgs>(UpdateLocnMast);
this._viewdata.InsertLocnMast += new EventHandler<EventArgs>(InsertLocnMast);
}
this._viewfetch.FetchLocnMasts += new EventHandler<EventArgs>(FetchLocnMasts);
this._viewfetch.RefreshLocnMast += new EventHandler<EventArgs>(RefreshLocnMast);
}
#endregion Init
#region Methods
/// <summary>
/// Routine: FetchLocnMasts
/// Purpose: Event to Fetch all details from the database by locnsubtype
/// Author: Frustrated Winforms Developer
/// Date: 13/11/2015
/// </summary>
private void FetchLocnMasts(object sender, EventArgs e)
{
try
{
using (var db = new DevDBContext())
var queryforobject = from l in db.LOCNMasts.AsNoTracking()
join t in db.LocnTypes.AsNoTracking() on l.LocationTypeID equals t.ID
join w in db.WHMasts.AsNoTracking() on l.WarehouseID equals w.ID
join c in db.LocnCategoryTypes.AsNoTracking() on l.LocationCategoryTypeID.Value equals c.ID into pp
from LocationCategoryTypeID in pp.DefaultIfEmpty()
orderby l.Name
//Put the query results into the bespoke object
select new LocnMastObject { ID = l.ID,
Name = l.Name,
Description = l.Description,
combinedtext = l.Name + " - " + l.Description,
LocationType = t.Description,
Warehouse = w.Description,
Category = LocationCategoryTypeID.Name,
LastEditedBy = l.LastEditedBy,
LastEditedDate = l.LastEditedDate,
Active = l.Active };
if (queryforobject.Count() > 0)
_dataobject = queryforobject.ToList();
}
}
catch (Exception ex)
{
//HandleError
}
}
所以,一切都好。 在表单上,我必须实现接口,为关键字段设置私有成员变量和属性,创建演示者类的实例并创建事件以匹配接口中定义的事件。
因此,在必须从6个演示者类中提取数据的表单上,代码是最重要的,具有多个实现,每个表的mutli ID属性等等。在复杂的形式上,该方法与传统的OOP方法相比没有任何重大优势。
关于如何解决这个问题的任何想法?我的相关表的另一个类继承了必要的演示者吗?
表单上的代码(注意三个接口实现):
public partial class frmConfigLocation : Telerik.WinControls.UI.RadForm, IWHMastView, ILocnCategoryTypeView, ILocnMastData
#region Member Variables
private Int16 _locationcategorytypeid = -1;
private Int16 _whmastid = -1;
private int _locnmastid = -1;
private Int16 _locnsubtypeid = -1;
private PresenterWHMast _presenterwhmast;
private PresenterLocnCategoryType _presenterlocncategorytype;
private PresenterLocnMast _presenterlocnmast;
#endregion Member Variables
#region Member Events
public event EventHandler<EventArgs> FetchLocnCategoryTypes;
public event EventHandler<EventArgs> RefreshLocnCategoryType;
public event EventHandler<EventArgs> FetchWHMasts;
public event EventHandler<EventArgs> RefreshWHMast;
public event EventHandler<EventArgs> FetchLocnMasts;
public event EventHandler<EventArgs> RefreshLocnMast;
public event EventHandler<EventArgs> UpdateLocnMast;
public event EventHandler<EventArgs> InsertLocnMast;
#endregion Member Events
public Int16 LocnCategoryTypeID
{
get { return _locationcategorytypeid; }
set { _locationcategorytypeid = LocnCategoryTypeID; }
}
public Int16 WHMastID
{
get { return _whmastid; }
set { _whmastid = WHMastID; }
}
public int LocnMastID
{
get { return _locnmastid; }
set { _locnmastid = LocnMastID; }
}
#endregion Member Properties
#region FormMethods
public frmConfigLocation()
{
this.FormClosed += new FormClosedEventHandler(frmLocation_FormClosed);
InitializeComponent();
_presenterlocnmast = new PresenterLocnMast(this, this);
_presenterlocncategorytype = new PresenterLocnCategoryType(this, null);
_presenterwhmast = new PresenterWHMast(this, null);
}
所以,毕竟,填充radGrid的例程很简单
private void FetchData([Optional] Boolean postsave)
{
try
{
this.Cursor = Cursors.WaitCursor;
if (FetchLocnMasts != null)
{
FetchLocnMasts(this, EventArgs.Empty);
radGridViewLocnAll.DataSource = _presenterlocnmast.LocnMastObjects;
//Hide the ID column of the radgrid
GlobalControlMethods.radGridViewColumnVisible(radGridViewLocnAll, 0, false);
radGridViewLocnAll.CurrentRow = null;
}
正如您所看到的,尽管获取数据非常简单,但仍需要很多代码来设置所有内容。我必须遗漏一些东西才能使表格背后的代码少得多,这一点肯定是肯定的?
很抱歉很长的帖子,欢迎所有反馈!