diff --git a/Modules/DelphiFMX/DelphiFMX.dpr b/Modules/DelphiFMX/DelphiFMX.dpr new file mode 100644 index 00000000..0e1ff9aa --- /dev/null +++ b/Modules/DelphiFMX/DelphiFMX.dpr @@ -0,0 +1,25 @@ +library DelphiFMX; + +uses + SysUtils, + Classes, + uMain in 'uMain.pas'; + +{$I ..\..\Source\Definition.Inc} + +exports + // This must match the pattern "PyInit_[ProjectName]" + // So if the project is named DelphiFMX then + // the export must be PyInit_DelphiFMX + PyInit_DelphiFMX; +{$IFDEF MSWINDOWS} +{$E pyd} +{$ENDIF} +{$IFDEF LINUX} +{$SONAME 'DelphiFMX'} + +{$ENDIF} + +begin +end. + diff --git a/Modules/DelphiFMX/DelphiFMX.dproj b/Modules/DelphiFMX/DelphiFMX.dproj new file mode 100644 index 00000000..12e25d06 --- /dev/null +++ b/Modules/DelphiFMX/DelphiFMX.dproj @@ -0,0 +1,820 @@ + + + True + Library + Release + None + DelphiFMX.dpr + Win64 + {0C4154A5-D276-4D62-BA30-564FACD77917} + 19.1 + 3 + + + true + + + true + Base + true + + + true + Base + true + + + true + Base + true + + + true + Base + true + + + true + Cfg_2 + true + true + + + DelphiFMX + 00400000 + System;Xml;Data;Datasnap;Web;Soap;Vcl;$(DCC_Namespace) + true + CompanyName=;FileDescription=;FileVersion=1.0.0.0;InternalName=;LegalCopyright=;LegalTrademarks=;OriginalFilename=;ProductName=;ProductVersion=1.0.0.0;Comments=;CFBundleName= + 1033 + + + Debug + Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;Bde;$(DCC_Namespace) + + + Debug + Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;$(DCC_Namespace) + + + 0 + RELEASE;$(DCC_Define) + false + 0 + + + DEBUG;$(DCC_Define) + true + false + + + (None) + + + + MainSource + + + + Base + + + Cfg_1 + Base + + + Cfg_2 + Base + + + + Delphi.Personality.12 + + + + + DelphiFMX.dpr + + + + + + + true + + + + + true + + + + + true + + + + + DelphiFMX.dll + true + + + + + 1 + + + 0 + + + + + classes + 1 + + + classes + 1 + + + + + res\xml + 1 + + + res\xml + 1 + + + + + library\lib\armeabi-v7a + 1 + + + + + library\lib\armeabi + 1 + + + library\lib\armeabi + 1 + + + + + library\lib\armeabi-v7a + 1 + + + + + library\lib\mips + 1 + + + library\lib\mips + 1 + + + + + library\lib\armeabi-v7a + 1 + + + library\lib\arm64-v8a + 1 + + + + + library\lib\armeabi-v7a + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + res\values-v21 + 1 + + + res\values-v21 + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + res\drawable + 1 + + + res\drawable + 1 + + + + + res\drawable-xxhdpi + 1 + + + res\drawable-xxhdpi + 1 + + + + + res\drawable-ldpi + 1 + + + res\drawable-ldpi + 1 + + + + + res\drawable-mdpi + 1 + + + res\drawable-mdpi + 1 + + + + + res\drawable-hdpi + 1 + + + res\drawable-hdpi + 1 + + + + + res\drawable-xhdpi + 1 + + + res\drawable-xhdpi + 1 + + + + + res\drawable-mdpi + 1 + + + res\drawable-mdpi + 1 + + + + + res\drawable-hdpi + 1 + + + res\drawable-hdpi + 1 + + + + + res\drawable-xhdpi + 1 + + + res\drawable-xhdpi + 1 + + + + + res\drawable-xxhdpi + 1 + + + res\drawable-xxhdpi + 1 + + + + + res\drawable-xxxhdpi + 1 + + + res\drawable-xxxhdpi + 1 + + + + + res\drawable-small + 1 + + + res\drawable-small + 1 + + + + + res\drawable-normal + 1 + + + res\drawable-normal + 1 + + + + + res\drawable-large + 1 + + + res\drawable-large + 1 + + + + + res\drawable-xlarge + 1 + + + res\drawable-xlarge + 1 + + + + + res\values + 1 + + + res\values + 1 + + + + + 1 + + + 1 + + + 0 + + + + + 1 + .framework + + + 1 + .framework + + + 0 + + + + + 1 + .dylib + + + 1 + .dylib + + + 0 + .dll;.bpl + + + + + 1 + .dylib + + + 1 + .dylib + + + 1 + .dylib + + + 1 + .dylib + + + 1 + .dylib + + + 0 + .bpl + + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 1 + + + 1 + + + + + + + + Contents\Resources + 1 + + + Contents\Resources + 1 + + + + + library\lib\armeabi-v7a + 1 + + + library\lib\arm64-v8a + 1 + + + 1 + + + 1 + + + 1 + + + 1 + + + 1 + + + 1 + + + 0 + + + + + library\lib\armeabi-v7a + 1 + + + + + 1 + + + 1 + + + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + ..\$(PROJECTNAME).app.dSYM\Contents\Resources\DWARF + 1 + + + + + + + + 1 + + + 1 + + + 1 + + + + + Assets + 1 + + + Assets + 1 + + + + + Assets + 1 + + + Assets + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\LaunchScreenImage.imageset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + ..\$(PROJECTNAME).launchscreen\Assets\AppIcon.appiconset + 1 + + + + + + + + + + + + + + + False + False + False + False + True + True + False + False + + + 12 + + + + + diff --git a/Modules/DelphiFMX/TestFMX.py b/Modules/DelphiFMX/TestFMX.py new file mode 100644 index 00000000..252a0add --- /dev/null +++ b/Modules/DelphiFMX/TestFMX.py @@ -0,0 +1,46 @@ +from DelphiFMX import * + +class MainForm(Form): + + def __init__(self, Owner): + self.Caption = "A FMX Form..." + self.SetBounds(10, 10, 500, 400) + + self.lblHello = Label(self) + self.lblHello.SetProps(Parent=self, Text="Hello Python") + self.lblHello.SetBounds(10, 10, 300, 24) + + self.edit1 = Edit(self) + self.edit1.SetProps(Parent=self) + self.edit1.SetBounds(10, 30, 250, 24) + + self.button1 = Button(self) + self.button1.Parent = self + self.button1.SetBounds(270,24,100,30) + self.button1.Text = "Add" + self.button1.OnClick = self.Button1Click + + self.lb1 = ListBox(self) + self.lb1.Parent = self + self.lb1.SetBounds(10,60,300,300) + + self.OnClose = self.MainFormClose + + def MainFormClose(self, Sender, Action): + Action.Value = caFree + Application.Terminate + + def Button1Click(self, Sender): + self.lb1.Items.Add(self.edit1.Text) + self.edit1.Text = "" + +def main(): + Application.Initialize() + Application.Title = "MyDelphiApp" + f = MainForm(Application) + f.Show() + #FreeConsole() + Application.Run() + +main() + diff --git a/Modules/DelphiFMX/uMain.pas b/Modules/DelphiFMX/uMain.pas new file mode 100644 index 00000000..d8f16cfa --- /dev/null +++ b/Modules/DelphiFMX/uMain.pas @@ -0,0 +1,56 @@ +unit uMain; + +interface + +uses PythonEngine; + +function PyInit_DelphiFMX: PPyObject; cdecl; + +implementation + +uses WrapDelphi, WrapDelphiFMX; + +var + gEngine : TPythonEngine; + gModule : TPythonModule; + gDelphiWrapper : TPyDelphiWrapper; + +// This must match the pattern "PyInit_[ProjectName]" +// So if the project is named DelphiFMX then +// the function must be PyInit_DelphiFMX +function PyInit_DelphiFMX: PPyObject; +begin + try + gEngine := TPythonEngine.Create(nil); + gEngine.AutoFinalize := False; + gEngine.UseLastKnownVersion := False; + // Adapt to the desired python version - Will only work with this version + gEngine.RegVersion := '3.9'; + gEngine.DllName := 'python39.dll'; + + gModule := TPythonModule.Create(nil); + gModule.Engine := gEngine; + // This must match the ProjectName and the function name pattern + gModule.ModuleName := 'DelphiFMX'; + + gDelphiWrapper := TPyDelphiWrapper.Create(nil); + gDelphiWrapper.Engine := gEngine; + gDelphiWrapper.Module := gModule; + + gEngine.LoadDll; + except + end; + Result := gModule.Module; +end; + +initialization + gEngine := nil; + gModule := nil; + gDelphiWrapper := nil; +finalization + gEngine.Free; + gModule.Free; + gDelphiWrapper.Free; +end. + + diff --git a/Packages/Delphi/Delphi 10.4+/PythonFmx.dpk b/Packages/Delphi/Delphi 10.4+/PythonFmx.dpk index e9cf1053..5bce1043 100644 --- a/Packages/Delphi/Delphi 10.4+/PythonFmx.dpk +++ b/Packages/Delphi/Delphi 10.4+/PythonFmx.dpk @@ -48,6 +48,8 @@ contains WrapFmxShapes in '..\..\..\Source\fmx\WrapFmxShapes.pas', WrapFmxStdCtrls in '..\..\..\Source\fmx\WrapFmxStdCtrls.pas', WrapFmxTypes in '..\..\..\Source\fmx\WrapFmxTypes.pas', - WrapDelphiFmx in '..\..\..\Source\fmx\WrapDelphiFmx.pas'; + WrapDelphiFmx in '..\..\..\Source\fmx\WrapDelphiFmx.pas', + WrapFmxEdit in '..\..\..\Source\fmx\WrapFmxEdit.pas', + WrapFmxListBox in '..\..\..\Source\fmx\WrapFmxListBox.pas'; end. diff --git a/Source/fmx/WrapDelphiFmx.pas b/Source/fmx/WrapDelphiFmx.pas index 5bd1b3b5..fd2efc20 100644 --- a/Source/fmx/WrapDelphiFmx.pas +++ b/Source/fmx/WrapDelphiFmx.pas @@ -11,6 +11,8 @@ implementation WrapFireDac, WrapFmxTypes, WrapFmxStdCtrls, + WrapFmxEdit, + WrapFmxListBox, WrapFmxActnList, WrapFmxComCtrls, WrapFmxDialogs, diff --git a/Source/fmx/WrapFmxEdit.pas b/Source/fmx/WrapFmxEdit.pas new file mode 100644 index 00000000..0106e229 --- /dev/null +++ b/Source/fmx/WrapFmxEdit.pas @@ -0,0 +1,105 @@ +{$I ..\Definition.Inc} + +unit WrapFmxEdit; + +interface + +uses + FMX.Edit, PythonEngine, WrapFmxTypes, WrapFmxControls; + + +type + TPyDelphiCustomEdit = class(TPyDelphiPresentedControl) + private + function GetDelphiObject: TCustomEdit; + procedure SetDelphiObject(const Value: TCustomEdit); + public + class function DelphiObjectClass: TClass; override; + // Properties + property DelphiObject: TCustomEdit read GetDelphiObject + write SetDelphiObject; + end; + + TPyDelphiEdit = class(TPyDelphiCustomEdit) + private + function GetDelphiObject: TEdit; + procedure SetDelphiObject(const Value: TEdit); + public + class function DelphiObjectClass: TClass; override; + // Properties + property DelphiObject: TEdit read GetDelphiObject + write SetDelphiObject; + end; + +implementation + +uses + WrapDelphi; + +{ Register the wrappers, the globals and the constants } +type + TEditRegistration = class(TRegisteredUnit) + public + function Name: string; override; + procedure RegisterWrappers(APyDelphiWrapper: TPyDelphiWrapper); override; + procedure DefineVars(APyDelphiWrapper: TPyDelphiWrapper); override; + end; + +{ TEditRegistration } + +procedure TEditRegistration.DefineVars(APyDelphiWrapper: TPyDelphiWrapper); +begin + inherited; +end; + +function TEditRegistration.Name: string; +begin + Result := 'Edit'; +end; + +procedure TEditRegistration.RegisterWrappers( + APyDelphiWrapper: TPyDelphiWrapper); +begin + inherited; + APyDelphiWrapper.RegisterDelphiWrapper(TPyDelphiCustomEdit); + APyDelphiWrapper.RegisterDelphiWrapper(TPyDelphiEdit); +end; + +{ TPyDelphiCustomEdit } + +class function TPyDelphiCustomEdit.DelphiObjectClass: TClass; +begin + Result := TCustomEdit; +end; + +function TPyDelphiCustomEdit.GetDelphiObject: TCustomEdit; +begin + Result := TCustomEdit(inherited DelphiObject); +end; + +procedure TPyDelphiCustomEdit.SetDelphiObject(const Value: TCustomEdit); +begin + inherited DelphiObject := Value; +end; + +{ TPyDelphiEdit } + +class function TPyDelphiEdit.DelphiObjectClass: TClass; +begin + Result := TEdit; +end; + +function TPyDelphiEdit.GetDelphiObject: TEdit; +begin + Result := TEdit(inherited DelphiObject); +end; + +procedure TPyDelphiEdit.SetDelphiObject(const Value: TEdit); +begin + inherited DelphiObject := Value; +end; + +initialization + RegisteredUnits.Add(TEditRegistration.Create); + +end. diff --git a/Source/fmx/WrapFmxListBox.pas b/Source/fmx/WrapFmxListBox.pas new file mode 100644 index 00000000..1cb29538 --- /dev/null +++ b/Source/fmx/WrapFmxListBox.pas @@ -0,0 +1,133 @@ +{$I ..\Definition.Inc} + +unit WrapFmxListBox; + +interface + +uses + FMX.ListBox, WrapFmxTypes, WrapFmxControls, WrapFmxLayouts, PythonEngine; + +type + TPyListBoxItem = class(TPyDelphiTextControl) + private + function GetDelphiObject: TListBoxItem; + procedure SetDelphiObject(const Value: TListBoxItem); + public + class function DelphiObjectClass: TClass; override; + property DelphiObject: TListBoxItem read GetDelphiObject + write SetDelphiObject; + end; + + TPyDelphiCustomListBox = class(TPyDelphiScrollBox) + private + function GetDelphiObject: TCustomListBox; + procedure SetDelphiObject(const Value: TCustomListBox); + public + class function DelphiObjectClass: TClass; override; + // Properties + property DelphiObject: TCustomListBox read GetDelphiObject + write SetDelphiObject; + end; + + TPyDelphiListBox = class(TPyDelphiCustomListBox) + private + function GetDelphiObject: TListBox; + procedure SetDelphiObject(const Value: TListBox); + public + class function DelphiObjectClass: TClass; override; + // Properties + property DelphiObject: TListBox read GetDelphiObject + write SetDelphiObject; + end; + +implementation + +uses + WrapDelphi; + +{ Register the wrappers, the globals and the constants } +type + TListBoxRegistration = class(TRegisteredUnit) + public + function Name: string; override; + procedure RegisterWrappers(APyDelphiWrapper: TPyDelphiWrapper); override; + procedure DefineVars(APyDelphiWrapper: TPyDelphiWrapper); override; + end; + +{ TListBoxRegistration } + +procedure TListBoxRegistration.DefineVars(APyDelphiWrapper: TPyDelphiWrapper); +begin + inherited; +end; + +function TListBoxRegistration.Name: string; +begin + Result := 'ListBox'; +end; + +procedure TListBoxRegistration.RegisterWrappers( + APyDelphiWrapper: TPyDelphiWrapper); +begin + inherited; + APyDelphiWrapper.RegisterDelphiWrapper(TPyListBoxItem); + APyDelphiWrapper.RegisterDelphiWrapper(TPyDelphiCustomListBox); + APyDelphiWrapper.RegisterDelphiWrapper(TPyDelphiListBox); +end; + +{ TPyListBoxItem } + +class function TPyListBoxItem.DelphiObjectClass: TClass; +begin + Result := TListBox; +end; + +function TPyListBoxItem.GetDelphiObject: TListBoxItem; +begin + Result := TListBoxItem(inherited DelphiObject); +end; + +procedure TPyListBoxItem.SetDelphiObject(const Value: TListBoxItem); +begin + inherited DelphiObject := Value; +end; + +{ TPyDelphiCustomListBox } + +class function TPyDelphiCustomListBox.DelphiObjectClass: TClass; +begin + Result := TCustomListBox; +end; + +function TPyDelphiCustomListBox.GetDelphiObject: TCustomListBox; +begin + Result := TCustomListBox(inherited DelphiObject); +end; + +procedure TPyDelphiCustomListBox.SetDelphiObject(const Value: TCustomListBox); +begin + inherited DelphiObject := Value; +end; + +{ TPyDelphiListBox } + +class function TPyDelphiListBox.DelphiObjectClass: TClass; +begin + Result := TListBox; +end; + +function TPyDelphiListBox.GetDelphiObject: TListBox; +begin + Result := TListBox(inherited DelphiObject); +end; + + +procedure TPyDelphiListBox.SetDelphiObject(const Value: TListBox); +begin + inherited DelphiObject := Value; +end; + +initialization + RegisteredUnits.Add(TListBoxRegistration.Create); + +end.