context: using System;
  using System.Data;
  using System.Windows.Forms;
  using System.Drawing;
  using LimnorUI;
  using System.Data.Common;
  using System.ComponentModel;
  using System.Drawing.Design;
  
  namespace LimnorDatabase
  {
  	/// <summary>
      /// Data source is provided by cmdSelection
  	/// </summary>
  	public class EPDataGrid : System.Windows.Forms.DataGrid
  	{
          public event System.EventHandler CurrentRowIndexChange = null;
          public event System.EventHandler RequeryFinished = null;
          //
          private EasyQuery _query;
          //
          private System.Windows.Forms.ComboBox[] cbx = null; //look ups including Yes/No
  		private System.Windows.Forms.Button[] bts=null; //datetime
          private int nCurrentRowIndex = -1;
          private int nCurrentCellColumn = -1;
          private System.Windows.Forms.Button btSave = null;
  
          private string sCurCaption = "";
          private bool bNewTable = false;
          private bool bNoEvents = false;
          private DataGridTableStyle myGridTableStyle = null;
          private bool bLoadingData = false;
          private bool pageLoaded = false;
  
  		private uint _lastTableClick = 0;
  		public EPDataGrid()
  		{
  			this.AllowSorting = false;
  			btSave = new System.Windows.Forms.Button();
  			btSave.Parent = this;
  			btSave.Width = 20;
  			btSave.Height = 20;
  			btSave.Top = 0;
              btSave.Image = Resource1.save; 
  			btSave.Left = this.Width - btSave.Width;
  			btSave.BackColor = System.Drawing.Color.FromArgb(255,236,233,216);
  			btSave.Click += new System.EventHandler(onSaveButtonClick);
  			//
  			this.Scroll += new EventHandler(EPDataGrid_Scroll);
  		}
          //public System.Data.OleDb.OleDbConnection GetOleDbConnection()
          //{
          //    if( daOle != null )
          //    {
          //        if( daOle.SelectCommand != null )
          //            return daOle.SelectCommand.Connection;
          //    }
  			
          //    return null;
          //}
  		public virtual bool ActAsVisible()
  		{
  			return true;
  		}
  		protected virtual string NullText
  		{
  			get
  			{
  				return "{null}";
  			}
  		}
          /// <summary>
          /// save changes by moving mouse to the last row and click
          /// </summary>
  		protected void moveMouseOff()
  		{
  			bool bOK = false;
  			if( _query != null )
  			{
                  if (_query.Tables.Count > 0)
  				{
      				bOK = true;
  				}
  			}
  			if( bOK )
  			{
  				try
  				{
                      //remember current position
  					Point curPoint = Cursor.Position;
                      //
  					Rectangle rc = GetCurrentCellBounds();
  					Point p2;
  					Point p = new Point(rc.X, rc.Y+rc.Height + 2);
  					p = PointToScreen(p);
  					p2 = new Point(rc.X, rc.Y + rc.Height + 2);
  					p2 = PointToScreen(p2);
  					//move to the next row
                      UIUtil.ClickMouse(p2.X, p2.Y);
  					Application.DoEvents();
  					Application.DoEvents();
                      UIUtil.ClickMouse(p2.X, p2.Y);
  					Application.DoEvents();
  					Application.DoEvents();
  					//move back
                      UIUtil.ClickMouse(p.X, p.Y);
  					Application.DoEvents();
  					Application.DoEvents();
                      UIUtil.ClickMouse(p.X, p.Y);
  					Application.DoEvents();
  					Application.DoEvents();
  					//move to original position
                      UIUtil.MoveMouse(curPoint.X, curPoint.Y);
  				}
  				catch
  				{
  				}
  			}
  		}
          /// <summary>
          /// save changes by moving mouse to the last row and click
          /// </summary>
  		protected void acceptByMouse()
  		{
  			if( !this.ReadOnly && ActAsVisible() )
  			{
  				moveMouseOff();
  				
  			}
  		}
  		public string DataTableName
  		{
  			get
  			{
                  if (_query != null && _query.Tables.Count > 0)
                  {
                      return _query.Tables[0].TableName;
                  }
                  return string.Empty;
  			}
  		}
  		public string CurrentColumnCaption
  		{
              get
              {
                  if (_query != null && _query.Tables.Count > 0)
                  {
                      if (_query.Tables[0] != null)
                      {
                          if (this.CurrentCell.ColumnNumber >= 0 && this.CurrentCell.ColumnNumber < _query.Tables[0].Columns.Count)
                          {
                              return _query.Tables[0].Columns[this.CurrentCell.ColumnNumber].Caption;
                          }
                      }
                  }
                  return string.Empty;
              }
  		}
  		public virtual void CloseConnections()
  		{
              if (_query != null)
              {
                  _query.CloseConnection();
              }
  		}
          //[Editor(typeof(QuerySelector), typeof(UITypeEditor))]
          [Description("The SQL query to get the data. The Query Builder helps you build SQL query.")]
          public EasyQuery Query
          {
              get
              {
                  return _query;
              }
              //set
              //{
              //    _query = value;
              //    QueryDatabase();
              //}
          }
          public virtual void QueryDatabase()
          {
              Requery();
          }
          protected bool daReady
          {
              get
              {
                  return (_query != null && _query.Adapter != null);
              }
          }
          [Description("Set a new query for the data table.")]
          public void SetQuery(EasyQuery query)
          {
              _query = query;
              QueryDatabase();
          }
          protected virtual void cancelChanges()
          {
              if (_query != null)
              {
                  Form frm = this.FindForm();
                  if (frm != null)
                  {
                      if (!frm.IsDisposed)
                      {
                          try
                          {
                              frm.BindingContext[_query, DataTableName].CancelCurrentEdit();
                          }
                          catch
                          {
                          }
                          Requery();
                      }
                  }
              }
          }
  		protected void onSaveButtonClick(object sender,System.EventArgs e)
  		{
              //for error log
              string sUpdate = "";
              string sInsert = "";
              string sDelete = "";
              try
              {
                  if (_query != null)
                  {
                      sDelete = _query.DeleteSql;
                      sInsert = _query.InsertSql;
                      sUpdate = _query.UpdateSql;
                      if (_query.Tables[0] != null)
                      {
                          int nCurrentRowIndex = this.CurrentRowIndex;
                          acceptByMouse();
                          Form frm = this.FindForm();
                          if (frm != null)
                          {
                              if (!frm.IsDisposed)
                              {
                                  frm.BindingContext[_query, DataTableName].EndCurrentEdit();
                                  if (_query.Update())
                                  {
                                      this.CurrentRowIndex = nCurrentRowIndex;
                                      Requery();
                                  }
                              }
                          }
                      }
                  }
              }
              catch (System.Data.DBConcurrencyException)
              {
                  RequeryAfterError();
              }
              catch (Exception er)
              {
                  FormLog.NotifyException(er, "Update command:{0}.\r\nInsert command:{1}.\r\nDelete command {2}", sUpdate, sInsert, sDelete);
                  RequeryAfterError();
              }
  		}
          protected void RequeryAfterError()
          {
              int n = nCurrentRowIndex;
              Requery();
              if (_query != null && _query.Tables.Count > 0)
              {
                  if (n >= 0 && n < _query.Tables[0].Rows.Count)
                  {
                      this.CurrentRowIndex = n;
                      nCurrentRowIndex = n;
                  }
              }
          }
  		protected virtual void onBeforeBind()
  		{
  		}
          protected virtual bool Requery()
          {
              if (bLoadingData)
                  return false;
              bLoadingData = true;
              int nCurrentRowIndex = this.CurrentRowIndex;
  
              this.DataBindings.Clear();
  
              if (_query != null)
              {
                  _query.RequerySelection();
  
                  if (_query.Tables.Count > 0)
                  {
                      bNewTable = (_query.Tables[0].Rows.Count == 0);
                      _query.Tables[0].RowDeleted += new DataRowChangeEventHandler(EPDataGrid_RowDeleted);
  
                      bindData();
                      if (nCurrentRowIndex >= 0 && nCurrentRowIndex < _query.Tables[0].Rows.Count)
                      {
                          this.CurrentRowIndex = nCurrentRowIndex;
                      }
                      onRowIndexChanged();
                      if (RequeryFinished != null)
                      {
                          RequeryFinished(this, EventArgs.Empty);
                      }
                      OnCurrentCellChanged(null);
                      _query.Tables[0].DefaultView.ListChanged += new ListChangedEventHandler(DefaultView_ListChanged);
                  }
              }
              bLoadingData = false;
              this.Invalidate();
              return (_query != null && _query.Tables.Count > 0);
          }
  		protected void bindData()
  		{
  			onBeforeBind();
  			bLoadingData = true;
              if (_query != null)
              {
                  this.DataSource = _query.Tables[0].DefaultView;
              }
  			bLoadingData = false;
  		}
  		public void BindData()
  		{
  			try
  			{
  				this.DataBindings.Clear();
                  if (_query != null)
  				{
                      if (_query.Tables.Count > 0)
  					{
                          if (_query.Tables[0] != null)
  						{
  							bindData();
  						}
  					}
  				}
  			}
  			catch(Exception er)
  			{
  				FormLog.NotifyException(er);
  			}
  		}
  		protected void setFieldEditor(int i)
  		{
  			if( _query == null )
  				return;
              if (i < 0 || i >= _query.Fields.Count)
  				return;
              if (_query.Fields[i].editor != null)
  			{
                  DataEditorButton bn = _query.Fields[i].editor as DataEditorButton;
  				if( bn != null )
  				{
  					bts[i] = bn.MakeButton(this.FindForm());
  					if( bts[i] != null )
  					{
  						bts[i].Parent = this;
  						bts[i].Visible = false;
                          _query.Fields[i].editor.OnPickValue += new fnOnPickValue(onPickValueByButton);
  					}
  				}
  				else
  				{
                      DataEditorLookupYesNo LK = _query.Fields[i].editor as DataEditorLookupYesNo;
  					if( LK != null )
  					{
  						cbx[i] = LK.MakeComboBox();
  						if( cbx[i] != null )
  						{
  							cbx[i].Parent = this;
  							cbx[i].Visible = false;
  							cbx[i].SelectedIndexChanged += new System.EventHandler(onLookupSelected);
  						}
  					}
  				}
  			}
  			else
  			{
  				cbx[i] = null;
  				bts[i] = null;
  			}
  		}
  		public virtual void ApplyStyle()
  		{
              //btSave.Visible = (!bReadOnly);
  			if( _query == null )
  				return;
              if (_query.Fields.Count == 0)
  				return;
  			int i;
              int n = _query.Fields.Count;
  			if( cbx != null )
  			{
  				for(i=0;i<cbx.Length;i++)
  				{
  					try
  					{
  						this.Controls.Remove(cbx[i]);
  					}
  					catch
  					{
  					}
  					cbx[i] = null;
  				}
  			}
  			if( bts != null )
  			{
  				for(i=0;i<bts.Length;i++)
  				{
  					try
  					{
  						this.Controls.Remove(bts[i]);
  					}
  					catch
  					{
  					}
  					bts[i] = null;
  				}
  			}
  			cbx = new System.Windows.Forms.ComboBox[n];
  			bts = new System.Windows.Forms.Button[n];
  			DataGridColumnStyle TextCol;
  			myGridTableStyle = new DataGridTableStyle();
  			myGridTableStyle.MappingName = DataTableName;
  			//			myGridTableStyle.AlternatingBackColor = System.Drawing.Color.LightPink;
  			//			int j=0;
  			
  			string cap;
              for (i = 0; i < _query.Fields.Count; i++)
  			{
                  if (ReadOnly || !EPField.IsBinary(_query.Fields[i].OleDbType))
  				{
                      if (_query.Fields[i].OleDbType == System.Data.OleDb.OleDbType.Boolean)
  					{
  						TextCol = new DataGridBoolColumn();
  					}
  					else
  					{
                          TextCol = new TextColumnStyle(_query.Fields[i].HeaderAlignment);// new DataGridTextBoxColumn();
  						//						((DataGridTextBoxColumn)TextCol).TextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
  						((DataGridTextBoxColumn)TextCol).TextBox.DoubleClick +=new EventHandler(TextBox_DoubleClick);
  						((DataGridTextBoxColumn)TextCol).TextBox.Click +=new EventHandler(TextBox_Click);
  						((DataGridTextBoxColumn)TextCol).TextBox.GotFocus +=new EventHandler(TextBox_GotFocus);
                          ((TextColumnStyle)TextCol).Format = _query.Fields[i].Format;
  						if(NullText != null)
  						{
  							((TextColumnStyle)TextCol).NullText = NullText;
  						}
  					}
  
  
gt:                     TextCol.MappingName = _query.Fields[i].Name;