{ +-------------------------------------------------------------+ } { | | } { | GM-Software | } { | =========== | } { | | } { | Project: DB Projects | } { | | } { | Description: ODBC User Interface Classes. | } { | | } { | | } { | Copyright (C) - 2001 - Gerrit Moeller. | } { | | } { | Source code distributed under MIT license. | } { | | } { | See: https://www.gm-software.de | } { | | } { +-------------------------------------------------------------+ } {$INCLUDE GMCompilerSettings.inc} unit GMOdbcUI; {$R *.res} interface uses {$IFDEF JEDIAPI}JwaWinType,{$ELSE}Windows,{$ENDIF} GMStrDef, GMMessages, GMIntf, GMCommon, GMUICore, GMxCtrls, GMOsCtrls, GMOsExCtrls, GMSql, GMOdbcObj; const UM_DSNDROPSELECT = UM_USER + 1; type TOdbcDataChangeProc = procedure (const NewName: TGMString = '') of Object; TComboBoxOdbcDSN = class(TGMComboBox) protected procedure WMAppCommand(var Msg: TWMCommand); message WM_COMMAND + WM_APP; procedure UMDSNDropSelect(var Msg: TMessage); message UM_DSNDROPSELECT; end; TGMOdbcConnectionPropUIArea = class(TGMSurroundingUiArea) // // Need to use PostMessage for FComboBoxDSN so cannot be TGMUiArea // protected FConnectProperties: IGMOdbcConnectProperties; FOnDataChange: TOdbcDataChangeProc; FComboBoxDSN: TGMComboBox; FComboBoxAccessMode: TGMComboBox; FEditUsername: TGMEditBase; FEditPassword: TGMEditBase; FComboBoxCursorOrigin: TGMComboBox; FComboBoxTransIsolation: TGMComboBox; FComboBoxDriverDialogs: TGMComboBox; FIntEditLoginTimeout: TGMIntEdit; FIntEditStmtTimeout: TGMIntEdit; FBtnEditConnectionString: TGMxToolBtnArea; FAttrCheckBoxes: array [TOdbcConnectionAttribute] of TGMxCheckBoxArea; procedure SetConnectProperties(const AValue: IGMOdbcConnectProperties); //procedure AddDSNToComboBox(const DSN: TGMString; const Obj: TObject); procedure DataChanged(const ANewName: TGMString = ''); // procedure OnComboBoxDSNDropSelect(const ASender: TObject); procedure OnComboBoxDSNTextChange(const ASender: TObject); procedure OnComboBoxAccessModeChange(const ASender: TObject); procedure OnComboBoxDriverDialogsChange(const ASender: TObject); procedure OnEditUserNameChange(const ASender: TObject); procedure OnEditPasswordChange(const ASender: TObject); procedure OnComboBoxCursorOriginChange(const ASender: TObject); procedure OnComboBoxTransIsolationChange(const ASender: TObject); procedure OnIntEditLoginTimeoutChange(const ASender: TObject); procedure OnIntEditOperationTimeoutChange(const ASender: TObject); procedure OnAttributesChange(const ASender: TObject); procedure OnBtnEditConnectionStringClick(const ASender: TObject); public OnAttributesChanged: TGMObjNotifyProc; constructor Create(const AParent: TObject; const APosition: TRect; const AAreaAlign: TGMAreaAlignRec; const AOnDataChange: TOdbcDataChangeProc = nil; const ABkgndColor: COLORREF = cDfltColor; const AVisible: Boolean = True; const ARefLifeTime: Boolean = False); reintroduce; overload; procedure CreateHandle; override; procedure FillupComboBoxDSN; property ConnectProperties: IGMOdbcConnectProperties read FConnectProperties write SetConnectProperties; end; TGMOdbcRecordsetPropUIArea = class(TGMSurroundingUiArea) protected FRecordsetProps: IGMOdbcRecordsetProperties; FOnDataChange: TOdbcDataChangeProc; FComboBoxCursorType: TGMComboBox; FComboBoxCursorSensitivity: TGMComboBox; FComboBoxUpdateStrategy: TGMComboBox; FComboBoxUpdateSimulation: TGMComboBox; //FComboBoxBlobCompression: TGMComboBox; FIntEditKeysetSize: TGMIntEdit; FIntEditReturnedRecords: TGMIntEdit; FIntEditMaxDataSize: TGMIntEdit; FIntEditReexecuteDelay: TGMIntEdit; // FComboBoxMaxStrLenOrigin: TGMComboBox; // FLabelCharSizeFactor: TGMxLabel; // FEditCharSizeFactor: TGMColorTextFramedEdit; // FSizeFactorConvertErrorHint: TGMHintWindow; FAttrCheckBoxes: array [TGMRecordsetAttribute] of TGMxCheckBoxArea; FCountStrgyCheckBoxes: array [TRecordCountStrategy] of TGMxCheckBoxArea; //FListViewAttributes: TOdbcCheckListView; //FListViewCountStrategies: TOdbcCheckListView; // FCheckBoxUseTimeoutFromCn: TGMCheckBox; FIntEditTimeout: TGMIntEdit; FCheckBoxDoEscapeScan: TGMcheckBox; FTimeoutLabel: TGMxLabel; //procedure UMAttributesChanged(var Msg: TMessage); message UM_ATTRIBUTESCHANGED; //procedure UMCountStrategyChanged(var Msg: TMessage); message UM_COUNTSTRATEGYCHANGED; // procedure ResetConvertErrorInfo; procedure SetRecordsetProps(const AValue: IGMOdbcRecordsetProperties); // procedure SetupTimeoutCtrls; // procedure SetupCharSizeFactor; procedure DataChanged(const ANewName: TGMString = ''); procedure OnComboBoxCursorTypeChange(const ASender: TObject); procedure OnComboBoxCursorSensitivityChange(const ASender: TObject); procedure OnComboBoxUpdateStrategyChange(const ASender: TObject); procedure OnComboBoxUpdateSimulationChange(const ASender: TObject); procedure OnIntEditKeysetSizeChange(const ASender: TObject); procedure OnIntEditReturnedRecordsChange(const ASender: TObject); procedure OnIntEditMaxDataSizeChange(const ASender: TObject); procedure OnIntEditReexecuteDelayChange(const Sender: TObject); procedure OnAttributesChange(const ASender: TObject); procedure OnCountStrategiesChange(const ASender: TObject); procedure OnCheckBoxUseTimeoutFromCnChange(const ASender: TObject); procedure OnIntEditTimeoutChange(const ASender: TObject); procedure OnCheckBoxDoEscapeScanChange(const ASender: TObject); // procedure OnComboBoxMaxStrLenOriginChange(const Sender: TObject); // procedure OnEditCharSizeFactorChange(const Sender: TObject); public constructor Create(const AParent: TObject; const APosition: TRect; const AAreaAlign: TGMAreaAlignRec; const AOnDataChange: TOdbcDataChangeProc = nil; const ABkgndColor: COLORREF = cDfltColor; const AVisible: Boolean = True; const ARefLifeTime: Boolean = False); reintroduce; overload; procedure CreateHandle; override; property RecordsetProps: IGMOdbcRecordsetProperties read FRecordsetProps write SetRecordsetProps; end; TGMConnectionStrEditDlg = class(TGMDlgWindow) protected FConnectionString: TGMString; FEditor: TGMFramedEdit; // procedure OnBtnHelpClick(const ASender: TObject); public constructor Create(const AConnectionString, ATitle, ALargeText: TGMString; const AParent: TGMWndObj = cDfltPrntWnd; const ABkgndColor: COLORREF = cDfltColor; const ARefLifeTime: Boolean = True); reintroduce; overload; procedure DoneDialog(const ASetData: Boolean); override; function GetText: TGMString; override; end; TGMShowConnectionStrDlg = class(TGMDlgWindow) protected FConnectionString: TGMString; FEditor: TGMFramedEdit; // procedure OnBtnHelpClick(const ASender: TObject); public constructor Create(const AConnectionString, ATitle, ALargeText: TGMString; const AParent: TGMWndObj = cDfltPrntWnd; const ABkgndColor: COLORREF = cDfltColor; const ARefLifeTime: Boolean = True); reintroduce; overload; // procedure DoneDialog(const ASetData: Boolean); override; function GetText: TGMString; override; end; TGMOdbcConnectDlg = class(TGMDlgWindow) protected FBtnODBCAdminDlg: TGMButton; FBottomArea: TGMDlgBottomArea; FCnPropsUIArea: TGMOdbcConnectionPropUIArea; procedure OnOdbcAdminDlgClick(const Sender: TObject); procedure OnDatachanged(const NewName: TGMString = ''); public constructor Create(const APosition: TRect; const AStyle: DWORD = cDfltWndStyle; const AExStyle: DWORD = cPrntWndExStyle; const AText: TGMString = cDfltWndText; const AParent: TGMWndObj = cDfltPrntWnd; const ADlgData: Pointer = cDfltDlgData; const AMenu: HMENU = cDfltWndMenu; const ABkgndColor: COLORREF = cDfltColor; const ARefLifeTime: Boolean = False); override; procedure SetupControls; override; procedure GetDlgData; override; //function CanClose(const ASetData: Boolean): Boolean; override; procedure DoneDialog(const ASetData: Boolean); override; end; function GMExecuteOdbcConnectDlg(const AOdbcCnProps: IUnknown; const AParent: TGMWndObj = cDfltPrntWnd): Integer; function GMOdbcConnect(const AConnection: TGMOdbcConnection; const AParent: TGMWndObj = cDfltPrntWnd): Boolean; implementation uses GMGdi, GMDlgs, GMOdbcAPI, GMOdbcInstallAPI {$IFDEF JEDIAPI},jwaWinUser{$ENDIF}; const cMaxTimeout = 100000; cResOdbcDlgHeaderIcon = 'OdbcDlgHeaderIcon'; cResOdbcDlgImageListBmp = 'OdbcDlgImageListBmp'; cItemDataTxIsolationUseDflt = -1; resourcestring RStrEditConnectionString = 'Edit connection string'; RStrConnectionString = 'Connection string'; RStrTryOtherParams = 'Try again with other parameters'; RStrOdbcConnectDlgCaption = 'Select ODBC data source'; //RStrEditCnStrDlgHintTitle = 'Edit connection string'; RStrEditCnStrDlgHintText = 'Edit the connection string in a separate dialog showing each entry on a separate line'; srConnectionStrTextWhenEmpty = 'DRIVER=???;DATABASE=???;PWD=???;SERVER=???;UID=???'; //RStrNoEmptyDSN = 'The data source name cannot be empty'; //RStrDataSource = 'Connection string'; RStrAccessMode = 'Access Mode'; RStrCursorOrigin = 'Cursor Origin'; RStrIsolation = 'Isolation'; RStrDriverDialogs = 'Driver Dialogs'; RStrLoginTimeout = 'Login Timeout'; RStrOperationTimeout = 'Operation Timeout'; RStrOdbc = 'ODBC'; RStrSelectDSN = 'Data source seletion'; RStrUseDBDefaultTxIsolation = 'Use Database default'; RStrCursorType = 'Cursor Type'; RStrCursorSensitivity = 'Cursor Sensitivity'; RStrUpdateStrategy = 'Update Strategy'; RStrUpdateSimulation = 'Update Simulation'; //RStrBLOBCompression = 'BLOB Compression'; RStrKeysetSize = 'Keyset Size'; RStrReturnedRecords = 'Returned Records'; RStrMaxDataSize = 'Max Data Size'; //RStrCharSizeFactor = 'String max-length factor'; //RStrReexecuteDelay = 'Reexecute Delay'; RStrAttributes = 'Attributes'; RStrCountStrateies = 'Count Strategies'; //RStrUseTimeoutFromCn = 'Use Timeout from Connection'; //RStrTimeout = 'Timeout'; //RStrDoEscScan = 'Scan SQL for escape sequences'; RStrTimeDesc = '[s] 0 = infinite'; RStrOdbcAdminDlg = 'ODBC Administration'; RStrTemplate = 'Template'; //RStrDataTypeConvertError = 'Datatype covert error'; var vOdbcDlgImages: IGMImageCollection = nil; { ------------------------- } { ---- Global Routines ---- } { ------------------------- } function GMExecuteOdbcConnectDlg(const AOdbcCnProps: IUnknown; const AParent: TGMWndObj): Integer; var PICnProps: IGMOdbcConnectProperties; begin if not GMQueryInterface(AOdbcCnProps, IGMOdbcConnectProperties, PICnProps) then Result := IdCancel else Result := GMShowModalDlg(TGMOdbcConnectDlg, swShowNormal, Pointer(AOdbcCnProps), '', AParent); end; function GMOdbcConnect(const AConnection: TGMOdbcConnection; const AParent: TGMWndObj): Boolean; var connectData: IGMOdbcConnectProperties; showConnectDlg: Boolean; begin if AConnection = nil then begin Result := False; Exit; end; Result := AConnection.Active; if not Result then begin showConnectDlg := False; connectData := TGMOdbcConnectProperties.CreateFromObj(AConnection, True); repeat try if showConnectDlg or (Length(connectData.Obj.ConnectionString) <= 0) then begin case GMExecuteOdbcConnectDlg(connectData, AParent) of IdOk: connectData.Obj.AssignToObj(AConnection); // AConnection.AssignFromObj(connectData); IdCancel: raise EGMAbort.Create(RStrOperationCanceled); end; end; AConnection.Open; Result := True; except on ex: TObject do if GMIsFatalException(ex) then raise else if not GMAskExceptionContinue(ex, eaAskUser, RStrTryOtherParams) then raise else showConnectDlg := True; // on EAbort do raise; // on E: Exception do if not GMAskExceptionContinue(E, eaAskUser, RStrTryOtherParams) then raise else showConnectDlg := True; else raise; end; until AConnection.Active; end; end; function OdbcDlgImages: IGMImageCollection; begin if vOdbcDlgImages = nil then vOdbcDlgImages := TGMImageCollection.Create(cResOdbcDlgImageListBmp, {$IFNDEF FPC}SysInit.{$ELSE}System.{$ENDIF}HInstance); Result := vOdbcDlgImages; end; //function ProfileCmdImages: IGMImageCollection; //begin //if vProfileCmdImages = nil then vProfileCmdImages := TGMImageCollection.Create(cResProfileCmdImages, {$IFNDEF FPC}SysInit.{$ELSE}System.{$ENDIF}HInstance); //Result := vProfileCmdImages; //end; { ------------------------- } { ---- Helper Routines ---- } { ------------------------- } procedure AddDSNToComboBox(const ADSN: TGMString; const AObj: TObject); begin GMSendObjMessage(AObj, CB_ADDSTRING, 0, LPARAM(PGMChar(ADSN))); end; procedure FillComboBoxDSN(const AComboBox: TGMComboBox; const ADSNEnumProc: TGMEnumDSNProc); var odbcEnv: TGMOdbcEnvironment; i, wMax: LongInt; oldText: TGMString; begin if (AComboBox = nil) or not Assigned(ADSNEnumProc) then Exit; oldText := AComboBox.Text; try GMSendObjMessage(AComboBox, CB_RESETCONTENT); AddDSNToComboBox(RStrTemplate + ': DRIVER=SQL Server;DATABASE=???;PWD=???;SERVER=???;UID=???', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER=Oracle in OraClient12Home1_32bit;DBQ=???;PWD=???;SERVER=???;UID=???', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER={Microsoft Text-Treiber (*.txt; *.csv)};DefaultDir=C:\Pfad\Daten;FIL=text', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER=Microsoft Excel-Treiber (*.xls);DBQ=C:\Pfad\Zur\Datei.xls;Readonly=1;HDR=YES;IMEX=0', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER=Microsoft Excel Driver (*.xls, *.xlsx, *.xlsm, *.xlsb);DBQ=C:\Pfad\Zur\Datei.xls;Readonly=1;HDR=YES;IMEX=0', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER=Microsoft Access-Treiber (*.mdb);DBQ=C:\Pfad\Zur\Datei.mdb', AComboBox); AddDSNToComboBox(RStrTemplate + ': DRIVER=Microsoft Access Driver (*.mdb, *.accdb);DBQ=C:\Pfad\Zur\Datei.mdb', AComboBox); odbcEnv := TGMOdbcEnvironment.Create(False); try ODBCEnumSystemDSN(odbcEnv, ADSNEnumProc, AComboBox); ODBCEnumUserDSN(odbcEnv, ADSNEnumProc, AComboBox); finally odbcEnv.Free; end; wMax := 0; for i:=0 to GMSendObjMessage(AComboBox, CB_GETCOUNT)-1 do wMax := Max(wMax, GMTextExtent(AComboBox.GetListBoxString(i), AComboBox.FontHandle).x); GMSendObjMessage(AComboBox, CB_SETDROPPEDWIDTH, wMax + 8, 0); finally AComboBox.Text := oldText; end; end; { -------------------------- } { ---- TComboBoxOdbcDSN ---- } { -------------------------- } procedure TComboBoxOdbcDSN.UMDSNDropSelect(var Msg: TMessage); var dsnTxt: TGMString; begin dsnTxt := ExtractDSNFromDisplayName(GetListBoxString(Msg.WParam)); if GMStrLScan(PGMChar(dsnTxt), '=', Length(dsnTxt)) = nil then Text := cStrCnStrDSN + '=' + dsnTxt else Text := dsnTxt; if Assigned(OnAfterEditTextChange) then OnAfterEditTextChange(Self); end; procedure TComboBoxOdbcDSN.WMAppCommand(var Msg: TWMCommand); begin case Msg.NotifyCode of CBN_SELCHANGE: GMPostObjMessage(Self, UM_DSNDROPSELECT, GMSendObjMessage(Self, CB_GETCURSEL)); else inherited; end; FPassMessageToOriginalHandler := False; end; { ----------------------------------- } { ---- TGMOdbcConnectionPropUIArea ---- } { ----------------------------------- } constructor TGMOdbcConnectionPropUIArea.Create(const AParent: TObject; const APosition: TRect; const AAreaAlign: TGMAreaAlignRec; const AOnDataChange: TOdbcDataChangeProc; const ABkgndColor: COLORREF; const AVisible, ARefLifeTime: Boolean); //const cSpace = c2CtlSpace; var area, upperArea, labelArea, ctrlArea: TObject; a: TOdbcConnectionAttribute; // tableArea: TGMxTableArea; begin inherited Create(AParent, APosition, AAreaAlign, ABkgndColor, AVisible, ARefLifeTime); FOnDataChange := AOnDataChange; upperArea := OwnArea(TGMSurroundingUiArea.Create(Self, cNullrect, cTopAligned, ABkgndColor)); //tableArea := OwnArea(TGMxTableArea.Create(upperArea, 2, cNullRect, cTopAligned, ABkgndColor)) as TGMxTableArea; labelArea := OwnArea(TGMSurroundingUiArea.Create(upperArea, GMRect(0, cCtlSpace, 0, 0), cTopLeftX, ABkgndColor)); ctrlArea := OwnArea(TGMUiArea.Create(upperArea, GMRect(0, cCtlSpace, 0, 0), cClientAligned, ABkgndColor)); //tableArea.OwnArea(TGMxLabel.Create(tableArea, cNullRect, cLeftAligned, cNullRect, RStrDataSource + ':', ABkgndColor)); //band := tableArea.OwnArea(TGMSurroundingUiArea.Create(tableArea, GMRect(c2CtlSpace, 0, 0, 0), cTopAligned, ABkgndColor)); //FBtnEditConnectionString := OwnArea(TGMxToolBtnArea.Create(band, GMRect(-cEditHeight, 0, 0, cEditHeight), cTopRightX, OnBtnEditConnectionStringClick, '', 0, OdbcDlgImages)) as TGMxToolBtnArea; //OwnArea(TGMHintWindow.Create(-Int64(FBtnEditConnectionString), cNullRect, cClientAligned, RStrEditCnStrDlgHintText, RStrEditCnStrDlgHintTitle)); //FComboBoxDSN := tableArea.OwnArea(TGMComboBox.Create(-Int64(band), GMRect(c2CtlSpace, 0, cCtlSpace, cEditHeight), cTopAligned, '', cVisibleTabstop or CBS_DROPDOWN or CBS_AUTOHSCROLL)) as TGMComboBox; OwnArea(TGMxLabel.Create(labelArea, GMRect(0, 0, 0, cEditHeight), cLabelAlign, cNullRect, RStrConnectionString + ':', ABkgndColor)); area := OwnArea(TGMUiArea.Create(ctrlArea, GMRect(0, 0, 0, cEditHeight), cTopAligned, ABkgndColor)); //area := tableArea.OwnArea(TGMSurroundingUiArea.Create(tableArea, GMRect(c2CtlSpace, 0, 0, 0), cTopAligned, ABkgndColor)); FBtnEditConnectionString := OwnArea(TGMxToolBtnArea.Create(area, GMRect(-cEditHeight, 0, 0, cEditHeight), cTopRightX, OnBtnEditConnectionStringClick, '', 0, OdbcDlgImages)) as TGMxToolBtnArea; OwnArea(TGMHintWindow.Create(-Int64(FBtnEditConnectionString), cNullRect, cClientAligned, RStrEditCnStrDlgHintText, RStrEditConnectionString)); FComboBoxDSN := OwnArea(TComboBoxOdbcDSN.Create(-Int64(area), GMRect(c2CtlSpace, 0, cCtlSpace, cEditHeight), cTopAligned, '', cVisibleTabstop or CBS_DROPDOWN or CBS_AUTOHSCROLL)) as TGMComboBox; FComboBoxDSN.TextWhenEmpty := srConnectionStrTextWhenEmpty; FComboBoxAccessMode := GMInsertLabeledCtrl(RStrAccessMode, labelArea, ctrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMComboBox; FEditUsername := GMInsertLabeledCtrl(RStrUsername, labelArea, ctrlArea, TGMFramedEdit, cVisibleTabstop, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMFramedEdit; FEditPassword := GMInsertLabeledCtrl(RStrPassword, labelArea, ctrlArea, TGMFramedEdit, cVisibleTabstop or ES_PASSWORD, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMFramedEdit; //FEditPassword.TextWhenEmpty := RStrPassword; FComboBoxCursorOrigin := GMInsertLabeledCtrl(RStrCursorOrigin, labelArea, ctrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMComboBox; FComboBoxTransIsolation := GMInsertLabeledCtrl(RStrIsolation, labelArea, ctrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMComboBox; FComboBoxDriverDialogs := GMInsertLabeledCtrl(RStrDriverDialogs, labelArea, ctrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, ABkgndColor, 0, cEditHeight, c2CtlSpace).Ctrl as TGMComboBox; // OwnArea(TGMxLabel.Create(labelArea, GMRect(0, cCtlSpace, 0, cEditHeight), cLabelAlign, cNullRect, RStrLoginTimeout + ':', BkgndColor)); // FIntEditLoginTimeout := OwnArea(TGMIntEdit.Create(ctrlArea, GMRect(0, cCtlSpace, 0, cEditHeight), cTopAligned, 0, cMaxTimeout)) as TGMIntEdit; // OwnArea(TGMxLabel.Create(labelArea, GMRect(0, cCtlSpace, 0, cEditHeight), cLabelAlign, cNullRect, RStrOperationTimeout + ':', BkgndColor)); // FIntEditStmtTimeout := OwnArea(TGMIntEdit.Create(ctrlArea, GMRect(0, cCtlSpace, 0, cEditHeight), cTopAligned, 0, cMaxTimeout)) as TGMIntEdit; OwnArea(TGMxLabel.Create(labelArea, GMRect(0, cCtlSpace, 0, cEditHeight), cLabelAlign, cNullRect, RStrLoginTimeout + ':', ABkgndColor)); area := OwnArea(TGMUiArea.Create(ctrlArea, GMRect(0, cCtlSpace, 0, cEditHeight), cTopAligned, ABkgndColor)); OwnArea(TGMxLabel.Create(area, GMRect(0, 0, 0, cEditHeight), cTopRightX, cNullRect, RStrTimeDesc, ABkgndColor)); FIntEditLoginTimeout := OwnArea(TGMIntEdit.Create(area, GMRect(c2CtlSpace, 0, c2CtlSpace, cEditHeight), cTopAligned, 0, cMaxTimeout)) as TGMIntEdit; OwnArea(TGMxLabel.Create(labelArea, GMRect(0, cCtlSpace, 0, cEditHeight), cLabelAlign, cNullRect, RStrOperationTimeout + ':', ABkgndColor)); area := OwnArea(TGMUiArea.Create(ctrlArea, GMRect(0, cCtlSpace, 0, cEditHeight), cTopAligned, ABkgndColor)); OwnArea(TGMxLabel.Create(area, GMRect(0, 0, 0, cEditHeight), cTopRightX, cNullRect, RStrTimeDesc, ABkgndColor)); FIntEditStmtTimeout := OwnArea(TGMIntEdit.Create(area, GMRect(c2CtlSpace, 0, c2CtlSpace, cEditHeight), cTopAligned, 0, cMaxTimeout)) as TGMIntEdit; // FCBChangeLogProtocolElement[e] := OwnArea(TGMCheckBox.Create(-Int64(Self), GMRect(c2CtlSpace, cTopSpace[e = Low(e)], c2CtlSpace, 0), // cWrapRightY, ChangeLogElementDisplayName(e), OnCBProtocolelementChanged, cAdjstChkBtnStyle, 0, ABkgndColor)) as TGMCheckBox; // FAttrCheckBoxes: array [TOdbcAllowDriverDialogs] of TGMxCheckBoxArea; OwnArea(TGMxLabel.Create(Self, GMRect(0, 6, 0, 0), cTopAligned, cNullRect, RStrAttributes + ':', ABkgndColor, GMBoldUIFont)); area := OwnArea(TGMSurroundingUiArea.Create(Self, GMRect(0, 2, 0, 0), cTopAligned, GMPoint(0, cCtlSpace), vLightGray)); GMAssignRoundedAreaProperties(area); //GMSetObjMultiFrame(area, frsRaised, frsLowered); for a:=Low(a) to High(a) do FAttrCheckBoxes[a] := OwnArea(TGMxCheckBoxArea.Create(area, GMRect(cCtlSpace, cCtlSpace, cCtlSpace, 0), cTopAligned, GMOdbcConnectionAttrName(a), OnAttributesChange, vLightGray)) as TGMxCheckBoxArea; //FComboBoxDSN.OnAfterSelectionChange := OnComboBoxDSNDropSelect; FComboBoxDSN.OnAfterEditTextChange := OnComboBoxDSNTextChange; FComboBoxAccessMode.OnAfterSelectionChange := OnComboBoxAccessModeChange; FComboBoxDriverDialogs.OnAfterSelectionChange := OnComboBoxDriverDialogsChange; FEditUsername.OnAfterTextChange := OnEditUserNameChange; FEditPassword.OnAfterTextChange := OnEditPasswordChange; FComboBoxCursorOrigin.OnAfterSelectionChange := OnComboBoxCursorOriginChange; FComboBoxTransIsolation.OnAfterSelectionChange := OnComboBoxTransIsolationChange; FIntEditLoginTimeout.OnAfterValueChange := OnIntEditLoginTimeoutChange; FIntEditStmtTimeout.OnAfterValueChange := OnIntEditOperationTimeoutChange; //IntEditLoginTimeout.Hint := RStrValueBoundsHint; //IntEditOperationTimeout.Hint := RStrValueBoundsHint; end; procedure TGMOdbcConnectionPropUIArea.DataChanged(const ANewName: TGMString); begin if Assigned(FOnDataChange) then FOnDataChange(ANewName); end; procedure TGMOdbcConnectionPropUIArea.FillupComboBoxDSN; begin FillComboBoxDSN(FComboBoxDSN, AddDSNToComboBox); end; procedure TGMOdbcConnectionPropUIArea.CreateHandle; var strValues: TGMStringArray; am: TAccessMode; cor: TCursorOrigin; txi: TTransactionIsolation; ddlg: TOdbcAllowDriverDialogs; itemDataArr: TGMUiItemDataArray; begin // if HandleAllocated then begin inherited CreateHandle; Exit; end else inherited CreateHandle; inherited; FillupComboBoxDSN; SetLength(strValues, 0); for am:=Low(am) to High(am) do GMAddStrToArray(GMAccessModeName(am), strValues); GMFillComboBoxFromStrings(FComboBoxAccessMode, strValues); SetLength(strValues, 0); for cor:=Low(cor) to High(cor) do GMAddStrToArray(GMCursorOriginName(cor), strValues); GMFillComboBoxFromStrings(FComboBoxCursorOrigin, strValues); //SetLength(strValues, 0); //for txi:=Low(txi) to High(txi) do GMAddStrToArray(GMTransactionIsolationName(txi), strValues); //GMFillComboBoxFromStrings(FComboBoxTransIsolation, strValues); SetLength(itemDataArr, 0); GMAddUiItemDataToArray(GMInitUiItemData(RStrUseDBDefaultTxIsolation, cItemDataTxIsolationUseDflt), itemDataArr); for txi:=Low(txi) to High(txi) do GMAddUiItemDataToArray(GMInitUiItemData(GMTransactionIsolationName(txi), Ord(txi)), itemDataArr); GMFillComboBox(FComboBoxTransIsolation, itemDataArr); SetLength(strValues, 0); for ddlg:=Low(ddlg) to High(ddlg) do GMAddStrToArray(GMDriverDialogName(ddlg), strValues); GMFillComboBoxFromStrings(FComboBoxDriverDialogs, strValues); end; procedure TGMOdbcConnectionPropUIArea.OnBtnEditConnectionStringClick(const ASender: TObject); var dlg: IGMGetHandle; begin dlg := TGMConnectionStrEditDlg.Create(FComboBoxDSN.Text, RStrEditConnectionString, RStrConnectionString, GMModalDlgParentWnd); if GMShowModalWnd(dlg.Handle) = IDOK then begin FComboBoxDSN.Text := GMGetIntfText(dlg); OnComboBoxDSNTextChange(FComboBoxDSN); end; end; procedure TGMOdbcConnectionPropUIArea.SetConnectProperties(const AValue: IGMOdbcConnectProperties); var t: TTransactionIsolation; a: TOdbcConnectionAttribute; itemData: PtrInt; begin //if FConnectProperties = Value then Exit; FConnectProperties := AValue; GMenableControls(Self, FConnectProperties <> nil, True, []); if AValue = nil then GMClearControls(Self, True, []) else begin FComboBoxDSN.Text := ConnectProperties.Obj.ConnectionString; FComboBoxAccessMode.SelectedIndex := Ord(ConnectProperties.Obj.AccessMode); FEditUsername.Text := ConnectProperties.Obj.Username; FEditPassword.Text := ConnectProperties.Obj.Password; FComboBoxCursorOrigin.SelectedIndex := Ord(ConnectProperties.Obj.CursorOrigin); FComboBoxDriverDialogs.SelectedIndex := Ord(ConnectProperties.Obj.AllowDriverDialogs); itemData := -100; if ConnectProperties.Obj.TransactionIsolation = [] then itemData := cItemDataTxIsolationUseDflt else for t:=Low(t) to High(t) do if t in ConnectProperties.Obj.TransactionIsolation then itemData := Ord(t); FComboBoxTransIsolation.SelectItemData(itemData, False); FIntEditLoginTimeout.Value := ConnectProperties.Obj.TimeoutForLogin; FIntEditStmtTimeout.Value := ConnectProperties.Obj.TimeoutForStatements; for a:=Low(a) to High(a) do FAttrCheckBoxes[a].Checked := a in ConnectProperties.Obj.Attributes; end; end; procedure TGMOdbcConnectionPropUIArea.OnComboBoxDSNTextChange(const ASender: TObject); begin if (ConnectProperties = nil) or GMSameText(ConnectProperties.Obj.ConnectionString, (ASender as TGMComboBox).Text) then Exit; ConnectProperties.Obj.ConnectionString := (ASender as TGMComboBox).Text; DataChanged(GMExtractNameFromConnectionString(ConnectProperties.Obj.ConnectionString)); end; //procedure TGMOdbcConnectionPropUIArea.OnComboBoxDSNDropSelect(const ASender: TObject); //begin //if ConnectProperties = nil then Exit; // ////GMPostObjMessage(FComboBoxDSN, WM_COMMAND + WM_APP, MakeLong(0, CBN_EDITCHANGE)); ////PostMessage(FComboBoxDSN.Handle, WM_COMMAND, MakeLong(0, CBN_EDITCHANGE), 0); // ////OnComboBoxDSNTextChange(FComboBoxDSN); ////FComboBoxDSN.SelectAll; //end; procedure TGMOdbcConnectionPropUIArea.OnComboBoxAccessModeChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.AccessMode := TAccessMode(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TAccessMode)), Ord(High(TAccessMode)))); DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnComboBoxDriverDialogsChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.AllowDriverDialogs := TOdbcAllowDriverDialogs(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TOdbcAllowDriverDialogs)), Ord(High(TOdbcAllowDriverDialogs)))); DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnEditUserNameChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.Username := (ASender as TGMFramedEdit).Text; DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnEditPasswordChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.Password := (ASender as TGMFramedEdit).Text; DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnComboBoxCursorOriginChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.CursorOrigin := TCursorOrigin(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TCursorOrigin)), Ord(High(TCursorOrigin)))); DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnComboBoxTransIsolationChange(const ASender: TObject); var itemVal: PtrInt; begin if (ConnectProperties <> nil) and (ASender is TGMComboBox) then begin itemVal := TGMComboBox(ASender).GetItemData(TGMComboBox(ASender).SelectedIndex); if GMISInRange(itemVal, Ord(Low(TTransactionIsolation)), Ord(High(TTransactionIsolation))) then begin ConnectProperties.Obj.TransactionIsolation := [TTransactionIsolation(itemVal)]; DataChanged; end else if itemVal = cItemDataTxIsolationUseDflt then begin ConnectProperties.Obj.TransactionIsolation := []; DataChanged; end; end; end; procedure TGMOdbcConnectionPropUIArea.OnIntEditLoginTimeoutChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.TimeoutForLogin := (ASender as TGMIntEdit).Value; DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnIntEditOperationTimeoutChange(const ASender: TObject); begin if ConnectProperties = nil then Exit; ConnectProperties.Obj.TimeoutForStatements := (ASender as TGMIntEdit).Value; DataChanged; end; procedure TGMOdbcConnectionPropUIArea.OnAttributesChange(const ASender: TObject); var a: TOdbcConnectionAttribute; begin if (ConnectProperties = nil) or not (ASender is TGMxCheckBoxArea) then Exit; for a:=Low(a) to High(a) do if ASender = FAttrCheckBoxes[a] then begin if (ASender as TGMxCheckBoxArea).Checked then ConnectProperties.Obj.Attributes := ConnectProperties.Obj.Attributes + [a] else ConnectProperties.Obj.Attributes := ConnectProperties.Obj.Attributes - [a]; if Assigned(OnAttributesChanged) then OnAttributesChanged(ASender); Datachanged; Break; end; end; { ------------------------------------ } { ---- TGMOdbcRecordsetPropUIArea ---- } { ------------------------------------ } constructor TGMOdbcRecordsetPropUIArea.Create(const AParent: TObject; const APosition: TRect; const AAreaAlign: TGMAreaAlignRec; const AOnDataChange: TOdbcDataChangeProc; const ABkgndColor: COLORREF; const AVisible, ARefLifeTime: Boolean); const //cSpace = c2CtlSpace; //cHAttrs = 92; cHCounts = 58; //cListStyle = LVS_SMALLICON or LVS_SINGLESEL or LVS_SHAREIMAGELISTS or LVS_SHOWSELALWAYS or LVS_NOSCROLL or LVS_AUTOARRANGE; // WS_VSCROLL cRCtrl: TRect = (Left: c2CtlSpace; Top: cCtlSpace; Right: 0; Bottom: cEditHeight); cRLabel: TRect = (Left: 0; Top: cCtlSpace; Right: 0; Bottom: 0); c2 = 2; c6 = 6; var tableArea: TGMxTableArea; area: TObject; a: TGMRecordsetAttribute; c: TRecordCountStrategy; begin inherited Create(AParent, APosition, AAreaAlign, ABkgndColor, AVisible, ARefLifeTime); FOnDataChange := AOnDataChange; tableArea := OwnArea(TGMxTableArea.Create(Self, 2, cNullRect, cTopAligned, ABkgndColor)) as TGMxTableArea; //FComboBoxCursorType := GMInsertLabeledCtrl(RStrCursorType, LabelArea, CtrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, cDfltColor, cSpace).Ctrl as TGMComboBox; tableArea.OwnArea(TGMxLabel.Create(tableArea, cNullRect, cLeftAligned, cNullRect, RStrCursorType + ':', ABkgndColor)); FComboBoxCursorType := tableArea.OwnArea(TGMComboBox.Create(-Int64(tableArea), GMRect(c2CtlSpace, 0, 0, cEditHeight), cTopAligned, '', cVisibleTabstop or CBS_DROPDOWNLIST)) as TGMComboBox; //tableArea[0, 1] := FComboBoxCursorType; FComboBoxCursorType.OnAfterSelectionChange := OnComboBoxCursorTypeChange; //FComboBoxCursorSensitivity := GMInsertLabeledCtrl(RStrCursorSensitivity, LabelArea, CtrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, cDfltColor, cSpace).Ctrl as TGMComboBox; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrCursorSensitivity + ':', ABkgndColor)); FComboBoxCursorSensitivity := tableArea.OwnArea(TGMComboBox.Create(-Int64(tableArea), cRCtrl, cTopAligned, '', cVisibleTabstop or CBS_DROPDOWNLIST)) as TGMComboBox; //tableArea[1, 1] := FComboBoxCursorSensitivity; FComboBoxCursorSensitivity.OnAfterSelectionChange := OnComboBoxCursorSensitivityChange; //FComboBoxUpdateStrategy := GMInsertLabeledCtrl(RStrUpdateStrategy, LabelArea, CtrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, cDfltColor, cSpace).Ctrl as TGMComboBox; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrUpdateStrategy + ':', ABkgndColor)); FComboBoxUpdateStrategy := tableArea.OwnArea(TGMComboBox.Create(-Int64(tableArea), cRCtrl, cTopAligned, '', cVisibleTabstop or CBS_DROPDOWNLIST)) as TGMComboBox; //tableArea[2, 1] := FComboBoxUpdateStrategy; FComboBoxUpdateStrategy.OnAfterSelectionChange := OnComboBoxUpdateStrategyChange; //FComboBoxUpdateSimulation := GMInsertLabeledCtrl(RStrUpdateSimulation, LabelArea, CtrlArea, TGMComboBox, cVisibleTabstop or CBS_DROPDOWNLIST, clrWindow, cDfltColor, cSpace).Ctrl as TGMComboBox; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrUpdateSimulation + ':', ABkgndColor)); FComboBoxUpdateSimulation := tableArea.OwnArea(TGMComboBox.Create(-Int64(tableArea), cRCtrl, cTopAligned, '', cVisibleTabstop or CBS_DROPDOWNLIST)) as TGMComboBox; //tableArea[3, 1] := FComboBoxUpdateSimulation; FComboBoxUpdateSimulation.OnAfterSelectionChange := OnComboBoxUpdateSimulationChange; //FComboBoxBlobCompression := GMInsertLabeledCtrl(RStrBLOBCompression, LabelArea, CtrlArea, TGMComboBox, CBS_DROPDOWNLIST, clrWindow, cDfltColor, cSpace).Ctrl as TGMComboBox; //FIntEditKeysetSize := OwnArea(TGMIntEdit.Create(CtrlArea, GMRect(cSpace, cCtlSpace, cSpace, cEditHeight), cTopAligned, 0, High(LongInt))) as TGMIntEdit; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrKeysetSize + ':', ABkgndColor)); FIntEditKeysetSize := tableArea.OwnArea(TGMIntEdit.Create(tableArea, cRCtrl, cTopAligned, 0, High(LongInt), ABkgndColor)) as TGMIntEdit; //tableArea[4, 1] := FIntEditKeysetSize; FIntEditKeysetSize.OnAfterValueChange := OnIntEditKeysetSizeChange; //FIntEditReturnedRecords := OwnArea(TGMIntEdit.Create(CtrlArea, GMRect(cSpace, cCtlSpace, cSpace, cEditHeight), cTopAligned, 0, High(LongInt))) as TGMIntEdit; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrReturnedRecords + ':', ABkgndColor)); FIntEditReturnedRecords := tableArea.OwnArea(TGMIntEdit.Create(tableArea, cRCtrl, cTopAligned, 0, High(LongInt), ABkgndColor)) as TGMIntEdit; //tableArea[5, 1] := FIntEditReturnedRecords; FIntEditReturnedRecords.OnAfterValueChange := OnIntEditReturnedRecordsChange; //FIntEditMaxDataSize := OwnArea(TGMIntEdit.Create(CtrlArea, GMRect(cSpace, cCtlSpace, cSpace, cEditHeight), cTopAligned, 0, High(LongInt))) as TGMIntEdit; tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrMaxDataSize + ':', ABkgndColor)); FIntEditMaxDataSize := tableArea.OwnArea(TGMIntEdit.Create(tableArea, cRCtrl, cTopAligned, 0, High(LongInt), ABkgndColor)) as TGMIntEdit; //tableArea[6, 1] := FIntEditMaxDataSize; FIntEditMaxDataSize.OnAfterValueChange := OnIntEditMaxDataSizeChange; //tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrMaxStrLenOrigin + ':', ABkgndColor)); //FComboBoxMaxStrLenOrigin := tableArea.OwnArea(TGMComboBox.Create(-Int64(tableArea), cRCtrl, cTopAligned, '', cVisibleTabstop or CBS_DROPDOWNLIST)) as TGMComboBox; //FComboBoxMaxStrLenOrigin.OnAfterSelectionChange := OnComboBoxMaxStrLenOriginChange; //FLabelCharSizeFactor := //tableArea.OwnArea(TGMxLabel.Create(tableArea, cRLabel, cLeftAligned, cNullRect, RStrCharSizeFactor + ':', ABkgndColor)); // as TGMxLabel; //FEditCharSizeFactor := tableArea.OwnArea(TGMColorTextFramedEdit.Create(-Int64(tableArea), cRCtrl, cTopAligned, '', cVisibleTabstop)) as TGMColorTextFramedEdit; //FEditCharSizeFactor.OnAfterTextChange := OnEditCharSizeFactorChange; //FSizeFactorConvertErrorHint := OwnArea(TGMHintWindow.Create(-Int64(FEditCharSizeFactor), cNullRect, cClientAligned, '', '')) as TGMHintWindow; OwnArea(TGMxLabel.Create(Self, GMRect(0, c6, 0, 0), cTopAligned, cNullRect, RStrAttributes + ':', ABkgndColor, GMBoldUIFont)); area := OwnArea(TGMSurroundingUiArea.Create(Self, GMRect(0, c2, 0, 0), cTopAligned, GMPoint(0, cCtlSpace), vLightGray)); GMAssignRoundedAreaProperties(area); //GMSetObjMultiFrame(area, frsRaised, frsLowered); for a:=Low(a) to High(a) do FAttrCheckBoxes[a] := OwnArea(TGMxCheckBoxArea.Create(area, GMRect(cCtlSpace, cCtlSpace, cCtlSpace, 0), cTopAligned, GMRecordsetAttributeName(a), OnAttributesChange, vLightGray)) as TGMxCheckBoxArea; OwnArea(TGMxLabel.Create(Self, GMRect(0, c6, 0, 0), cTopAligned, cNullRect, RStrCountStrateies + ':', ABkgndColor, GMBoldUIFont)); area := OwnArea(TGMSurroundingUiArea.Create(Self, GMRect(0, c2, 0, 0), cTopAligned, GMPoint(0, cCtlSpace), vLightGray)); GMAssignRoundedAreaProperties(area); //GMSetObjMultiFrame(area, frsRaised, frsLowered); for c:=Low(c) to High(c) do FCountStrgyCheckBoxes[c] := OwnArea(TGMxCheckBoxArea.Create(area, GMRect(cCtlSpace, cCtlSpace, cCtlSpace, 0), cTopAligned, GMCountStrategyName(c), OnCountStrategiesChange, vLightGray)) as TGMxCheckBoxArea; // // //OwnArea(TGMxLabel.Create(LabelArea, GMRect(cSpace, cCtlSpace, 0, cEditHeight), cLabelAlign, cNullRect, RStrReexecuteDelay + ':', haLeft, vaCenter, BkgndColor)); //FIntEditReexecuteDelay := OwnArea(TGMIntEdit.Create(CtrlArea, GMRect(cSpace, cCtlSpace, cSpace, cEditHeight), cTopAligned, 0, High(LongInt))) as TGMIntEdit; //FIntEditReexecuteDelay.OnAfterValueChange := OnIntEditReexecuteDelayChange; // // //area := OwnArea(TGMSurroundingUiArea.Create(Self, GMRect(cSpace, cCtlSpace, cSpace, 0), cTopAligned, GMPoint(0, cCtlSpace))); //FCheckBoxUseTimeoutFromCn := OwnArea(TGMCheckBox.Create(-Int64(area), GMRect(cSpace, cCtlSpace, cSpace, 0), cTopAligned, RStrUseTimeoutFromCn, cAdjstChkBtnStyle)) as TGMCheckBox; //FTimeoutLabel := OwnArea(TGMxLabel.Create(area, GMRect(cSpace, cCtlSpace, 0, cEditHeight), cTopLeftX, cNullRect, RStrTimeout + ':', haLeft, vaCenter, BkgndColor)) as TGMxLabel; //FIntEditTimeout := OwnArea(TGMIntEdit.Create(area, GMRect(cSpace, cCtlSpace, cSpace, cEditHeight), cTopAligned, 0, High(LongInt))) as TGMIntEdit; //GMSetObjMultiFrame(area, frsRaised, frsLowered); // //FCheckBoxDoEscapeScan := OwnArea(TGMCheckBox.Create(-Int64(Self), GMRect(cSpace, cCtlSpace, cSpace, 0), cTopAligned, RStrDoEscScan, cAdjstChkBtnStyle)) as TGMCheckBox; // //FCheckBoxUseTimeoutFromCn.OnClick := OnCheckBoxUseTimeoutFromCnChange; //FIntEditTimeout.OnAfterValueChange := OnIntEditTimeoutChange; //FCheckBoxDoEscapeScan.OnClick := OnCheckBoxDoEscapeScanChange; end; procedure TGMOdbcRecordsetPropUIArea.DataChanged(const ANewName: TGMString); begin if Assigned(FOnDataChange) then FOnDataChange(ANewName); end; //procedure TGMOdbcRecordsetPropUIArea.SetupTimeoutCtrls; ////const cColor: array [Boolean] of COLORREF = (clBlack, clDkGray); //begin //FIntEditTimeout.Enabled := not FCheckBoxUseTimeoutFromCn.Checked; ////FTimeoutLabel.SetFontColor(cColor[FCheckBoxUseTimeoutFromCn.Checked]); //FTimeoutLabel.SetEnabled(not FCheckBoxUseTimeoutFromCn.Checked); //end; procedure TGMOdbcRecordsetPropUIArea.CreateHandle; var strValues: TGMStringArray; c: TGMCursorType; s: TCursorSensitivity; u: TUpdateStrategy; v: TPositionedUpdateSimulation; // l: TGMMaxStringLengthOrigin; begin // if HandleAllocated then begin inherited CreateHandle; Exit; end else inherited CreateHandle; inherited; SetLength(strValues, 0); for c:=Low(c) to High(c) do GMAddStrToArray(GMCursorTypeName(c), strValues); GMFillComboBoxFromStrings(FComboBoxCursorType, strValues); SetLength(strValues, 0); for s:=Low(s) to High(s) do GMAddStrToArray(GMCursorSensitivityName(s), strValues); GMFillComboBoxFromStrings(FComboBoxCursorSensitivity, strValues); SetLength(strValues, 0); for u:=Low(u) to High(u) do GMAddStrToArray(GMUpdateStrategyName(u), strValues); GMFillComboBoxFromStrings(FComboBoxUpdateStrategy, strValues); SetLength(strValues, 0); for v:=Low(v) to High(v) do GMAddStrToArray(GMUpdateSimulationName(v), strValues); GMFillComboBoxFromStrings(FComboBoxUpdateSimulation, strValues); //SetLength(strValues, 0); //for l:=Low(l) to High(l) do GMAddStrToArray(GMMaxStrLenOriginName(l), strValues); //GMFillComboBoxFromStrings(FComboBoxMaxStrLenOrigin, strValues); end; procedure TGMOdbcRecordsetPropUIArea.SetRecordsetProps(const AValue: IGMOdbcRecordsetProperties); var a: TGMRecordsetAttribute; c: TRecordCountStrategy; // txt: TGMString; begin //ResetConvertErrorInfo; FRecordsetProps := AValue; GMenableControls(Self, FRecordsetProps <> nil, True, []); if AValue = nil then GMClearControls(Self, True, []) else begin FComboBoxCursorType.SelectedIndex := Ord(RecordsetProps.Obj.CursorType); FComboBoxCursorSensitivity.SelectedIndex := Ord(RecordsetProps.Obj.CursorSensitivity); FComboBoxUpdateStrategy.SelectedIndex := Ord(RecordsetProps.Obj.UpdateStrategy); FComboBoxUpdateSimulation.SelectedIndex := Ord(RecordsetProps.Obj.PositionedUpdateSimulation); for a:=Low(a) to High(a) do FAttrCheckBoxes[a].Checked := a in RecordsetProps.Obj.Attributes; for c:=Low(c) to High(c) do FCountStrgyCheckBoxes[c].Checked := c in RecordsetProps.Obj.RecordCountStrategies; FIntEditKeysetSize.Value := RecordsetProps.Obj.KeysetSize; FIntEditReturnedRecords.Value := RecordsetProps.Obj.MaxRecordsReturned; FIntEditMaxDataSize.Value := RecordsetProps.Obj.MaxFieldDataSize; // FIntEditReexecuteDelay.Value := RecordsetProps.TimedReExecutionDelay; // FComboBoxMaxStrLenOrigin.SelectedIdx := Ord(RecordsetProps.MaxStringLengthOrigin); // txt := GMStripRight(GMExtendedToStr(RecordsetProps.MaxStringLengthCharSizeFactor, -1, 20), cWhiteSpace + '0'); // if (Length(txt) > 0) then // case txt[Length(txt)] of // ',', '.': txt := txt + '0'; // end; // FEditCharSizeFactor.Text := txt; // SetupCharSizeFactor; // if FListViewAttributes.HandleAllocated then // for a:=Low(a) to High(a) do ListView_SetCheckState(FListViewAttributes.Handle, Ord(a), a in RecordsetProps.Attributes); // // if FListViewCountStrategies.HandleAllocated then // for c:=Low(c) to High(c) do ListView_SetCheckState(FListViewCountStrategies.Handle, Ord(c), c in RecordsetProps.RecordCountStrategies); // // FCheckBoxUseTimeoutFromCn.Checked := RecordsetProps.TimeoutProperties.UseValueFromConnection; // FIntEditTimeout.AValue := RecordsetProps.TimeoutProperties.TimeoutForStatements; // // FCheckBoxDoEscapeScan.Checked := RecordsetProps.UseSQLEscapeSequences; // SetupTimeoutCtrls; end; end; //procedure TGMOdbcRecordsetPropUIArea.SetupCharSizeFactor; //var enable: Boolean; //begin //enable := FComboBoxMaxStrLenOrigin.SelectedIdx = Ord(sloLengthInChars); //FLabelCharSizeFactor.SetEnabled(enable); //GMEnableObj(FEditCharSizeFactor, enable); //end; //procedure TGMOdbcRecordsetPropUIArea.ResetConvertErrorInfo; //begin //GMSendObjMessage(FSizeFactorConvertErrorHint, TTM_POP); //FSizeFactorConvertErrorHint.SetText(''); //FSizeFactorConvertErrorHint.SetTitleAndIcon('', -1); //FEditCharSizeFactor.SetFontColor(GMRGBColor(cDfltFontColor)); //end; procedure TGMOdbcRecordsetPropUIArea.OnComboBoxCursorTypeChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.CursorType := TGMCursorType(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TGMCursorType)), Ord(High(TGMCursorType)))); Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnComboBoxCursorSensitivityChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.CursorSensitivity := TCursorSensitivity(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TCursorSensitivity)), Ord(High(TCursorSensitivity)))); Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnComboBoxUpdateStrategyChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.UpdateStrategy := TUpdateStrategy(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TUpdateStrategy)), Ord(High(TUpdateStrategy)))); Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnComboBoxUpdateSimulationChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.PositionedUpdateSimulation := TPositionedUpdateSimulation(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TPositionedUpdateSimulation)), Ord(High(TPositionedUpdateSimulation)))); Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnIntEditKeysetSizeChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.KeysetSize := (ASender as TGMIntEdit).Value; Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnIntEditMaxDataSizeChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.MaxFieldDataSize := (ASender as TGMIntEdit).Value; Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnIntEditReexecuteDelayChange(const Sender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.TimedReExecutionDelay := (Sender as TGMIntEdit).Value; Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnIntEditReturnedRecordsChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.MaxRecordsReturned := (ASender as TGMIntEdit).Value; Datachanged; end; //procedure TGMOdbcRecordsetPropUIArea.OnComboBoxMaxStrLenOriginChange(const ASender: TObject); //begin //if Recordset = nil then Exit; //Recordset.MaxStringLengthOrigin := TGMMaxStringLengthOrigin(GMBoundedInt(GMSendObjMessage(ASender, CB_GETCURSEL), Ord(Low(TGMMaxStringLengthOrigin)), Ord(High(TGMMaxStringLengthOrigin)))); //Datachanged; //SetupCharSizeFactor; //end; //procedure TGMOdbcRecordsetPropUIArea.OnEditCharSizeFactorChange(const ASender: TObject); //var dblVal: Double; strVal: TGMString; convertCode: Integer; //begin //if Recordset = nil then Exit; //strVal := (ASender as TGMEditBase).Text; //strVal := GMReplaceChars(strVal, ',', '.'); // GMDeleteChars(AValue, ThousandSeparator) //Val(strVal, dblVal, convertCode); //if convertCode <> 0 then // begin // (ASender as TGMColorTextFramedEdit).SetFontColor(clRed); // FSizeFactorConvertErrorHint.SetText(GMFormat(RStrInvalidFloatStrFmt, [strVal, convertCode])); // FSizeFactorConvertErrorHint.SetTitleAndIcon(RStrDataTypeConvertError, TTI_ERROR); // GMSendObjMessage(FSizeFactorConvertErrorHint, TTM_POPUP); // end //else // begin // Recordset.MaxStringLengthCharSizeFactor := dblVal; // Datachanged; // ResetConvertErrorInfo; // end; ////if convertCode <> 0 then raise EGMConvertException.ObjError(GMFormat(RStrInvalidFloatStrFmt, [AValue, convertCode]), nil, 'GMStrToDouble'); //end; procedure TGMOdbcRecordsetPropUIArea.OnAttributesChange(const ASender: TObject); var a: TGMRecordsetAttribute; begin if (RecordsetProps = nil) or not (ASender is TGMxCheckBoxArea) then Exit; for a:=Low(a) to High(a) do if ASender = FAttrCheckBoxes[a] then begin if (ASender as TGMxCheckBoxArea).Checked then RecordsetProps.Obj.Attributes := RecordsetProps.Obj.Attributes + [a] else RecordsetProps.Obj.Attributes := RecordsetProps.Obj.Attributes - [a]; Datachanged; Break; end; end; procedure TGMOdbcRecordsetPropUIArea.OnCountStrategiesChange(const ASender: TObject); var c: TRecordCountStrategy; begin if (RecordsetProps = nil) or not (ASender is TGMxCheckBoxArea) then Exit; for c:=Low(c) to High(c) do if ASender = FCountStrgyCheckBoxes[c] then begin if (ASender as TGMxCheckBoxArea).Checked then RecordsetProps.Obj.RecordCountStrategies := RecordsetProps.Obj.RecordCountStrategies + [c] else RecordsetProps.Obj.RecordCountStrategies := RecordsetProps.Obj.RecordCountStrategies - [c]; Datachanged; Break; end; end; procedure TGMOdbcRecordsetPropUIArea.OnCheckBoxUseTimeoutFromCnChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.TimeoutProperties.UseValueFromConnection := (ASender as TGMCheckBox).Checked; //SetupTimeoutCtrls; Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnIntEditTimeoutChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.TimeoutProperties.TimeoutForStatements := (ASender as TGMIntEdit).Value; Datachanged; end; procedure TGMOdbcRecordsetPropUIArea.OnCheckBoxDoEscapeScanChange(const ASender: TObject); begin if RecordsetProps = nil then Exit; RecordsetProps.Obj.UseSQLEscapeSequences := (ASender as TGMCheckBox).Checked; Datachanged; end; { --------------------------------- } { ---- TGMConnectionStrEditDlg ---- } { --------------------------------- } constructor TGMConnectionStrEditDlg.Create(const AConnectionString, ATitle, ALargeText: TGMString; const AParent: TGMWndObj; const ABkgndColor: COLORREF; const ARefLifeTime: Boolean); var clientArea: TObject; txt: TGMString; cnStorage: IGMConnectionStringStorage; begin inherited Create(cNullRect, cSizeDlgWndStyle, 0, ATitle, AParent, nil, 0, ABkgndColor, ARefLifeTime); FSizeConstraints.MinSize := WndSizeFromClientSize(GMPoint(230, 300)); //FLayoutBounds := GMCenteredWndRect(GMPoint(300, 500), AParent); //FLayoutBounds := GMCenteredWndRect(GMRectSize(GMLoadDlgRect(UserSettings, '\' + cPrsFolderWindow, cPrsFolderWindow, GMPoint(300, 500), 0)), AParent); //FLayoutBounds := GMLoadDlgRect(UserSettings, GMAbsPath(cPrsMaskEditDlg), cPrsMaskEditDlg, GMPoint(300, 500), AParent); FLayoutBounds := GMCenteredWndRect(GMPoint(400, 500), AParent); OwnArea(TGMDlgHeaderArea.Create(self, cNullRect, cTopAligned, ALargeText, ATitle)); clientArea := OwnArea(TGMUiArea.Create(Self, cNullRect, cClientAligned, ABkgndColor)); cnStorage := TGMConnectionStringStorage.Create(AConnectionString); txt := GMNamesAndValuesAsString(cnStorage.Obj.Values, GMVarToConnectionStrLiteral, cNewLine, cCnStrValSep); FEditor := OwnArea(TGMFramedEdit.Create(-Int64(clientArea), GMRect(cCtlSpace, cCtlSpace, cCtlSpace, cCtlSpace), cClientAligned, txt, cVisibleTabstop or ES_MultiLine or WS_HSCROLL or WS_VSCROLL)) as TGMFramedEdit; //area := OwnArea(TGMDlgBottomArea.Create(Self, cDlgBtnsOkCancel, dbkOk)); //OwnArea(TGMHintToolBtnArea.Create(area, GMRect(cCtlSpace, 0, cDlgBtnSize, cDlgBtnSize), // GMAreaAlign(ealAligned, ealCentered, ealFixed, ealCentered, True), OnBtnHelpClick, '', Ord(fmbHelp), // MainDlgBtnImg, RStrNameMaskHelp, RStrNameMaskHelpText)); ActiveControl := FEditor; end; procedure TGMConnectionStrEditDlg.DoneDialog(const ASetData: Boolean); var i: LongInt; line: TGMString; len: Word; begin //if WndStyle and cMinimizedOrMaximized = 0 then // GMStoreRect(UserSettings, GMAbsPath(cPrsMaskEditDlg), cPrsMaskEditDlg, LayoutBounds); if ASetData then begin // FConnectionString := ''; for i:=0 to GMSendObjMessage(FEditor, EM_GETLINECOUNT) - 1 do begin len := GMSendObjMessage(FEditor, EM_LINELENGTH, GMSendObjMessage(FEditor, EM_LINEINDEX, i)); SetLength(line, len + SizeOf(len)); Inc(len); // <- allow to write terminating zero TGMChar Move(len, PGMChar(line)^, SizeOf(len)); GMSendObjMessage(FEditor, EM_GETLINE, i, LPARAM(PGMChar(line))); FConnectionString := GMStringJoin(FConnectionString, cCnStrEntrySep, GMStrip(Copy(line, 1, len-1), cCnStrEntrySep)); end; end; end; function TGMConnectionStrEditDlg.GetText: TGMString; begin Result := FConnectionString; end; { --------------------------------- } { ---- TGMShowConnectionStrDlg ---- } { --------------------------------- } constructor TGMShowConnectionStrDlg.Create(const AConnectionString, ATitle, ALargeText: TGMString; const AParent: TGMWndObj; const ABkgndColor: COLORREF; const ARefLifeTime: Boolean); var clientArea: TObject; txt: TGMString; // cnStorage: IGMConnectionStringStorage; begin inherited Create(cNullRect, cSizeDlgWndStyle, 0, ATitle, AParent, nil, 0, ABkgndColor, ARefLifeTime); FSizeConstraints.MinSize := WndSizeFromClientSize(GMPoint(230, 300)); //FLayoutBounds := GMCenteredWndRect(GMPoint(300, 500), AParent); //FLayoutBounds := GMCenteredWndRect(GMRectSize(GMLoadDlgRect(UserSettings, '\' + cPrsFolderWindow, cPrsFolderWindow, GMPoint(300, 500), 0)), AParent); //FLayoutBounds := GMLoadDlgRect(UserSettings, GMAbsPath(cPrsMaskEditDlg), cPrsMaskEditDlg, GMPoint(300, 500), AParent); FLayoutBounds := GMCenteredWndRect(GMPoint(400, 500), AParent); OwnArea(TGMDlgHeaderArea.Create(self, cNullRect, cTopAligned, ALargeText, ATitle)); clientArea := OwnArea(TGMUiArea.Create(Self, cNullRect, cClientAligned, ABkgndColor)); //cnStorage := TGMConnectionStringStorage.Create(AConnectionString); //txt := GMNamesAndValuesAsString(cnStorage.Obj.Values, GMVarToConnectionStrLiteral, cNewLine, cCnStrValSep); FEditor := OwnArea(TGMFramedEdit.Create(-Int64(clientArea), GMRect(cCtlSpace, cCtlSpace, cCtlSpace, cCtlSpace), cClientAligned, txt, cVisibleTabstop or ES_READONLY or ES_MultiLine or WS_HSCROLL or WS_VSCROLL)) as TGMFramedEdit; //area := OwnArea(TGMDlgBottomArea.Create(Self, [dbkClose], dbkClose)); //OwnArea(TGMHintToolBtnArea.Create(area, GMRect(cCtlSpace, 0, cDlgBtnSize, cDlgBtnSize), // GMAreaAlign(ealAligned, ealCentered, ealFixed, ealCentered, True), OnBtnHelpClick, '', Ord(fmbHelp), // MainDlgBtnImg, RStrNameMaskHelp, RStrNameMaskHelpText)); ActiveControl := FEditor; end; //procedure TGMShowConnectionStrDlg.DoneDialog(const ASetData: Boolean); //begin //inherited; // //end; function TGMShowConnectionStrDlg.GetText: TGMString; begin Result := FEditor.Text; end; { --------------------------- } { ---- TGMOdbcConnectDlg ---- } { --------------------------- } constructor TGMOdbcConnectDlg.Create(const APosition: TRect; const AStyle, AExStyle: DWORD; const AText: TGMString; const AParent: TGMWndObj; const ADlgData: Pointer; const AMenu: HMENU; const ABkgndColor: COLORREF; const ARefLifeTime: Boolean); //const cSpace = c2CtlSpace; var DlgClient, Panel: TObject; begin inherited Create(cNullRect, AStyle or cSizeDlgWndStyle, AExStyle, RStrOdbcConnectDlgCaption, AParent, ADlgData, AMenu, ABkgndColor, ARefLifeTime); FSizeConstraints.MinSize := WndSizeFromClientSize(GMPoint(350, 450)); FLayoutBounds := GMCenteredWndRect(FSizeConstraints.MinSize, AParent); OwnArea(TGMDlgHeaderArea.Create(Self, cNullRect, cTopAligned, RStrOdbc, RStrSelectDSN, cResOdbcDlgHeaderIcon)); DlgClient := OwnArea(TGMUiArea.Create(Self, cNullRect, cClientAligned)); Panel := OwnArea(TGMUiArea.Create(DlgClient, GMRect(cCtlSpace, cCtlSpace, cCtlSpace, cCtlSpace), cClientAligned, vLightGray)); GMAssignRoundedAreaProperties(Panel); //GMSetObjMultiFrame(DlgClient, frsNone, frsLowered, cAllEdges, frkTile, cDlgFrmSpace); // frkTile frkFlat FCnPropsUIArea := OwnArea(TGMOdbcConnectionPropUIArea.Create(Panel, GMRect(c2CtlSpace, c2CtlSpace, c2CtlSpace, 0), cClientAligned, OnDatachanged, vLightGray)) as TGMOdbcConnectionPropUIArea; //GMSetObjMultiFrame(FCnPropsUIArea, frsNone, frsLowered, cAllEdges, frkTile); // frkTile frkFlat FBottomArea := OwnArea(TGMDlgBottomArea.Create(Self, cDlgBtnsOkCancel, dbkOk)) as TGMDlgBottomArea; FBtnODBCAdminDlg := OwnArea(TGMMinWidthBtn.Create(-Int64(FBottomArea), GMRect(0, 0, c2CtlSpace, cDlgBtnHeight), cDlgBtnAlign, RStrOdbcAdminDlg + cStr_More, OnOdbcAdminDlgClick, cVisibleTabstop)) as TGMButton; ActiveControl := FCnPropsUIArea.FComboBoxDSN; MessageBeep(MB_ICONQUESTION); end; procedure TGMOdbcConnectDlg.SetupControls; begin GMEnableWindow(FBottomArea.Buttons[dbkOk], Length(GMStrip(FCnPropsUIArea.FComboBoxDSN.Text)) > 0); end; procedure TGMOdbcConnectDlg.OnDatachanged(const NewName: TGMString); begin SetupControls; end; procedure TGMOdbcConnectDlg.GetDlgData; var odbcCnProperties: IGMOdbcConnectProperties; begin odbcCnProperties := TGMOdbcConnectProperties.CreateFromIntf(IUnknown(DlgData), nil, True); FCnPropsUIArea.ConnectProperties := odbcCnProperties; end; //function TGMOdbcConnectDlg.CanClose(const ASetData: Boolean): Boolean; //begin //if ASetData and (GMStrip(FComboBoxDSN.Text) = '') then raise EGMException.ObjError(RStrNoEmptyDSN, Self, 'CanClose'); //Result := inherited CanClose(ASetData); //end; procedure TGMOdbcConnectDlg.DoneDialog(const ASetData: Boolean); begin if ASetData and (FCnPropsUIArea.ConnectProperties <> nil) then FCnPropsUIArea.ConnectProperties.Obj.AssignToIntf(IUnknown(DlgData)); end; procedure TGMOdbcConnectDlg.OnOdbcAdminDlgClick(const Sender: TObject); begin // // A simple call to SQLManageDataSources would do. // But the ODBC Admin Dialog on WinXP isn't safe against common control 6.0 manifest! - very stupid! // So we create the ODBC Admin Dialog via CreateProcess and wait for the process to terminate. // //if GMWinVersion <= wvWin2000 then if GMWinVersion <> wvWinXP then begin if SQLManageDataSources(Handle) then FCnPropsUIArea.FillupComboBoxDSN; end else begin GMEnableWindow(Self, False); try if GMExecProcess('OdbcAd32.exe', 0, True) = 0 then FCnPropsUIArea.FillupComboBoxDSN; finally GMEnableWindow(Self, True); SetForegroundWindow(Handle); // BringWindowToTop(Handle); SetActiveWindow(ActiveWindow); end; end; end; end.