Jump to content

Juan C.Cilleruelo

Members
  • Content Count

    103
  • Joined

  • Last visited

Posts posted by Juan C.Cilleruelo


  1. I have in my plans the use of PyVista inside a Delphi application.
     

    I'm currently using OpenSCAD to draw my graphics, but I think PyVista will be a better solution.

     

    But, I still have not initiated searching for this idea's viability.

     

    Have you advanced something in this field? 

     

    I need to achieve the rendering of surfaces and more speed in the drawing. Do you think this is possible?


  2. 3 hours ago, uefi said:

    Dude, all I needed was in the code below. Why are you bringing me some utter nonsense? And you offer me some shitty code?

    Welcome to the unique forum in the world, whose members will try to understand you, with the goal of helping you to solve some of your problems!

    Good luck with your search for help! 

     

    (sincerely)


  3. 2 hours ago, uefi said:

    The code is too intricately written and this is not exactly what I want, I just need to get the result of the script execution into a variable after PythonEngine1.ExecString

     

    You probably need a Math Parser component. The goal of a scripting language is not this. 
    I think that Python doesn't have this concept of "result." 

    If anyone can confirm or deny this affirmation, please do. 

     

    With a Scripting language you need to assign your result to a variable and after take the value of this variable from Delphi. 


  4. Try this method. 

     

    I've tried to document it over the code. 

     

    I do not use TPythonDelphiVar because have some connotations of visual components that we don't need. 

     

    This example assumes you know the type of the variable whose value you want to recover.

     

    procedure TForm1.Button1Click(Sender: TObject);
    var PythonEngine :TPythonEngine;
        PythonModule :TPythonModule;
        Pointer      :PPyObject;     //Pointer to create a value inside the Engine.
        VarColor     :Variant;       //Variant to recover the Color from the Engine
        PasColor     :string;        //The color in Pascal.
    begin
       PythonEngine := TPythonEngine.Create(nil);
       {Documentation explains that these properties are for Embedded (not registered)
        installations of Python }
       PythonEngine.AutoLoad            := False;
       PythonEngine.DllName             := 'python311.dll';
       PythonEngine.DllPath             := 'C:\Views\senCille\bin\Win64\Python';
       PythonEngine.APIVersion          := 1013;
       PythonEngine.RegVersion          := '3.11';
       PythonEngine.UseLastKnownVersion := False;
       PythonEngine.SetPythonHome('C:\Views\senCille\bin\Win64\Python');

     

       {We create a Module that points to a special one inside PythonEngine}
       PythonModule := TPythonModule.Create(nil);
       PythonModule.Engine                := PythonEngine;
       PythonModule.ModuleName            := '__main__';

     

      try
         PythonEngine.LoadDll;

     

         {Now we are going to create a Variable inside PythonEngine}

         {p point to and Unicode string created inside the PyEngine}
         Pointer := PythonEngine.PyUnicode_FromString('Dark Blue');
         {Create the Variable Color inside PythonEngine and assigns p as his value}
         PythonModule.SetVar('Color', Pointer);


         {At this moment, the value pointed by p has two references:
          Pointer  : a pointer inside the Delphi source and
          Color : The variable inside PythonEngine.
          We call Py_DecRef to decrement this counter and allow PythonEngine to
          free this variable when not more need it}
         PythonEngine.Py_DecRef(Pointer);

     

         {We use a python script to assign a value to Color instance inside PythonEngine}

         PythonEngine.ExecString('Color = "Dark Blu"');

     

     

         {Now we retrieve a PythonEngine value contained in Color variable}
         VarColor := PythonModule.GetVarAsVariant('Color');

         {if the local variant don't have a value, we assign on by default}
         if not (VarColor = unassigned) then begin
            {We can use the Variant in our program, but we prefer a string type}
            PasColor := VarColor;
         end
         else PasColor := 'No color Assigned';

     

         ShowMessage('Value = ' + PasColor);
      finally
         PythonModule.Free;
         PythonEngine.Free;
      end;
    end;

    DemoVar.zip


  5. 2 hours ago, pyscripter said:

    Call you delphi module say "delphimodule"  and in your script:

     

    import delphimodule

    print(delphimodule.QUANTITY);

     

    or 

    from delphimodule import QUANTITY

    print(QUANTITY)

     

    Please look at the demos, before asking questions here and do yourself a favour.  Do watch the two video tutorials. It is only two hours viewing and will save you masses of time if you plan to do any serious work with P4D.

     

    I made it.   The error now says "ModuleNotFoundError"   No module named "delphimodule".

     

    Do you continue thinking that is better this conversation that try the code I added? 

     

    Demo on the fly.zip


  6. 2 hours ago, pyscripter said:

    Please do.  You will do everyone a favour.

    All the demos are about complex examples. Sharing Objects and complex things. Only applicable to try to demonstrate that the person doing it is more intelligent than the rest of the mortals. 
    No examples apply to daily cases like creating integer variables, string variables, float variables, and easy things, like sharing easy methods between python and Delphi. Always complex examples. I think the people that developed these examples are "really very intelligent," but for me, all of them are useless. 

    And the help they give?

    I wasted my time creating an example. A very easy and straightforward example to show what the problem is. And the attitude of the creators is.....

    No one tries my code: excuses, excuses, and more excuses. The last, they supposed that I don't watch video tutorials or I don't tried the source code of the demos. 

    I made all of this. But the authors try to exacerbate me. I'm sure. 

    The solution remains here. Tryin the added code and see that the components don't work when you create it on the fly. 
    It is easy. But it is more convenient to have this type of thread where the creators finally stay over the poor users. 

    Is this a serious component set? 

     


  7. 11 minutes ago, pyscripter said:

     

    Please look at the demos, before asking questions here and do yourself a favour.  Do watch the two video tutorials. It is only two hours viewing and will save you masses of time if you plan to do any serious work with P4D.

    After visualizing all the video tutorials, seeing the demos, and seeing what kind of support the components have, I'm seriously thinking of abandoning this line of investigation.

     

    I see these components are still very, very, very, very green. 


  8. 9 minutes ago, pyscripter said:

    Call you delphi modue say "delphimodule"  and in your script:

     

    import delphimodule

    print(delphimodule.QUANTITY);

     

    Please look at the demos, before asking questions here.

    Can you please download the included example and try to run it?  

    I beg. 

    Is not a failure of my code. It is a failure of the behavior of the components. 

     

    If you try it and I'm not in the truth. I will recognize that the components are working well. 

     


  9. Just now, pyscripter said:

    Call you delphi modue say "delphimodule"  and in your script:

     

    import delphimodule

    print(delphimodule.QUANTITY);

     

    Please look at the demos, before asking questions here.

    Why do they work when I use visual components?
    Why can't I use functions and variables created in the __main__ module? What is the matter?
    Why do I need to create different scripts if I create the components visually than if I create them on the fly?

    All of this is absurd, true?

    I've read all the demos and a lot of demos on the web. Of course.  

     

    I'm going to try this, but this doesn't solve the fact of the different behavior with visual and no visual form of creating the components. 


  10. Just now, pyscripter said:

    Also do not call the module __main__.  This is name is reserved for the main python module.

    Yes, but that is where I want to declare the functions and the variables. 

    I've seen a lot of examples that do this. 

     

    I don't want to include my members in another module.

     

    Anyway, with the version of the visual component works very well with the __main__ module.


  11. 2 hours ago, pyscripter said:

    Create and link all non-visual components before you call LoadDLL. 

    This is not the solution to all the problems.

     

    This is the more accurate form of doing it. 

     

    Don't work!!!!!

     

     

     

    var p :PPyObject;
    begin
       FOutput := TStringList.Create;
       FPythonIO := TPythonInputOutput.Create(Self);
       FPythonIO.UnicodeIO     := True;
       FPythonIO.RawOutput     := False;
       FPythonIO.OnSendUniData := OnSendUniData;

      
          FPyEngine := TPythonEngine.Create(nil);
          FPyEngine.AutoLoad            := False;
          FPyEngine.DllName             := 'python311.dll';
          FPyEngine.DllPath             := 'C:\Views\senCille\bin\Win64\Python';
          FPyEngine.APIVersion          := 1013;
          FPyEngine.RegVersion          := '3.11';
          FPyEngine.UseLastKnownVersion := False;
          FPyEngine.OnBeforeLoad        := PyEngineBeforeLoad;
          FPyEngine.InitScript.Add('import sys'                         );
          FPyEngine.InitScript.Add('print ("Python Dll: ", sys.version)');
          FPyEngine.InitScript.Add('print (sys.copyright)'              );
          FPyEngine.InitScript.Add('print'                              );
          FPyEngine.IO := FPythonIO;

     

          FPyModule := TPythonModule.Create(nil);
          FPyModule.Engine := FPyEngine;
          FPyModule.Name   := '__main__';
          FPyModule.OnInitialization := PyModuleInitialization;

     

          FPyEngine.LoadDll;


          FPyModule.Initialize;
     

          p := FPyEngine.PyLong_FromLong(1);
          FPyModule.SetVar('QUANTITY', p);
          FPyEngine.Py_DecRef(p);

    +++++++

    I can't load DLL after PyModule creation or link because I get an error calling Initialize;

    The script admits the declaration of variables or functions but doesn't recognize either when I run the script.

    I'm sure it is a problem with the components. I'm investigating it. 

    It probably is creating the variables and the modules in a missing module or something like this.




     


  12. 24 minutes ago, pyscripter said:

    Set PyEngine.IO before you call LoadDLL

     

    Redirection is setup by TPythonEngine.Initialize, which is called by LoadDLL.

    Ok. 

    The version with Visual components works with this order of lines:

     

    ...

    {$IFDEF VISUAL_COMPONENTS}
          PyEngine.IO := FPythonIO;

          PyEngine.LoadDll;

          p := PyEngine.PyLong_FromLong(1);
          PyModule.SetVar('QUANTITY', p);
          PyEngine.Py_DecRef(p);
       {$ELSE}

    ...

     

     

       I'm still fighting with the version of non-visual components. 

    If you want try it, I'm going to thank you.

     

     


  13. 1 hour ago, pyscripter said:

    You can use TPythonInputOutput event handlers to log python output to file or produce output in a console application.

    I'm creating TPythonInputOutput on the fly, with visual components. 

     

    procedure TForm1.FormCreate(Sender: TObject);
    var p :PPyObject;
    begin
       FOutput := TStringList.Create;
       FPythonIO := TPythonInputOutput.Create(Self);
       FPythonIO.UnicodeIO     := True;
       FPythonIO.RawOutput     := False;
       FPythonIO.OnSendUniData := OnSendUniData;

     

       {$IFDEF VISUAL_COMPONENTS}
          PyEngine.LoadDll;

          p := PyEngine.PyLong_FromLong(1);
          PyModule.SetVar('QUANTITY', p);
          PyEngine.Py_DecRef(p);

          PyEngine.IO := FPythonIO;
       {$ELSE}

     

    With the next code in OnSendUniData EventHandler:

     

         FOutput.Add(PChar(Data));

     

    And this code in the Button Execute On Click Event Handler:

     

     PyEngine.CheckError();
          PyEngine.ExecStrings(Memo1.Lines);
          if FOutput.Count > 0 then begin
             Memo2.Lines.Assign(FOutput);
          end;

     

    And I always get FOutput.Count = 0.   It seems the ExecStrings(Memo1.Lines) don't work well with on the fly created TPythonInputOutput component.

     

    I Include the complete code.

    Demo on Fly.zip


  14. On 1/11/2023 at 7:30 PM, KoRiF said:

    As far as I understand your question, you just need get access to the Python error output, this is usual situation:
    https://github.com/pyscripter/python4delphi/blob/master/Demos/Demo01/Unit1.dfm#L119

    Unfortunately, this solution doesn't work well when you don't use visual components.

     

    I need to recover the error messages in a TStringList instance and if there are not empty, translate them to the user, probably in a log file.

     

    The first thing is to create the TMemo programmatically without a visual parent, but this doesn't work in the current version of VCL. 

     

    TMemo visual component needs a Parent to allow add strings in his Lines (TStringList) property, raising an exception if you make this without the Parent assigned.

    https://quality.embarcadero.com/browse/RSP-40383

     

    I will try to solve this without this visual component. 


  15. The same problem with the class TPythonModule.  If I create in visual form, including it on a form, it works well. If I create it on the fly, the next statements 

     

    FPythonModule.AddDelphiMethod('ComponentCount', ComponentCount, 'ComponentCount');
    FPythonModule.AddDelphiMethod('GetPRICE'      , GetPRICE      , 'GetPRICE'      );

     

    run, but when I try to use ComponentCount in my Python Script, does not exist. 

     

    what's happening?   

     


  16. I'm having the following problem with TPythonDelphiVar component.


    I use the next method to create one instance of this component on-the-fly:

    function TForm1.NewVariable(AVarName :string):TPythonDelphiVar;
    begin
       Result := TPythonDelphiVar.Create(nil);
       Result.Engine    := PythonEngine;
       Result.Module    := '__main__';
       Result.VarName   := AVarName;
       Result.Initialize;
    end;

    I have a Private variable declared in the TForm1class, like this:

    public
        FVariable :TPythonDelphiVar;


    And I use the next code to create on-the-fly my variable QUANTITY:

    FVariable := NewVariable('QUANTITY');
    FVariable.Value := 1.0;


    All seems ok, but when I execute the program, and I try to print the value of QUANTITY:

    (Phyton script).

    print(QUANTITY)

    I get the following message error in a message error window: "NameError: 'QUANTITY' is not defined. " 

    And in the output memo of the PythonEngine, the next one:

    Traceback (most recent call last):
      File "<string>", line 13, in <module>
    NameError: name 'QUANTITY' is not defined


    I can't understand why creating the TPythonDelphiVar on-the-fly doesn't work while creating the same component in design time works well. 

    Do you understand what the problem is?


  17. 13 hours ago, KoRiF said:

    As far as I understand your question, you just need get access to the Python error output, this is usual situation:
    https://github.com/pyscripter/python4delphi/blob/master/Demos/Demo01/Unit1.dfm#L119

    Thank you!!!

     

    That is better than what I'm looking for.

     

    I was looking for an example of exception management. Still, this solution is better because it allows the final user to generate error messages inside the Python code that can return to the application.

     

    I'm going to investigate this line.

     

    The type of scripts I expect that the final user write doesn't need any returned message. Because of this, I can consider any message the final user includes as a warning of an error message. 

     

    Great. Thanks.

     

    Now I need to embed this functionality in an on-the-fly component.

×