Imports System.ComponentModel Imports System.Text.RegularExpressions Imports DD_LIB_Standards Imports DevExpress.Utils Imports DevExpress.XtraEditors Imports DevExpress.XtraEditors.Controls Imports DevExpress.XtraEditors.NavigatorButtons Imports DevExpress.XtraEditors.Repository Imports DevExpress.XtraGrid Imports DevExpress.XtraGrid.Columns Imports DevExpress.XtraGrid.Views.Base Imports DevExpress.XtraGrid.Views.Grid Imports DigitalData.Controls.LookupGrid Imports DigitalData.Modules.Language.Utils Imports DigitalData.GUIs.Common Imports DigitalData.Modules.Logging Imports DigitalData.Modules.EDMI.API.DatabaseWithFallback Imports DigitalData.Modules.EDMI.API.Constants Imports DigitalData.Modules.Language.DataTableEx Public Class ClassControlCreator ''' ''' Konstanten ''' Private Const DEFAULT_TEXT = "Bezeichnung definieren" Private Const DEFAULT_FONT_SIZE As Integer = 10 Private Const DEFAULT_FONT_FAMILY As String = "Arial" Private Const DEFAULT_FONT_STYLE As FontStyle = FontStyle.Regular Private Const DEFAULT_COLOR As Integer = 0 Private Const DEFAULT_WIDTH As Integer = 170 Private Const DEFAULT_HEIGHT As Integer = 20 Private Const DEFAULT_HEIGHT_TABLE As Integer = 150 Public Const PREFIX_TEXTBOX = "TXT" Public Const PREFIX_LABEL = "LBL" Public Const PREFIX_CHECKBOX = "CHK" Public Const PREFIX_COMBOBOX = "CMB" Public Const PREFIX_DATETIMEPICKER = "DTP" Public Const PREFIX_DATAGRIDVIEW = "DGV" Public Const PREFIX_LOOKUP = "LU" Public Const PREFIX_TABLE = "TB" Public Const PREFIX_LINE = "LINE" Public Const PREFIX_BUTTON = "BTN" Public Const AGGREGATE_NONE = "NONE" Public Const AGGREGATE_TOTAL_INTEGER = "TOTAL_INTEGER" Public Const AGGREGATE_TOTAL_FLOAT = "TOTAL_FLOAT" Public Const AGGREGATE_TOTAL_MIN = "TOTAL_MIN" Public Const AGGREGATE_TOTAL_MAX = "TOTAL_MAX" Public Const AGGREGATE_TOTAL_AVG = "TOTAL_AVG" Public Const AGGREGATE_TOTAL_COUNT = "TOTAL_COUNT" Public Shared Property Logger As Logger ''' ''' Saves the column data for each grid and each column in that grid ''' Public Shared Property GridTables As New Dictionary(Of Integer, Dictionary(Of String, RepositoryItem)) Public Shared Property GridColumns As New Dictionary(Of Integer, DataTable) ''' ''' Standard Eigenschaften für alle Controls ''' Private Class ControlDBProps Public Guid As Integer Public Name As String Public Location As Point Public [Font] As Font Public [Color] As Color Public [ReadOnly] As Boolean End Class Public Class ControlMetadata Public Guid As Integer Public Name As String Public [ReadOnly] As Boolean = False End Class Private Shared Function TransformDataRow(row As DataRow) As ControlDBProps Dim x As Integer = row.Item("X_LOC") Dim y As Integer = row.Item("Y_LOC") Dim style As FontStyle = NotNull(row.Item("FONT_STYLE"), DEFAULT_FONT_STYLE) Dim size As Single = NotNull(row.Item("FONT_SIZE"), DEFAULT_FONT_SIZE) Dim familyString As String = NotNull(row.Item("FONT_FAMILY"), DEFAULT_FONT_FAMILY) Dim family As FontFamily = New FontFamily(familyString) Dim oGuid As Integer = row.Item("GUID") Dim oName As String = row.Item("NAME") Dim oLocation As New Point(x, y) Dim oFont As New Font(family, size, style, GraphicsUnit.Point) Dim oColor As Color = IntToColor(NotNull(row.Item("FONT_COLOR"), DEFAULT_COLOR)) Dim oReadOnly As Boolean = row.Item("READ_ONLY") Return New ControlDBProps() With { .Guid = oGuid, .Name = oName, .Location = oLocation, .Font = oFont, .Color = oColor, .ReadOnly = oReadOnly } End Function Public Shared Function CreateBaseControl(ctrl As Control, OControlRow As DataRow, designMode As Boolean) As Control Try Dim props As ControlDBProps = TransformDataRow(OControlRow) ctrl.Tag = New ControlMetadata() With { .Guid = props.Guid, .ReadOnly = props.ReadOnly, .Name = props.Name } ctrl.Name = props.Name ctrl.Location = props.Location ctrl.Font = props.Font ctrl.ForeColor = props.Color If designMode Then ctrl.Cursor = Cursors.Hand End If If props.ReadOnly Then ctrl.BackColor = Color.LightGray End If Return ctrl Catch ex As Exception Logger.Error(ex) Return Nothing End Try End Function ' ----------------------- NEW CONTROLS ----------------------- Public Shared Function CreateNewTextBox(location As Point) As TextBox Dim control As New TextBox With { .Name = $"{PREFIX_TEXTBOX}_{clsTools.ShortGuid()}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT), .Location = location, .ReadOnly = True, .BackColor = Color.White, .Cursor = Cursors.Hand } Return control End Function Public Shared Function CreateNewLabel(location As Point) As Label Dim control As New Label With { .Name = $"{PREFIX_LABEL}_{clsTools.ShortGuid}", .Text = DEFAULT_TEXT, .AutoSize = True, .Location = location, .Cursor = Cursors.Hand } Return control End Function Public Shared Function CreateNewCheckbox(location As Point) As CheckBox Dim control As New CheckBox With { .Name = $"{PREFIX_CHECKBOX}_{clsTools.ShortGuid}", .AutoSize = True, .Text = DEFAULT_TEXT, .Cursor = Cursors.Hand, .Location = location, .CheckState = CheckState.Indeterminate } Return control End Function Public Shared Function CreateNewCombobox(location As Point) As ComboBox Dim control As New ComboBox With { .Name = $"{PREFIX_COMBOBOX}_{clsTools.ShortGuid}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT), .Cursor = Cursors.Hand, .Location = location } Return control End Function Public Shared Function CreateNewDatetimepicker(location As Point) As DateTimePicker Dim control As New DateTimePicker With { .Name = $"{PREFIX_DATETIMEPICKER}_{clsTools.ShortGuid}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT), .Cursor = Cursors.Hand, .Location = location, .Format = DateTimePickerFormat.Short } Return control End Function Public Shared Function CreateNewDatagridview(location As Point) As DataGridView Dim control As New DataGridView With { .Name = $"{PREFIX_DATAGRIDVIEW}_{clsTools.ShortGuid}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT_TABLE), .Cursor = Cursors.Hand, .Location = location, .AllowUserToAddRows = False, .AllowUserToDeleteRows = False, .AllowUserToResizeColumns = False, .AllowUserToResizeRows = False } control.Columns.Add(New DataGridViewTextBoxColumn With { .HeaderText = "", .Name = "column1" }) Return control End Function Friend Shared Function CreateNewLookupControl(location As Point) As LookupControl3 Dim control As New LookupControl3 With { .Name = $"{PREFIX_LOOKUP}_{clsTools.ShortGuid}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT), .Cursor = Cursors.Hand, .Location = location } Return control End Function Public Shared Function CreateNewTable(location As Point) As GridControl Dim oControl As New GridControl With { .Name = $"{PREFIX_TABLE}_{clsTools.ShortGuid}", .Size = New Size(DEFAULT_WIDTH, DEFAULT_HEIGHT_TABLE), .Cursor = Cursors.Hand, .Location = location } oControl.UseEmbeddedNavigator = True oControl.ForceInitialize() Dim oView As GridView = oControl.DefaultView oView.OptionsView.ShowGroupPanel = False Dim oDatatable As New DataTable() oDatatable.Columns.Add("column1", GetType(String)) oDatatable.Columns.Add("column2", GetType(String)) oControl.DataSource = oDatatable Return oControl End Function Public Shared Function CreateNewLine(location As Point) As LineLabel Dim control As New LineLabel With { .Name = $"{PREFIX_LINE}_{clsTools.ShortGuid}", .Text = "---------------------------------", .Size = New Size(100, 5), .Location = location } Return control End Function Public Shared Function CreateNewButton(location As Point) As Button Dim control As New Button With { .Name = $"{PREFIX_BUTTON}_{clsTools.ShortGuid}", .Size = New Size(108, 28), .Cursor = Cursors.Hand, .Location = location } Return control End Function ' ----------------------- EXISITING CONTROLS ----------------------- Public Shared Function CreateExistingTextbox(oControlRow As DataRow, designMode As Boolean) As TextBox Try Dim control As TextBox = CreateBaseControl(New TextBox(), oControlRow, designMode) control.BackColor = Color.White If oControlRow.Item("HEIGHT") > 27 Then control.Multiline = True End If control.Height = oControlRow.Item("HEIGHT") control.Width = oControlRow.Item("WIDTH") If Not designMode Then control.AcceptsReturn = True control.ReadOnly = oControlRow.Item("READ_ONLY") control.TabStop = Not oControlRow.Item("READ_ONLY") control.BackColor = IIf(oControlRow.Item("READ_ONLY"), Color.LightGray, Color.White) control.ScrollBars = ScrollBars.Vertical Else control.ReadOnly = True End If Return control Catch ex As Exception Logger.Error(ex) End Try End Function Public Shared Function CreateExistingLabel(row As DataRow, designMode As Boolean) As Label Dim control As Label = CreateBaseControl(New Label(), row, designMode) Try control.Text = row.Item("CTRL_CAPTION_LANG") Catch ex As Exception control.Text = row.Item("CTRL_TEXT") End Try control.AutoSize = True Return control End Function Public Shared Function CreateExistingButton(row As DataRow, designMode As Boolean) As Button Dim oControl As Button = CreateBaseControl(New Button(), row, designMode) Dim ctrl_image As Bitmap = Nothing Dim oBitmap As Bitmap If Not IsDBNull(row.Item("IMAGE_CONTROL")) Then Dim obimg() As Byte = row.Item("IMAGE_CONTROL") oBitmap = ByteArrayToBitmap(obimg) ctrl_image = oBitmap End If Try oControl.Text = row.Item("CTRL_CAPTION_LANG") Catch ex As Exception oControl.Text = row.Item("CTRL_TEXT") End Try oControl.Height = row.Item("HEIGHT") oControl.Width = row.Item("WIDTH") If Not IsNothing(ctrl_image) And Not IsNothing(oBitmap) Then oControl.Image = oBitmap oControl.ImageAlign = ContentAlignment.MiddleLeft oControl.TextAlign = ContentAlignment.MiddleRight End If oControl.AutoSize = True Return oControl End Function Public Shared Function CreateExistingCombobox(row As DataRow, designMode As Boolean) As Windows.Forms.ComboBox Dim control As Windows.Forms.ComboBox = CreateBaseControl(New Windows.Forms.ComboBox(), row, designMode) control.Size = New Size(row.Item("WIDTH"), row.Item("HEIGHT")) If Not designMode Then control.Enabled = Not row.Item("READ_ONLY") control.TabStop = Not row.Item("READ_ONLY") control.BackColor = IIf(row.Item("READ_ONLY"), Color.LightGray, Color.White) control.AutoCompleteMode = AutoCompleteMode.SuggestAppend control.AutoCompleteSource = AutoCompleteSource.ListItems End If Return control End Function Public Shared Function CreateExistingDatepicker(row As DataRow, designMode As Boolean) As DateTimePicker Dim control As DateTimePicker = CreateBaseControl(New DateTimePicker(), row, designMode) control.Size = New Size(row.Item("WIDTH"), row.Item("HEIGHT")) control.Format = DateTimePickerFormat.Short If Not designMode Then control.Enabled = Not row.Item("READ_ONLY") control.TabStop = Not row.Item("READ_ONLY") End If Return control End Function Public Shared Function CreateExisingCheckbox(row As DataRow, designMode As Boolean) As CheckBox Dim oCheckBox As CheckBox = CreateBaseControl(New CheckBox(), row, designMode) oCheckBox.AutoSize = True Try oCheckBox.Text = row.Item("CTRL_CAPTION_LANG") Catch ex As Exception oCheckBox.Text = row.Item("CTRL_TEXT") End Try oCheckBox.CheckState = CheckState.Indeterminate If Not designMode Then oCheckBox.Enabled = Not row.Item("READ_ONLY") oCheckBox.TabStop = Not row.Item("READ_ONLY") End If Return oCheckBox End Function Public Shared Function CreateExistingDataGridView(row As DataRow, designMode As Boolean) As DataGridView Dim control As DataGridView = CreateBaseControl(New DataGridView(), row, designMode) control.Size = New Size(row.Item("WIDTH"), row.Item("HEIGHT")) control.AllowUserToAddRows = False control.AllowUserToDeleteRows = False control.AllowUserToResizeColumns = False control.AllowUserToResizeRows = False control.AlternatingRowsDefaultCellStyle.BackColor = Color.Aqua Dim col As New DataGridViewTextBoxColumn col.HeaderText = "" col.Name = "column1" col.Width = control.Width - 30 control.Columns.Add(col) If Not designMode Then control.Enabled = Not row.Item("READ_ONLY") control.TabStop = Not row.Item("READ_ONLY") End If Return control End Function Public Shared Function CreateExistingLookupControl(row As DataRow, designMode As Boolean) As LookupControl3 Dim control As LookupControl3 = CreateBaseControl(New LookupControl3(), row, designMode) control.Properties.Name = control.Name control.Width = row.Item("WIDTH") control.ReadOnly = row.Item("READ_ONLY") If designMode Then control.Cursor = Cursors.Hand End If Return control End Function Public Shared Function CreateExistingGridControl(row As DataRow, DT_MY_COLUMNS As DataTable, designMode As Boolean) As GridControl Dim oControl As GridControl = CreateBaseControl(New GridControl(), row, designMode) Dim oControlId = DirectCast(oControl.Tag, ControlMetadata).Guid Dim oDatatable As New DataTable Dim oView As GridView oControl.ForceInitialize() oView = oControl.MainView oView.OptionsView.ShowGroupPanel = False oControl.ContextMenu = Nothing Dim oGridBuilder As New GridBuilder(oView) oGridBuilder.WithClipboardHandler() If Not designMode Then oView.OptionsBehavior.Editable = Not row.Item("READ_ONLY") oView.OptionsBehavior.ReadOnly = row.Item("READ_ONLY") 'oView.OptionsBehavior.EditorShowMode = EditorShowMode.Click oControl.UseEmbeddedNavigator = Not row.Item("READ_ONLY") oView.OptionsBehavior.EditorShowMode = EditorShowMode.MouseDown ' Copy single cell value in CTRL+C instead of whole row oView.OptionsSelection.MultiSelectMode = GridMultiSelectMode.CellSelect oView.OptionsSelection.MultiSelect = True oView.OptionsClipboard.CopyColumnHeaders = DefaultBoolean.False If row.Item("VKT_ADD_ITEM") = True Then oView.OptionsBehavior.AllowAddRows = DefaultBoolean.True oView.OptionsBehavior.AllowDeleteRows = DefaultBoolean.True oView.OptionsView.NewItemRowPosition = NewItemRowPosition.Bottom Else oView.OptionsBehavior.AllowAddRows = DefaultBoolean.False oView.OptionsBehavior.AllowDeleteRows = DefaultBoolean.False oView.OptionsView.NewItemRowPosition = NewItemRowPosition.None End If End If oControl.Size = New Size(row.Item("WIDTH"), row.Item("HEIGHT")) ' Add and configure navigator to delete rows oControl.UseEmbeddedNavigator = True With oControl.EmbeddedNavigator.Buttons .CancelEdit.Visible = False .Edit.Visible = False .EndEdit.Visible = False .First.Visible = False .Last.Visible = False .Next.Visible = False .NextPage.Visible = False .PrevPage.Visible = False .Prev.Visible = False End With If GridColumns.ContainsKey(oControlId) Then GridColumns.Item(oControlId) = DT_MY_COLUMNS Else GridColumns.Add(oControlId, DT_MY_COLUMNS) End If If GridTables.ContainsKey(oControlId) Then GridTables.Item(oControlId).Clear() Else GridTables.Add(oControlId, New Dictionary(Of String, RepositoryItem)()) End If For Each oRow As DataRow In DT_MY_COLUMNS.Rows ' Create Columns in Datatable Dim oColumn = New DataColumn() With { .ColumnName = oRow.Item("SPALTENNAME"), .Caption = oRow.Item("SPALTEN_HEADER"), .ReadOnly = False } Select Case oRow.Item("TYPE_COLUMN") Case "TEXT" oColumn.DataType = GetType(String) Case "INTEGER" oColumn.DataType = GetType(Integer) Case "BOOLEAN" oColumn.DataType = GetType(Boolean) Case Else oColumn.DataType = GetType(String) End Select oDatatable.Columns.Add(oColumn) ' Fetch and cache Combobox results Dim oConnectionId As Integer = NotNull(oRow.Item("CONNECTION_ID"), 0) Dim oSqlCommand As String = NotNull(oRow.Item("SQL_COMMAND"), "") If oConnectionId > 0 And oSqlCommand <> "" Then Try Dim oComboboxDataTable As DataTable = Nothing Dim oColumnName As String = oRow.Item("SPALTENNAME") Logger.Debug("Working on SQL for Column[{0}]...", oColumnName) If Not clsPatterns.HasComplexPatterns(oSqlCommand) Then Logger.Debug("SQL has no complex patterns!") 'oComboboxDataTable = ClassDatabase.Return_Datatable_ConId(oSqlCommand, oConnectionId) oComboboxDataTable = DatabaseFallback.GetDatatable(New GetDatatableOptions(oSqlCommand, DatabaseType.ECM) With { .ConnectionId = oConnectionId }) Else Logger.Debug("...has complex patterns!!") End If Dim oRepositoryItem = GridTables_GetRepositoryItemForColumn(oColumnName, oComboboxDataTable, oRow.Item("ADVANCED_LOOKUP")) If GridTables.Item(oControlId).ContainsKey(oColumnName) Then GridTables.Item(oControlId).Item(oColumnName) = oRepositoryItem Else GridTables.Item(oControlId).Add(oColumnName, oRepositoryItem) End If Catch ex As Exception Logger.Warn("Could not load data for column {0} in control {1}", oRow.Item("SPALTENNAME"), oControl.Name) Logger.Error(ex) End Try End If Next oView.PopulateColumns(oDatatable) oControl.DataSource = oDatatable oControl.RefreshDataSource() oControl.ForceInitialize() If row.Item("TABLE_ORDER_COLUMN") <> String.Empty Then Try Dim oSortTerm = row.Item("TABLE_ORDER_COLUMN").ToString Dim oSortOrder As DevExpress.Data.ColumnSortOrder = DevExpress.Data.ColumnSortOrder.Ascending If oSortTerm.Contains(" ASC") Then oSortTerm = oSortTerm.Replace(" ASC", "") ElseIf oSortTerm.Contains(" DESC") Then oSortOrder = DevExpress.Data.ColumnSortOrder.Descending oSortTerm = oSortTerm.Replace(" DESC", "") End If oView.BeginDataUpdate() Try oView.ClearSorting() oView.Columns(oSortTerm).SortOrder = oSortOrder Finally oView.EndDataUpdate() End Try Catch ex As Exception End Try End If Dim oShouldDisplayFooter As Boolean = False For Each oCol As GridColumn In oView.Columns Dim oColumnData As DataRow = DT_MY_COLUMNS. Select($"SPALTENNAME = '{oCol.FieldName}'"). FirstOrDefault() If oColumnData Is Nothing Then Continue For End If Dim oSequence As Integer = oColumnData.Item("SEQUENCE") oCol.VisibleIndex = oSequence Dim oSummaryFunction As String = oColumnData.Item("SUMMARY_FUNCTION") Select Case oSummaryFunction Case AGGREGATE_TOTAL_INTEGER oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Sum oCol.SummaryItem.DisplayFormat = "SUM: {0:0}" oShouldDisplayFooter = True Case AGGREGATE_TOTAL_FLOAT oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Sum oCol.SummaryItem.DisplayFormat = "SUM: {0:n2}" oShouldDisplayFooter = True Case AGGREGATE_TOTAL_AVG oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Average oCol.SummaryItem.DisplayFormat = "AVG: {0}" oShouldDisplayFooter = True Case AGGREGATE_TOTAL_MAX oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Max oCol.SummaryItem.DisplayFormat = "MAX: {0}" oShouldDisplayFooter = True Case AGGREGATE_TOTAL_MIN oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Min oCol.SummaryItem.DisplayFormat = "MIN: {0}" oShouldDisplayFooter = True Case AGGREGATE_TOTAL_COUNT oCol.SummaryItem.SummaryType = DevExpress.Data.SummaryItemType.Count oCol.SummaryItem.DisplayFormat = "NUM: {0}" oShouldDisplayFooter = True End Select Next oView.OptionsView.ShowFooter = oShouldDisplayFooter AddHandler oView.InitNewRow, Sub(sender As Object, e As InitNewRowEventArgs) Try Logger.Debug("Initialzing new row") For Each oColumnData As DataRow In DT_MY_COLUMNS.Rows For Each oGridColumn As GridColumn In oView.Columns If oGridColumn.FieldName <> oColumnData.Item("SPALTENNAME") Then Continue For End If Dim oDefaultValue = NotNull(oColumnData.Item("DEFAULT_VALUE"), String.Empty) If oDefaultValue <> String.Empty Then Logger.Debug("Setting default value [{0}] for column [{1}]", oDefaultValue, oGridColumn.FieldName) oView.SetRowCellValue(e.RowHandle, oGridColumn.FieldName, oDefaultValue) End If Next Next Catch ex As Exception Logger.Error(ex) Finally newRowModified = False End Try End Sub AddHandler oView.CustomRowCellEdit, Sub(sender As Object, e As CustomRowCellEditEventArgs) Try For Each oRow As DataRow In DT_MY_COLUMNS.Rows Dim oColumnName = oRow.Item("SPALTENNAME") Dim oEditorExists = GridTables_TestEditorExistsByControlAndColumn(oControlId, oColumnName) If oColumnName <> e.Column.FieldName Then Continue For End If If oEditorExists Then Dim oEditor = GridTables.Item(oControlId).Item(oColumnName) Logger.Debug("Assigning Editor to Column [{0}]", oColumnName) e.RepositoryItem = oEditor Else Logger.Debug("Editor for Column [{0}] does not exist", oColumnName) End If Next Catch ex As Exception Logger.Warn("Error in CustomRowCellEdit for [{0}]", e.CellValue) Logger.Error(ex) End Try End Sub AddHandler oView.ValidatingEditor, Sub(sender As Object, e As BaseContainerValidateEditorEventArgs) Dim oRow As DataRowView = oView.GetRow(oView.FocusedRowHandle) Dim oColumnName = oView.FocusedColumn.FieldName Logger.Debug("Validating Editor for Column [{0}]", oColumnName) GridTables_ValidateColumn(oView, DT_MY_COLUMNS, oColumnName, e.Value, e.Valid, e.ErrorText) End Sub AddHandler oView.InvalidRowException, AddressOf View_InvalidRowException AddHandler oView.ValidatingEditor, AddressOf View_ValidatingEditor ' These handlers are all used for the custom DefaultValue functionality, additionally some code in the 'InitNewRow' event. ' https://supportcenter.devexpress.com/ticket/details/t1035580/how-to-default-a-value-in-a-column-when-add-new-row-in-data-grid AddHandler oView.ShowingEditor, AddressOf View_ShowingEditor AddHandler oView.ShownEditor, AddressOf View_ShownEditor AddHandler oView.ValidateRow, AddressOf View_ValidateRow AddHandler oControl.LostFocus, Sub(sender As GridControl, e As EventArgs) Dim oView2 As GridView = sender.FocusedView oView2.UpdateCurrentRow() End Sub ' 08.11.2021: Fix editor being empty on first open oView.FocusInvalidRow() Return oControl End Function Private Shared newRowModified As Boolean = False Private Shared Sub View_ShowingEditor(sender As Object, e As CancelEventArgs) Dim view As GridView = TryCast(sender, GridView) Logger.Debug("Showing editor.") If view.IsNewItemRow(view.FocusedRowHandle) AndAlso Not newRowModified Then Logger.Debug("Adding new row.") view.AddNewRow() End If End Sub Private Shared Sub View_ShownEditor(sender As Object, e As EventArgs) Dim view As GridView = TryCast(sender, GridView) If view.IsNewItemRow(view.FocusedRowHandle) Then Logger.Debug("Attaching Modified Handler.") AddHandler view.ActiveEditor.Modified, Sub() Logger.Debug("Row was modified.") newRowModified = True End Sub End If End Sub Private Shared Sub View_ValidateRow(sender As Object, e As ValidateRowEventArgs) Dim view As GridView = TryCast(sender, GridView) If view.IsNewItemRow(e.RowHandle) AndAlso Not newRowModified Then Logger.Debug("Deleting unused row") view.DeleteRow(e.RowHandle) End If Logger.Debug("Validating row. Resetting Modified.") newRowModified = False End Sub Private Shared Sub View_ValidatingEditor(sender As Object, e As BaseContainerValidateEditorEventArgs) Dim oValue As String = NotNull(e.Value, "") If oValue.Contains(" | ") Then oValue = oValue.Split(" | ").ToList().First() e.Value = oValue End If End Sub Private Shared Sub View_InvalidRowException(sender As Object, e As InvalidRowExceptionEventArgs) e.ExceptionMode = ExceptionMode.NoAction End Sub Public Shared Function CreateExistingLine(row As DataRow, designMode As Boolean) As LineLabel Dim control As LineLabel = CreateBaseControl(New LineLabel(), row, designMode) control.Text = "------------------------------" control.BorderStyle = BorderStyle.None control.AutoSize = False control.BackColor = IntToColor(NotNull(row.Item("FONT_COLOR"), DEFAULT_COLOR)) control.Size = New Size(row.Item("WIDTH"), row.Item("HEIGHT")) Return control End Function ' ----------------------- CUSTOM LABEL/LINE CLASS ----------------------- Public Class LineLabel Inherits Label Protected Overrides Sub OnPaint(e As PaintEventArgs) 'MyBase.OnPaint(e) Dim size As New Size(e.ClipRectangle.Width, 2) Dim rect As New Rectangle(New Point(0, 0), size) 'ControlPaint.DrawBorder(e.Graphics, rect, Me.ForeColor, ButtonBorderStyle.Solid) e.Graphics.DrawLine(New Pen(ForeColor, 100), New Point(0, 0), New Point(e.ClipRectangle.Width, 2)) End Sub End Class Public Shared Function GET_CONTROL_PROPERTIES(DT_CONTROL As DataTable, ControlName As String) Try CURRENT_CONTROL_ID = 0 CURR_CON_ID = 0 CURR_SELECT_CONTROL = "" CURR_CHOICE_LIST = "" Dim dt As New DataTable dt = DT_CONTROL ' Define the filter Dim filter As String = "NAME = '" & ControlName & "'" ' Filter the rows using Select() method of DataTable Dim FilteredRows As DataRow() = dt.Select(filter) If FilteredRows.Count = 1 Then For Each row As DataRow In FilteredRows CURRENT_CONTROL_ID = row("GUID") CURR_CON_ID = IIf(IsDBNull(row("CONNECTION_ID")), 0, row("CONNECTION_ID")) If CURR_CON_ID = 0 Then Logger.Info("CONNECTION NOT DEFINED - CTRL_GUID:" & CURRENT_CONTROL_ID) End If CURR_SELECT_CONTROL = IIf(IsDBNull(row("SQL_UEBERPRUEFUNG")), "", row("SQL_UEBERPRUEFUNG")) CURR_CHOICE_LIST = IIf(IsDBNull(row("CHOICE_LIST")), "", row("CHOICE_LIST")) Next Return 1 Else Return 0 End If Catch ex As Exception Logger.Error(ex) Logger.Info("Unexpected Error in GET_CONTROL_PROPERTIES (" & ControlName & "):" & ex.Message) Return 0 End Try End Function Public Shared Function GET_CONTROL_PROPERTY(DT_CONTROL As DataTable, ControlGUID As Integer, ColNAME As String) Try CURRENT_CONTROL_ID = 0 CURR_CON_ID = 0 CURR_SELECT_CONTROL = "" CURR_CHOICE_LIST = "" Dim dt As New DataTable dt = DT_CONTROL ' Define the filter Dim filter As String = "GUID = " & ControlGUID ' Filter the rows using Select() method of DataTable Dim FilteredRows As DataRow() = dt.Select(filter) If FilteredRows.Count = 1 Then Dim oRESULT = FilteredRows(0).Item(ColNAME) If IsDBNull(oRESULT) Then Return Nothing Return oRESULT Else Return Nothing End If Catch ex As Exception Logger.Error(ex) Logger.Info("Unexpected Error in GET_CONTROL_PROPERTY (" & ControlGUID & "#" & ColNAME & "):" & ex.Message) Return Nothing End Try End Function Public Shared Function GET_DEPENDING_CONTROLS(DT_CONTROLS As DataTable, ControlName As String) Try Dim dt As New DataTable dt = DT_CONTROLS ' Define the filter Dim filter As String = String.Format("SQL_UEBERPRUEFUNG LIKE '%{0}%'", ControlName) Dim FilteredRows As DataRow() = dt.Select(filter) CURR_DT_DEPENDING_CONTROLS = Nothing If FilteredRows.Length > 0 Then CURR_DT_DEPENDING_CONTROLS = FilteredRows.CopyToDataTable End If Return True Catch ex As Exception Logger.Error(ex) Logger.Info("Unexpected Error in GET_DEPENDING_CONTROLS (" & ControlName & "):" & ex.Message) Return 0 End Try End Function Public Shared Function GET_CONNECTION_INFO(CON_ID As Integer) Try Dim dt As New DataTable dt = BASEDATA_DT_TBDD_CONNECTION ' Define the filter Dim filter As String = "GUID = " & CON_ID ' Filter the rows using Select() method of DataTable Dim FilteredRows As DataRow() = dt.Select(filter) If FilteredRows.Count = 1 Then Return FilteredRows Else Return Nothing End If Catch ex As Exception Logger.Error(ex) Logger.Info("Unexpected Error in GET_CONNECTION_INFO (" & CON_ID.ToString & "):" & ex.Message) Return Nothing End Try End Function Public Shared Sub GridTables_CacheDatatableForColumn(pControlId As Object, pColumnName As Object, pSqlStatement As Object, pConnectionId As Integer, pAdvancedLookup As Boolean) Try 'Dim oTable As DataTable = ClassDatabase.Return_Datatable_ConId(pSqlStatement, pConnectionId) Dim oTable As DataTable = DatabaseFallback.GetDatatable(New GetDatatableOptions(pSqlStatement, DatabaseType.ECM) With { .ConnectionId = pConnectionId }) ' If no columns for this control have been added, create an empty dict now If Not GridTables.ContainsKey(pControlId) Then GridTables.Add(pControlId, New Dictionary(Of String, RepositoryItem)) End If Dim oRepositoryItem = GridTables_GetRepositoryItemForColumn(pColumnName, oTable, pAdvancedLookup) Dim oColumnDictionary = GridTables.Item(pControlId) If oColumnDictionary.ContainsKey(pColumnName) Then oColumnDictionary.Item(pColumnName) = oRepositoryItem Else oColumnDictionary.Add(pColumnName, oRepositoryItem) End If Catch ex As Exception Logger.Error(ex) End Try End Sub Public Shared Function GridTables_GetRepositoryItemForColumn(pColumnName As String, pDataTable As DataTable, pIsAdvancedLookup As Boolean) As RepositoryItem If pIsAdvancedLookup Then Dim oEditor = New RepositoryItemLookupControl3 If pDataTable IsNot Nothing Then oEditor.DisplayMember = pDataTable.Columns.Item(0).ColumnName oEditor.ValueMember = pDataTable.Columns.Item(0).ColumnName oEditor.DataSource = pDataTable End If Return oEditor Else Dim oEditor = New RepositoryItemComboBox() Dim oItems As New List(Of String) AddHandler oEditor.Validating, Sub(_sender As ComboBoxEdit, _e As CancelEventArgs) If oItems.Contains(_sender.EditValue) Then _e.Cancel = False Else _e.Cancel = True End If End Sub If pDataTable IsNot Nothing Then For Each oRow2 As DataRow In pDataTable.Rows Dim oValue = oRow2.Item(0) Try oValue &= $" | {oRow2.Item(1)}" Catch ex As Exception End Try oEditor.Items.Add(oValue) oItems.Add(oValue) Next End If Return oEditor End If End Function Public Shared Sub GridTables_HandleControlValueChange(pControlPanel As Panel, pColumnsWithSqlAndControlPlaceholders As DataTable) If Not IsNothing(pColumnsWithSqlAndControlPlaceholders) AndAlso pColumnsWithSqlAndControlPlaceholders.Rows.Count > 0 Then For Each oRow As DataRow In pColumnsWithSqlAndControlPlaceholders.Rows Try Dim oSqlStatement = oRow.ItemEx("SQL_COMMAND", String.Empty) Dim oConnectionId = oRow.ItemEx("CONNECTION_ID", -1) Dim oControlId = oRow.Item("CONTROL_ID") Dim oColumnName = oRow.Item("SPALTENNAME") Dim oAdvancedLookup = oRow.Item("ADVANCED_LOOKUP") If oSqlStatement <> String.Empty And oConnectionId > -1 Then oSqlStatement = clsPatterns.ReplaceAllValues(oSqlStatement, pControlPanel, True) GridTables_CacheDatatableForColumn(oControlId, oColumnName, oSqlStatement, oConnectionId, oAdvancedLookup) ' === Block to force setting the editor for GridColumns Logger.Info("Force-setting Editor for all Gridcells..") For Each oControl As Control In pControlPanel.Controls Try Dim oMeta = DirectCast(oControl.Tag, ClassControlCreator.ControlMetadata) If oMeta.Guid = oControlId AndAlso TypeOf oControl Is GridControl Then Dim oGrid As GridControl = DirectCast(oControl, GridControl) DirectCast(oGrid.FocusedView, GridView).FocusInvalidRow() Logger.Info("Force-setting Editor for Grid [{0}]", oGrid.Name) Exit For End If Catch ex As Exception Logger.Error(ex) End Try Next ' === End End If Catch ex As Exception Logger.Error(ex) Logger.Info("Unexpected Error in Display SQL result for grid column: " & oRow.Item("CONTROL_ID") & " - ERROR: " & ex.Message) End Try Next End If End Sub Private Shared Function GridTables_TestEditorExistsByControlAndColumn(oControlId As Integer, pColumn As String) As Boolean If GridTables.ContainsKey(oControlId) Then Dim oContainsKey = GridTables.Item(oControlId).ContainsKey(pColumn) If oContainsKey AndAlso GridTables.Item(oControlId).Item(pColumn) IsNot Nothing Then Return True Else Return False End If Else Return False End If End Function Private Shared Function GridTables_ValidateColumn(pView As GridView, pColumnDefinition As DataTable, ColumnName As String, pValue As Object, ByRef pIsValid As Boolean, ByRef pErrorText As String) As Boolean Dim oColumn As DataRow = (From r As DataRow In pColumnDefinition.Rows Where r.Item("SPALTENNAME") = ColumnName Select r).FirstOrDefault() Dim oGridColumn As GridColumn = (From c As GridColumn In pView.Columns Where c.FieldName = ColumnName Select c).FirstOrDefault() Dim oIsRequired = oColumn.Item("VALIDATION") Try Dim oRegex = NotNull(oColumn.Item("REGEX_MATCH"), String.Empty) Dim oRegexMessage = NotNull(oColumn.Item("REGEX_MESSAGE_DE"), String.Empty) If oRegex <> String.Empty Then Dim oMatch = New Regex(oRegex).IsMatch(pValue.ToString) Dim oDefaultMessage = "Wert entspricht nicht dem gefordertem Format!" Dim oMessage = IIf(oRegexMessage <> String.Empty, oRegexMessage, oDefaultMessage) If oMatch = False Then pErrorText = oMessage pIsValid = False Return False End If End If Catch ex As Exception Logger.Error(ex) End Try If oIsRequired And pValue.ToString = "" Then pErrorText = "Spalte muss ausgefüllt werden!" pIsValid = False Return False End If Return True End Function End Class