Jump to content

FranzB

Members
  • Content Count

    55
  • Joined

  • Last visited

Everything posted by FranzB

  1. based on demo code 34 I wrote this code with the following new features a) create Pythonengine and PythonInOut at run time b) config pythonengine from an INI file c) find/exchange config parameter for different python installations , UNIX systems here in this forum d) set path to python libs via this INI file, no need for recompile Issues with this code a) OS=WINDOWS : text output of python is not shown in the memo. Guess this is due to the fact that I create the PythonInOut at run time and the is no property defined ( memo, using FMX or VCL ???) b) OS=LINUX : text output of python is not shown in the memo but in the calling CMD Window of this app. Guess a fix of a) will also help here c) pls. share addition setting to python libs like numpy etc. , what settings worked on your computer , how to find our the correct parameter on my computer etc. ....... i added the complete project, pls. share your improvement ideas 🙂 the used config file for windows did not have any problem calling a few NumPy statements [PythonEngine] DLLName=python39.dll DLLPath= AutoFinalize=0 AutoLoad=0 AutoUnload=0 RedirectIO=0 UseLastKnownVersion=0 UseWindowsConsole=0 the used config file for LINUX, simple code runs well, but I failed to set the path to the NumPy lib on the target system [PythonEngine] DLLName=libpython3.6m.so DLLPath=/usr/lib/x86_64-linux-gnu/ AutoFinalize=0 AutoLoad=0 AutoUnload=0 RedirectIO=0 UseLastKnownVersion=0 Config_linux .ini Config_windows.ini P4Ddemo34Config.dpr demopython34config.fmx demopython34config.pas
  2. good news : changed the code according your help and also created new *.ini file -> text is written to output file now 🙂 bad news : its difficult to find the correct parameter settings on a client computer system - there are to many options where python might be installed ...... https://github.com/pyscripter/python4delphi/wiki/FindingPython action : improve finding and setting of correct parameters ..... otherwise an app won't run on a different computer procedure TPythonEngineConfig.SetPythonengineValues(PythonEngine : TPythonEngine); var FPyVersions: TPythonVersions; begin /// /// convert this https://github.com/pyscripter/python4delphi/wiki/FindingPython /// into a small automatic setting of parameter /// PythonEngine.UseLastKnownVersion := Self.UseLastKnownVersion; if Self.UseLastKnownVersion then begin {$IFDEF MSWINDOWS} FPyVersions := GetRegisteredPythonVersions; FPyVersions[0].AssignTo(PythonEngine); {$ENDIF} {$IFDEF LINUX} /// see https://en.delphipraxis.net/topic/4700-getregisteredpythonversions-for-linux/ {$ENDIF} end else begin PythonEngine.DllName := Self.DllName; PythonEngine.DllPath := Self.DllPath; PythonEngine.AutoFinalize := Self.AutoFinalize; PythonEngine.AutoLoad := Self.AutoLoad; PythonEngine.AutoUnload := Self.AutoUnload; PythonEngine.RedirectIO := Self.RedirectIO; PythonEngine.UseWindowsConsole := Self.UseWindowsConsole; end; end; demo project : demopython34config.fmx demopython34config.pas P4Ddemo34Config.dpr screen dumps.
  3. yes, tried debugging function TForm_P4Deval.PythonInputOutputSendUniData(Sender: TObject); is never called , even I assigned this function during the create components function for data output. I'm using FMX framework and lastest Delphi 10.4.2 , full working code is attached below FPythonInOut.UnicodeIO := True; FPythonInOut.RawOutput := True; FPythonInOut.OnSendUniData := PythonInputOutputSendUniData; {$IFDEF MSWINDOWS} FPyVersions := GetRegisteredPythonVersions; FPyVersions[0].AssignTo(FPythonEngine); {$ENDIF} FPythonEngineConfig.SetPythonengineValues(FPythonEngine); FPythonEngine.Loaddll; FPythonEngine.IO := FPythonInOut; Config_windows.ini demopython34config.fmx demopython34config.pas P4Ddemo34Config.dpr
  4. I still need a helping hand on one failure of the demo34Extend sample : Q : why is python text output not written to the output memo in Delphi app, python engine for sure is running, see post above procedure TForm_P4Deval.btn_CreatePythonEnviromentClick(Sender: TObject); begin // run this function prior to execute python code FPythonEngine := TPythonEngine.Create(nil); FPythonInOut := TPythonInputOutput.Create(nil); try FPythonInOut.UnicodeIO := True; FPythonInOut.RawOutput := True; FPythonInOut.OnSendUniData := PythonInputOutputSendUniData; {$IFDEF MSWINDOWS} FPyVersions := GetRegisteredPythonVersions; FPyVersions[0].AssignTo(FPythonEngine); {$ENDIF} FPythonEngineConfig.SetPythonengineValues(FPythonEngine); FPythonEngine.Loaddll; FPythonEngine.IO := FPythonInOut; { TPythonModule } FPythonModule1 := TPythonModule.Create(Self); FPythonModule1.Name := 'PythonModule1'; FPythonModule1.Engine := FPythonEngine; FPythonModule1.ModuleName := 'spam'; with FPythonModule1.Errors.Add do begin Name := 'PointError'; ErrorType := etClass; end; with FPythonModule1.Errors.Add do begin Name := 'EBadPoint'; ErrorType := etClass; ParentClass.Name := 'PointError'; end; except on E: Exception do writeln(E.ClassName, ': ', E.Message); end; end; procedure TForm_P4Deval.btn_FreePythonEnviromentClick(Sender: TObject); begin FPythonEngine.Free; FPythonInOut.Free; end; Config_windows.ini demopython34config.fmx demopython34config.pas P4Ddemo34Config.dpr
  5. yes , here comes a numpy short demo on windows .... execution is perfect I installed numpy via pip , did not need to set a DLL path see screen dump (on LINUX i don't have admin rights to install software using pip, will report results later - need other LINUX computer ) # demo script import matplotlib.pyplot as plt import numpy as np x = np.arange(0,8*np.pi,0.1) # start,stop,step y = np.cos(x) *1/(1+x) plt.plot(x,y) plt.show()
  6. working also on this topic, and need to find out how get the correct settings on different UNIX system, I started from your code and did this code now :
  7. I have created the following simple application which should run on WINDOWS and LINUX using FMX framework and creating delphi4python components on run time . Why does this demo code not show any output result ? Most important line of code is this , or not ...? PythonInOut.OnSendUniData := PythonInputOutputSendUniData; I know this source https://blogs.embarcadero.com/learn-how-to-dynamically-create-and-destroy-python4delphi-components-with-a-delphi-windows-app/ but I intend to create a minimum code sequence type TForm1 = class(TForm) memoIn: TMemo; Splitter1: TSplitter; memoOut: TMemo; Panel1: TPanel; Button1: TButton; btnLoadScript: TButton; dlgOpen_pythonscript: TOpenDialog; btn_CreatePythonEnviroment: TButton; btn_FreePythonEnviroment: TButton; procedure Button1Click(Sender: TObject); procedure PythonInputOutputSendUniData(Sender: TObject; const Data: string); procedure FormCreate(Sender: TObject); procedure FormDestroy(Sender: TObject); procedure btnLoadScriptClick(Sender: TObject); procedure btn_CreatePythonEnviromentClick(Sender: TObject); procedure btn_FreePythonEnviromentClick(Sender: TObject); private { Private declarations } FOutputStream: TMemoryStream; FCriticalSection: TCriticalSection; public { Public declarations } PythonEngine: TPythonEngine; PythonInOut: TPythonInputOutput; end; var Form1: TForm1; implementation {$R *.fmx} procedure TForm1.btnLoadScriptClick(Sender: TObject); begin if dlgOpen_pythonscript.Execute then begin memoIn.Lines.Clear; memoIn.Lines.LoadFromFile(dlgOpen_pythonscript.FileName) end; end; /// /// did not drop components on a form , create components at run time ... /// procedure TForm1.btn_CreatePythonEnviromentClick(Sender: TObject); begin PythonEngine := TPythonEngine.Create(nil); PythonInOut := TPythonInputOutput.Create(nil); try PythonEngine.AutoLoad := true; {$IFDEF LINUX} PythonEngine.DllName := 'libpython3.6m.so'; PythonEngine.DllPath := '/usr/lib/x86_64-linux-gnu/'; {$ENDIF} {$IFDEF MSWINDOWS} PythonEngine.DllName := 'python310.dll'; PythonEngine.DllPath := ''; {$ENDIF} PythonEngine.AutoFinalize := true; PythonEngine.AutoLoad := true; PythonEngine.AutoUnload := true; PythonEngine.RedirectIO := true; PythonEngine.UseLastKnownVersion := true; PythonEngine.Loaddll; PythonEngine.IO := PythonInOut; PythonInOut.RawOutput := True; PythonInOut.OnSendUniData := PythonInputOutputSendUniData; except on E: Exception do writeln(E.ClassName, ': ', E.Message); end; end; procedure TForm1.Button1Click(Sender: TObject); begin PythonEngine.ExecString(UTF8Encode(memoIn.Text)); end; procedure TForm1.FormCreate(Sender: TObject); begin FOutputStream := TMemoryStream.Create; FCriticalSection := TCriticalSection.Create; end; procedure TForm1.FormDestroy(Sender: TObject); begin FOutputStream.Free; FCriticalSection.Free; end; procedure TForm1.PythonInputOutputSendUniData(Sender: TObject; const Data: string); { FMX TMemo is slow when adding many lines one by one. To avoid this we accumulate output and print it in one go. The critical section allows for multiple threads to print. If you use this code then set PythonInputOuput.RawOutput to True A simpler solution would be to set RawOuput to False and then do MemoOut.Lines.Add(Data); MemoOut.GoToTextEnd; This should be good enough if python does not produce a massive amount of output. } Var ScheduleWrite: Boolean; begin if Data = '' then Exit; FCriticalSection.Enter; try ScheduleWrite := FOutputStream.Size = 0; FOutputStream.Write(Data[1], Length(Data) * 2); if ScheduleWrite then TThread.ForceQueue(nil, procedure var WS: string; begin FCriticalSection.Enter; try if FOutputStream.Size > 0 then begin SetLength(WS, FOutputStream.Size div 2); FOutputStream.Position := 0; FOutputStream.Read(WS[1], Length(WS) * 2); FOutputStream.Size := 0; if (memoOut.Lines.Count > 0) and (memoOut.Lines[memoOut.Lines.Count - 1] <> '') then memoOut.Lines.Add(''); memoOut.Text := memoOut.Text + WS; memoOut.GoToTextEnd; end; finally FCriticalSection.Leave; end; end); finally FCriticalSection.Leave; end; end; end.
  8. FranzB

    create delphi4python at run time

    did a code rework and need to ask a different question
  9. FranzB

    Can't load package Python$(Auto).bpl

    update to 10.4.2 done installation is now perfect ! Many thanks for your help
  10. how to use madexcept inside a DLL? the DLL does not contain any form the DLL does not write any test to a console - just a set of data processing functions - drag and drop of mashi component does not work
  11. FranzB

    madexcept inside a DLL

    using : http://help.madshi.net/HowToUseMadExcept.htm I added : uses madexcept, system,.... ....; end; but after a run time error in my console / DLL application no madshi form is created , or any other error report ....
  12. I use 2 Polygon definitions as in the code below type TPolygon = array of TPoint T4Polygon = array [1..4] of TPoint ; .... function ProcessPolygon (aPoly : TPolygon); begin end; is there a better way to call the function ProcessPolygon with a variable of the T4Polygon ? I don't want to copy the data from one data type to the other, writing overloaded functions seems to my also not the best solution , any better idea ?
  13. I want to use this class with an array of TPoint type. type TedgearryPoints = Array [1..4] of TPoint ; type TGEORect = class ..... private : Fedges : TedgearryPoints ; public : ..... property edges : TedgearryPoints read Fedge write Fedge; end; but the code fails because I can not assign data to the individual edges MyGEORECT.Edges[1] , compiles says "[dcc64 Error] GEOUnit.pas(1303): E2064 Left side cannot be assigned to "
  14. but this means : I have to write extra code if I want to assign just one edge with your solution above via property or if I want to assign all 4 edge with one command making the edge variable public: allows both, but I think from class design this look not that good type TGEORect = class private : ..... public : edges : TedgearryPoints ; end;
  15. I installed delphi 10.4 , but now I failed adding components via GETIT with error msg , How to solve ?
  16. FranzB

    Migration from BDE paradox to TFDtable or other options

    some basic video
  17. I tried to execute the FMX demos of Python for Delphi ( . https://github.com/pyscripter/python4delphi ) OS = WIN 64 no problem I can compile this code for LINUX / UBUNTU as well, but I can't execute error msg Exception EAccessViolation in module libicuuc.so.60 at 00007FA5A18A15EB. Access violation at address 00007FA5A18A15EB, accessing address 0000000003A73000 how to fix this error ?? Remark : same exe copied to RED HAT V 7 system, execution seems to be perfect after 1st. test ..... questions goes more to help on config my ubuntu system 😞
  18. i like to use https://github.com/malcolmgroves/FluentLiveBindings var BindSourceDB1: TBindSourceDB; begin aServername := edt_Servername.Text; adatabasename := edt_databasename.Text; ConnecttoDatabase(aServername, adatabasename, aConnection); aQuery.SQL.Text := 'select * from Mytab'; aQuery.Active := True; BindSourceDB1 := TBindSourceDB.Create(Self); BindSourceDB1.DataSet := aQuery; BindingsList1.BindGrid(grd_objecttab).ToBindSource(BindSourceDB1); but run time error msg is now like below , any idea for this error ?
  19. is there an option to increase the amount of information written to the XML outputfile ? a) I want to add all parameter for a testcase to the XML log b) I want to add some information during the test case execution to the XML log my code follow the basic instructions given for DUNITX var runner : ITestRunner; results : IRunResults; logger : ITestLogger; nunitLogger : ITestLogger; begin try //Check command line options, will exit if invalid TDUnitX.CheckCommandLine; //Create the test runner runner := TDUnitX.CreateRunner; //Tell the runner to use RTTI to find Fixtures runner.UseRTTI := True; //tell the runner how we will log things //Log to the console window logger := TDUnitXConsoleLogger.Create(true); runner.AddLogger(logger); //Generate an NUnit compatible XML File nunitLogger := TDUnitXXMLNUnitFileLogger.Create(TDUnitX.Options.XMLOutputFile); runner.AddLogger(nunitLogger); runner.FailsOnNoAsserts := False; //When true, Assertions must be made during tests; //Run tests results := runner.Execute; if not results.AllPassed then System.ExitCode := EXIT_ERRORS; {$IFNDEF CI} //We don't want this happening when running under CI. if TDUnitX.Options.ExitBehavior = TDUnitXExitBehavior.Pause then begin System.Write('Done.. press <Enter> key to quit.'); System.Readln; end; {$ENDIF} except on E: Exception do System.Writeln(E.ClassName, ': ', E.Message); end; end.
  20. FranzB

    Draw TBitmap

    I want to insert a bitmap on it's own left side again using canvas.drawbitmap function but actually this code does not do anything..... can't see my mistake here 😞 procedure InsertonMyleft(aBMP : TBitmap); var tempBMP: TBitmap; RecFull: TRectF; RecLeft: TRectF; begin tempBMP := TBitmap.Create; try aBMP.Canvas.BeginScene; tempBMP.Assign(localBMP); tempBMP.SaveToFile('c:\temp\debugme.bmp'); RecFull := RectF(0, 0, aBMP.Width, aBMP.Height); RecLeft := RectF(0, 0, round(aBMP.Width / 3), round(aBMP.Height / 1)); aBMP.Canvas.DrawBitmap(tempBMP, RecFull, RecLeft, 50, True); aBMP.Canvas.EndScene; aBMP.SaveToFile('c:\temp\debugme2.bmp'); finally tempBMP.Free; end; end;
  21. FranzB

    Draw TBitmap

    procedure InsertonMyleft(aBMP: TBitmap); var tempBMP: TBitmap; RecFull: TRectF; RecLeft: TRectF; begin tempBMP := TBitmap.Create; try // tempBMP.Assign(aBMP); // tempBMP.SaveToFile('c:\temp\debugme.bmp'); tempBMP.LOadfromFile('c:\temp\debugme3.bmp'); RecFull := RectF(0, 0, aBMP.Width - 2, aBMP.Height - 2); RecLeft := RectF(0, 0, round(aBMP.Width / 3), round((aBMP.Height - 1) / 1)); aBMP.Canvas.BeginScene; aBMP.Canvas.DrawBitmap(tempBMP, RecFull, RecLeft, 50, True); aBMP.Canvas.EndScene; aBMP.SaveToFile('c:\temp\debugme2.bmp'); finally tempBMP.Free; end; end; if I load a bitmap from a file , my code works fine but the assign sequence does not have the desired function, (insert the bmp on the left side) even the savetofile saved the correct bitmap content
  22. FranzB

    Draw TBitmap

    already changed to width-1 ...... see code above RecFull := RectF(0, 0, aBMP.Width-1, aBMP.Height-1); // size of full trect, 0,0,500,500
  23. FranzB

    Draw TBitmap

    I changed the code to make it a full separate process function like below , Trect full has correct size 0,0,500,500 and Trect left size is 0,0,250,500 image size is 501 x501 pixel but still no effect from this code 😞 procedure InsertonMyleft(aBMP : TBitmap); var tempBMP: TBitmap; RecFull: TRectF; RecLeft: TRectF; begin tempBMP := TBitmap.Create; try aBMP.Canvas.BeginScene; tempBMP.Assign(aBMP); tempBMP.SaveToFile('c:\temp\debugme.bmp'); RecFull := RectF(0, 0, aBMP.Width-1, aBMP.Height-1); // size of full trect, 0,0,500,500 RecLeft := RectF(0, 0, round((aBMP.Width-1) / 2), // just lest side round((aBMP.Height-1) / 1)); aBMP.Canvas.DrawBitmap(tempBMP, RecFull, RecLeft, 50, True); aBMP.Canvas.EndScene; aBMP.SaveToFile('c:\temp\debugme2.bmp'); finally tempBMP.Free; end; end;
×