Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Execute Python code in QM
#1
These functions can be used to execute Python code in QM.

Python setup

1. Download Python 32-bit (not 64-bit) from https://www.python.org/downloads/windows/
    Note: may not work with Python 3.12 and later. Works with 3.11.
2. Uninstall other versions of 32-bit Python.
3. Run the downloaded Python installer as administrator.
4. Check "Add python.exe to PATH".
5. Install.
6. Run cmd as administrator. Run it directly from explorer (eg Start menu), else it may inherit old environment variables.
7. In cmd run: where python
    It should print one or more paths. One of them must be of the new installed 32-bit Python. Copy it without "\python.exe" to the clipboard.
8. In cmd change current directory to the copied. Example:
    cd C:\Users\me\AppData\Local\Programs\Python\Python312-32
9. In cmd run: python -m pip install --upgrade pywin32
10. In cmd run one of the following. The first installs just what need for QM, the second something more.
    python Lib\site-packages\win32comext\axscript\client\pyscript.py
    python Scripts/pywin32_postinstall.py -install
11. Exit QM (not just close window). Run QM again. Now QM Python functions should work.

--
The SETUP instructions in the downloaded macro are now obsolete.


Attached Files
.qml   Python.qml (Size: 10 KB / Downloads: 1,209)
#2
Is there anyway to capture output of a "print" statement in python to a QM string or to QM output window?
Macro test PythonExec1
Code:
Copy      Help
PythonExec ""

#ret
print("Hello World!")
#3
If the QM macro is a console exe, Python print() will write to its console.

Else:

Function PythonPrintToQM
Code:
Copy      Help
;Redirects Python print() function output to QM output.

;REMARKS
;print() will be redirected in all Python code added by PythonExec or PythonAddCode that are called after calling this function in current thread.

;EXAMPLE
;PythonPrintToQM
;PythonExec ""
;
;#ret
;print("test")
;print("") # empty line
;print("one\ntwo") # multiline
;print(2) # number
;print("list", 1, 2, 3)
;print("list2", 1, 2, 3, sep=", ")


PythonAddCode ""

#ret
import sys
import ctypes
import win32gui

def printQM(*a, sep = ' '):
,s = ""
,for v in a:
,,if(s != ""): s += sep
,,s += str(v)
,
,if(printQM.hwndQM == 0): printQM.hwndQM=win32gui.FindWindow("QM_Editor", None)
,
,ctypes.windll.user32.SendMessageW(printQM.hwndQM, 12, -1, s)
printQM.hwndQM = 0

print = printQM

Macro test PythonPrintToQM
Code:
Copy      Help
out
PythonPrintToQM
PythonExec ""


#ret
print("test")
print("") # empty line
print("one\ntwo") # multiline
print(2) # number
print("list", 1, 2, 3)
print("list2", 1, 2, 3, sep=", ")


Or alternative:

Macro Python print output to QM - alternative
Code:
Copy      Help
out
PythonExec ""


#ret

def Script():
,print("test")
,print("") # empty line
,print("one\ntwo") # multiline
,print(2) # number


# ---------------------------------------------------------------------------------
# Put your Python script in the Script() function. Don't need to change other code.

import sys
import ctypes
import os
import win32gui

class PrintRedirector(object):
,def __init__(self):
,,self.hwndQM=win32gui.FindWindow("QM_Editor", None)
,
,def write(self, message):
,,if(message=='\n'): return
,,ctypes.windll.user32.SendMessageW(self.hwndQM, 12, -1, message)

sys.stdout = PrintRedirector()
try: Script()
finally: sys.stdout = sys.__stdout__
#4
Thanks a lot for your "PrintToQM" workarounds. They worked as expected. Big Grin
#5
I downloaded from the website http://www.activestate.com/activepython/downloads the latest 2.7.13 operating tests, there has been an error

My system version is: win7 64-bit


Attached Files Image(s)
   
#6
I tested ActiveState Python 2.7.13 now, and it does not work.

Try the second option - https://www.python.org/ . I did not test its newest version 3.6.2. The older version 3.5.2 works on my Windows 7 64-bit.
#7
I tested the new version of python3.7 to run successfully.  Smile

Step 1 Download pyton_3.7:
https://www.python.org/ftp/python/3.7.0/...-3.7.0.exe

Step 2 Download pywin32_3.7:
Select pywin32-223.win32-py3.7.exe
https://github.com/mhammond/pywin32/releases
You can directly click on the link below to download
pywin32-223.win32-py3.7.exe

Step 3 Download QM extension
http://www.quickmacros.com/forum/attachment.php?aid=592

I want to know, in QM3, can it be called like this? Huh

I generated the exe file, but I put the exe file together with the already installed python3.7 and it will not run on another computer.

How modify the code and I can implement the above requirements?  thank you very much  Heart


Attached Files Image(s)
   
#8
Quote:I want to know, in QM3, can it be called like this?
I googled how Python can be used in C#. The most popular are these 2 methods: 1. Save code in a file and run the Python command line program that executes the file. 2. IronPython. But I'm sure in C# also can be used the COM method like here in QM. And probably the 4-th method - like in C. Also found "Python for .NET", not tested.
Quote:I generated the exe file, but I put the exe file together with the already installed python3.7 and it will not run on another computer.
I tested now Python 3.7.2. Works without problems.
Maybe not installed pywin32. Or installed Python 64 bit. Need 32 bit. Or did not add to PATH when installing.
I installed Python in Q:\Python37. When installing, I choose to install for all users, add to PATH, and removed the PATH length limitation. Everything else is standard.
#9
Thank you for your reply, maybe I didn’t describe it clearly.

1. I installed python3.7 and pywin32 on my computer. I found that pywin32 is installed in the \Lib\site-packages\ folder of python. I tested the python script test file in QM, it can run successfully, then I Generated exe file with QM

2. I have another computer. I don't want to install python3.7 and pywin32. I want to copy the python installation folder installed on the first computer directly to the same folder as exe. Is there any way to run the exe file?

I think that Python sets the environment variable when it is installed. This is the key to success.

How to modify the Python script code in QM, set environment variables, and run exe file directly on any computer? This is very convenient, portable and easy to use.

My English is not good, I used Google Translate  Big Grin

The following code can't run successfully  Huh


Function py_test
Code:
Copy      Help
out
PythonExec ""


#ret

def Script():
,i = int(raw_input('Net profit:'))
,arr = [1000000,600000,400000,200000,100000,0]
,rat = [0.01,0.015,0.03,0.05,0.075,0.1]
,r = 0
,for idx in range(0,6):
,,if i>arr[idx]:
,,,r+=(i-arr[idx])*rat[idx]
,,,print (i-arr[idx])*rat[idx]
,,,i=arr[idx]
,print r


# ---------------------------------------------------------------------------------
# Put your Python script in the Script() function. Don't need to change other code.

import sys
import ctypes
import os
import win32gui

class PrintRedirector(object):
,def __init__(self):
,,self.hwndQM=win32gui.FindWindow("QM_Editor", None)
,
,def write(self, message):
,,if(message=='\n'): return
,,ctypes.windll.user32.SendMessageW(self.hwndQM, 12, -1, message)

sys.stdout = PrintRedirector()
try: Script()
finally: sys.stdout = sys.__stdout__
#10
I saw Python has a version that can be redistributed with applications, but did not test it. It guess it would work only when executing the command line Python, not through COM like we do here.
#11
Hello, in QM3, support python scripts? Smile

I found the tool to run python under .net , the link below.


https://ironpython.net
#12
Maybe. I did not test it.
#13
I found a python version that don't need to install. Double-click Python35.cmd directly to enter python shell mode
How does QM call it directly? is it possible?

Python35.cmd  Code:
 
Code:
Copy      Help
 
@echo off
CD /d "%~dp0"
set "PATH=%CD%\Main\;%CD%\Main\Scripts\;%PATH%"
if "%~f1"=="" (
if exist "%~dp0Main\used.li" (
echo Init pip ...
python -m pip install -U pip
del /f /q "%~dp0Main\used.li"
)
python
) else (
python "%~f1"
pause>NUL
)


Attached Files
.zip   Python35.zip (Size: 9.35 MB / Downloads: 562)
#14
Use RunConsole2.
#15
It's easier to use (powershell + ironpython) without installing pywin32 and without installing python Tongue
The grammar is simpler and easier to understand

https://ironpython.net
#16
Unzip the attachment IPY2.7.9 to the desktop and run the following code
But I have a problem, the result will show extra characters, how to remove it?
Huh

I think there may be a better way to use ironpython in QM2, without using powershell Idea


Macro IPY
Code:
Copy      Help
str s.expandpath("$desktop$\IPY\IronPython.dll")
int i=50
_s=
F
;[reflection.assembly]::LoadFrom("{s}")
;$py = [ironpython.hosting.python]::CreateEngine()
;$py.Execute("print {i}+4")

PsCmd3 _s "" str's1
mes s1



Attached Files Image(s)
   

.zip   IPY2.7.9.zip (Size: 5.06 MB / Downloads: 528)
#17
IronPython should be used directly from C#, not through PowerShell. In QM can be used C#, but without intellisense. Therefore at first test C# code in Visual Studio. Then either copy C# code to QM, or run your C# app from QM.
#18
Thank you for your reply, I prefer to use powershell, because the PS syntax is simpler, don't need to install Visual Studio, the system comes with powershell ISE
#19
Executing python function successfully Smile


Macro IPY fun
Code:
Copy      Help
str s.expandpath("$desktop$\IPY\IronPython.dll")
_s=
F
;[reflection.assembly]::LoadFrom("{s}")
;$py = [ironpython.hosting.python]::CreateEngine()
;$pyv = $py.CreateScope()
;$pyc = $py.CreateScriptSourceFromString(    
;"
;def fun():
;;;;;print 'hello from example function'
;");
;$pyc.Execute($pyv)
;$py.Operations.Invoke($pyv.GetVariable("fun"));
PsCmd3 _s "" str's1
mes s1

Remove extra GAC ​​characters  Smile

 [reflection.assembly]::LoadFrom("{s}") | Out-Null


Forum Jump:


Users browsing this thread: 5 Guest(s)