forked from amazingfate/loongoffice
To enhance the compatibility between
- sf dictionaries
- python dicts
- arrays of PropertyValues
it was necessary to propose the support
of case-sensitive keys, i.e. keys are
different if a case-sensitive comparison
finds them different.
So far only not case-sensitive keys
were supported.
This required a re-visit of the implementation
of the ScriptForge.SF_Dictionary service. So far
it was built upon a Basic Collection class which
differentiates keys not case-sensitively. The
new implementation uses sorted arrays.
The invocation of the service is now:
dict = CreateScriptService("Dictionary", True/False)
True means case-sensitive keys.
Default = False, which preserves the compatibility
with the past.
ScriptForge uses dictionaries internally in
several places. For each of them it has been
assessed if the new attribute was justified
or not. For most of the contexts, it was.
The functionality makes sense only for Basic
user scripts.
The documentation of the Dictionary page
should be revised according to the new invocation
syntax.
Change-Id: If1f695bcbf1673a2b71c1e41487b1781caab71c2
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/173044
Tested-by: Jenkins
Reviewed-by: Jean-Pierre Ledure <jp@ledure.be>
999 lines
45 KiB
XML
999 lines
45 KiB
XML
<?xml version="1.0" encoding="UTF-8"?>
|
|
<!DOCTYPE script:module PUBLIC "-//OpenOffice.org//DTD OfficeDocument 1.0//EN" "module.dtd">
|
|
<script:module xmlns:script="http://openoffice.org/2000/script" script:name="SF_PythonHelper" script:language="StarBasic" script:moduleType="normal">REM =======================================================================================================================
|
|
REM === The ScriptForge library and its associated libraries are part of the LibreOffice project. ===
|
|
REM === Full documentation is available on https://help.libreoffice.org/ ===
|
|
REM =======================================================================================================================
|
|
|
|
Option Compatible
|
|
Option Explicit
|
|
|
|
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
|
|
''' SF_PythonHelper (aka Basic)
|
|
''' ===============
|
|
''' Singleton class implementing the "ScriptForge.Basic" service
|
|
''' Implemented as a usual Basic module
|
|
'''
|
|
''' The "Basic" service must be called ONLY from a PYTHON script
|
|
''' Service invocations: Next Python code lines are equivalent:
|
|
''' bas = CreateScriptService('ScriptForge.Basic')
|
|
''' bas = CreateScriptService('Basic')
|
|
'''
|
|
''' This service proposes a collection of methods to be executed in a Python context
|
|
''' to simulate the exact behaviour of the identical Basic builtin method.
|
|
''' Typical example:
|
|
''' bas.MsgBox('This has to be displayed in a message box')
|
|
'''
|
|
''' The service includes also an agnostic "Python Dispatcher" function.
|
|
''' It dispatches Python script requests to execute Basic services to the
|
|
''' appropriate properties and methods via dynamic call techniques
|
|
'''
|
|
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
|
|
|
|
REM ================================================================== EXCEPTIONS
|
|
|
|
REM ============================================================ MODULE CONSTANTS
|
|
|
|
REM ===================================================== CONSTRUCTOR/DESTRUCTOR
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function Dispose() As Variant
|
|
Set Dispose = Nothing
|
|
End Function ' ScriptForge.SF_PythonHelper Explicit destructor
|
|
|
|
REM ================================================================== PROPERTIES
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Property Get ObjectType As String
|
|
''' Only to enable object representation
|
|
ObjectType = "SF_PythonHelper"
|
|
End Property ' ScriptForge.SF_PythonHelper.ObjectType
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Property Get ServiceName As String
|
|
''' Internal use
|
|
ServiceName = "ScriptForge.Basic"
|
|
End Property ' ScriptForge.SF_PythonHelper.ServiceName
|
|
|
|
REM ============================================================== PUBLIC METHODS
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyCDate(ByVal DateArg As Variant) As Variant
|
|
''' Convenient function to replicate CDate() in Python scripts
|
|
''' Args:
|
|
''' DateArg: a date as a string or as a double
|
|
''' Returns:
|
|
''' The converted date as a UNO DateTime structure
|
|
''' If the input argument could not be recognized as a date, return the argument unchanged
|
|
''' Example: (Python code)
|
|
''' a = bas.CDate('2021-02-18')
|
|
|
|
Dim vDate As Variant ' Return value
|
|
Const cstThisSub = "Basic.CDate"
|
|
Const cstSubArgs = "datearg"
|
|
|
|
On Local Error GoTo Catch
|
|
vDate = Null
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
vDate = CDate(DateArg)
|
|
|
|
Finally:
|
|
If VarType(vDate) = V_DATE Then PyCDate = CDateToUnoDateTime(vDate) Else PyCDate = DateArg
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
On Local Error GoTo 0
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyCDate
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyConvertFromUrl(ByVal FileName As Variant) As String
|
|
''' Convenient function to replicate ConvertFromUrl() in Python scripts
|
|
''' Args:
|
|
''' FileName: a string representing a file in URL format
|
|
''' Returns:
|
|
''' The same file name in native operating system notation
|
|
''' Example: (Python code)
|
|
''' a = bas.ConvertFromUrl('file:////boot.sys')
|
|
|
|
Dim sFileName As String ' Return value
|
|
Const cstThisSub = "Basic.ConvertFromUrl"
|
|
Const cstSubArgs = "filename"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
sFileName = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
sFileName = ConvertFromUrl(FileName)
|
|
|
|
Finally:
|
|
PyConvertFromUrl = sFileName
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyConvertFromUrl
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyConvertToUrl(ByVal FileName As Variant) As String
|
|
''' Convenient function to replicate ConvertToUrl() in Python scripts
|
|
''' Args:
|
|
''' FileName: a string representing a file in native operating system notation
|
|
''' Returns:
|
|
''' The same file name in URL format
|
|
''' Example: (Python code)
|
|
''' a = bas.ConvertToUrl('C:\boot.sys')
|
|
|
|
Dim sFileName As String ' Return value
|
|
Const cstThisSub = "Basic.ConvertToUrl"
|
|
Const cstSubArgs = "filename"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
sFileName = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
sFileName = ConvertToUrl(FileName)
|
|
|
|
Finally:
|
|
PyConvertToUrl = sFileName
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyConvertToUrl
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyCreateUnoService(ByVal UnoService As Variant) As Variant
|
|
''' Convenient function to replicate CreateUnoService() in Python scripts
|
|
''' Args:
|
|
''' UnoService: a string representing the service to create
|
|
''' Returns:
|
|
''' A UNO object
|
|
''' Example: (Python code)
|
|
''' a = bas.CreateUnoService('com.sun.star.i18n.CharacterClassification')
|
|
|
|
Dim vUno As Variant ' Return value
|
|
Const cstThisSub = "Basic.CreateUnoService"
|
|
Const cstSubArgs = "unoservice"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
Set vUno = Nothing
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
Set vUno = CreateUnoService(UnoService)
|
|
|
|
Finally:
|
|
Set PyCreateUnoService = vUno
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyCreateUnoService
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyDateAdd(ByVal Add As Variant _
|
|
, ByVal Count As Variant _
|
|
, ByVal DateArg As Variant _
|
|
) As Variant
|
|
''' Convenient function to replicate DateAdd() in Python scripts
|
|
''' Args:
|
|
''' Add: The unit to add
|
|
''' Count: how many times to add (might be negative)
|
|
''' DateArg: a date as a com.sun.star.util.DateTime UNO structure
|
|
''' Returns:
|
|
''' The new date as a string in iso format
|
|
''' Example: (Python code)
|
|
''' a = bas.DateAdd('d', 1, bas.Now()) ' Tomorrow
|
|
|
|
Dim vNewDate As Variant ' Return value
|
|
Dim vDate As Date ' Alias of DateArg
|
|
Const cstThisSub = "Basic.DateAdd"
|
|
Const cstSubArgs = "add, count, datearg"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
vNewDate = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
If VarType(DateArg) = V_OBJECT Then
|
|
vDate = CDateFromUnoDateTime(DateArg)
|
|
Else
|
|
vDate = SF_Utils._CStrToDate(DateArg)
|
|
End If
|
|
vNewDate = DateAdd(Add, Count, vDate)
|
|
|
|
Finally:
|
|
If VarType(vNewDate) = V_DATE Then PyDateAdd = CDateToUnoDateTime(vNewDate) Else PyDateAdd = vNewDate
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyDateAdd
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyDateDiff(ByVal Add As Variant _
|
|
, ByVal Date1 As Variant _
|
|
, ByVal Date2 As Variant _
|
|
, ByVal WeekStart As Variant _
|
|
, ByVal YearStart As Variant _
|
|
) As Long
|
|
''' Convenient function to replicate DateDiff() in Python scripts
|
|
''' Args:
|
|
''' Add: The unit of the date interval
|
|
''' Date1, Date2: the two dates to be compared
|
|
''' WeekStart: the starting day of a week
|
|
''' YearStart: the starting week of a year
|
|
''' Returns:
|
|
''' The number of intervals expressed in Adds
|
|
''' Example: (Python code)
|
|
''' a = bas.DateDiff('d', bas.DateAdd('d', 1, bas.Now()), bas.Now()) ' -1 day
|
|
|
|
Dim lDiff As Long ' Return value
|
|
Dim vDate1 As Date ' Alias of Date1
|
|
Dim vDate2 As Date ' Alias of Date2
|
|
Const cstThisSub = "Basic.DateDiff"
|
|
Const cstSubArgs = "add, date1, date2, [weekstart=1], [yearstart=1]"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
lDiff = 0
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
If VarType(Date1) = V_OBJECT Then
|
|
vDate1 = CDateFromUnoDateTime(Date1)
|
|
Else
|
|
vDate1 = SF_Utils._CStrToDate(Date1)
|
|
End If
|
|
If VarType(Date2) = V_OBJECT Then
|
|
vDate2 = CDateFromUnoDateTime(Date2)
|
|
Else
|
|
vDate2 = SF_Utils._CStrToDate(Date2)
|
|
End If
|
|
lDiff = DateDiff(Add, vDate1, vDate2, WeekStart, YearStart)
|
|
|
|
|
|
Finally:
|
|
PyDateDiff = lDiff
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyDateDiff
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyDatePart(ByVal Add As Variant _
|
|
, ByVal DateArg As Variant _
|
|
, ByVal WeekStart As Variant _
|
|
, ByVal YearStart As Variant _
|
|
) As Long
|
|
''' Convenient function to replicate DatePart() in Python scripts
|
|
''' Args:
|
|
''' Add: The unit of the date interval
|
|
''' DateArg: The date from which to extract a part
|
|
''' WeekStart: the starting day of a week
|
|
''' YearStart: the starting week of a year
|
|
''' Returns:
|
|
''' The specified part of the date
|
|
''' Example: (Python code)
|
|
''' a = bas.DatePart('y', bas.Now()) ' day of year
|
|
|
|
Dim lPart As Long ' Return value
|
|
Dim vDate As Date ' Alias of DateArg
|
|
Const cstThisSub = "Basic.DatePart"
|
|
Const cstSubArgs = "add, datearg, [weekstart=1], [yearstart=1]"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
lPart = 0
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
If VarType(DateArg) = V_OBJECT Then
|
|
vDate = CDateFromUnoDateTime(DateArg)
|
|
Else
|
|
vDate = SF_Utils._CStrToDate(DateArg)
|
|
End If
|
|
lPart = DatePart(Add, vDate, WeekStart, YearStart)
|
|
|
|
|
|
Finally:
|
|
PyDatePart = lPart
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyDatePart
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyDateValue(ByVal DateArg As Variant) As Variant
|
|
''' Convenient function to replicate DateValue() in Python scripts
|
|
''' Args:
|
|
''' DateArg: a date as a string
|
|
''' Returns:
|
|
''' The converted date as a UNO DateTime structure
|
|
''' Example: (Python code)
|
|
''' a = bas.DateValue('2021-02-18')
|
|
|
|
Dim vDate As Variant ' Return value
|
|
Const cstThisSub = "Basic.DateValue"
|
|
Const cstSubArgs = "datearg"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
vDate = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
vDate = DateValue(DateArg)
|
|
|
|
Finally:
|
|
If VarType(vDate) = V_DATE Then PyDateValue = CDateToUnoDateTime(vDate) Else PyDateValue = vDate
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyDateValue
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyFormat(ByVal Value As Variant _
|
|
, ByVal Pattern As Variant _
|
|
) As String
|
|
''' Convenient function to replicate Format() in Python scripts
|
|
''' Args:
|
|
''' Value: a date or a number
|
|
''' Pattern: the format to apply
|
|
''' Returns:
|
|
''' The formatted value
|
|
''' Example: (Python code)
|
|
''' MsgBox bas.Format(6328.2, '##,##0.00')
|
|
|
|
Dim sFormat As String ' Return value
|
|
Dim vValue As Variant ' Alias of Value
|
|
Const cstThisSub = "Basic.Format"
|
|
Const cstSubArgs = "value, pattern"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
sFormat = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
If VarType(Value) = V_OBJECT Then vValue = CDateFromUnoDateTime(Value) ELse vValue = Value
|
|
If IsEmpty(Pattern) Or Len(Pattern) = 0 Then sFormat = Str(vValue) Else sFormat = Format(vValue, Pattern)
|
|
|
|
|
|
Finally:
|
|
PyFormat = sFormat
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyFormat
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyGetGuiType() As Integer
|
|
''' Convenient function to replicate GetGuiType() in Python scripts
|
|
''' Args:
|
|
''' Returns:
|
|
''' The GetGuiType value
|
|
''' Example: (Python code)
|
|
''' MsgBox bas.GetGuiType()
|
|
|
|
Const cstThisSub = "Basic.GetGuiType"
|
|
Const cstSubArgs = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
PyGetGuiType = GetGuiType()
|
|
|
|
|
|
Finally:
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
End Function ' ScriptForge.SF_PythonHelper.PyGetGuiType
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyGetSystemTicks() As Long
|
|
''' Convenient function to replicate GetSystemTicks() in Python scripts
|
|
''' Args:
|
|
''' Returns:
|
|
''' The GetSystemTicks value
|
|
''' Example: (Python code)
|
|
''' MsgBox bas.GetSystemTicks()
|
|
|
|
Const cstThisSub = "Basic.GetSystemTicks"
|
|
Const cstSubArgs = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
PyGetSystemTicks = GetSystemTicks()
|
|
|
|
|
|
Finally:
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
End Function ' ScriptForge.SF_PythonHelper.PyGetSystemTicks
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyGlobalScope(ByVal Library As Variant) As Object
|
|
''' Convenient function to replicate GlobalScope() in Python scripts
|
|
''' Args:
|
|
''' Library: "Basic" or "Dialog"
|
|
''' Returns:
|
|
''' The GlobalScope value
|
|
''' Example: (Python code)
|
|
''' MsgBox bas.GlobalScope.BasicLibraries()
|
|
|
|
Const cstThisSub = "Basic.GlobalScope.BasicLibraries" ' or DialogLibraries
|
|
Const cstSubArgs = ""
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
Select Case Library
|
|
Case "Basic"
|
|
PyGlobalScope = GlobalScope.BasicLibraries()
|
|
Case "Dialog"
|
|
PyGlobalScope = GlobalScope.DialogLibraries()
|
|
Case Else
|
|
End Select
|
|
|
|
Finally:
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
End Function ' ScriptForge.SF_PythonHelper.PyGlobalScope
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyInputBox(ByVal Msg As Variant _
|
|
, ByVal Title As Variant _
|
|
, ByVal Default As Variant _
|
|
, Optional ByVal XPosTwips As Variant _
|
|
, Optional ByVal YPosTwips As Variant _
|
|
) As String
|
|
''' Convenient function to replicate InputBox() in Python scripts
|
|
''' Args:
|
|
''' Msg: String expression displayed as the message in the dialog box
|
|
''' Title: String expression displayed in the title bar of the dialog box
|
|
''' Default: String expression displayed in the text box as default if no other input is given
|
|
''' XPosTwips: Integer expression that specifies the horizontal position of the dialog
|
|
''' YPosTwips: Integer expression that specifies the vertical position of the dialog
|
|
''' If XPosTwips and YPosTwips are omitted, the dialog is centered on the screen
|
|
''' The position is specified in twips.
|
|
''' Returns:
|
|
''' The entered value or "" if the user pressed the Cancel button
|
|
''' Example: (Python code)
|
|
''' a = bas.InputBox ('Please enter a phrase:', 'Dear User')
|
|
|
|
Dim sInput As String ' Return value
|
|
Const cstThisSub = "Basic.InputBox"
|
|
Const cstSubArgs = "msg, [title=''], [default=''], [xpostwips], [ypostwips]"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
sInput = ""
|
|
|
|
Check:
|
|
If IsMissing(YPosTwips) Then YPosTwips = 1
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
If IsMissing(XPosTwips) Then
|
|
sInput = InputBox(Msg, Title, Default)
|
|
Else
|
|
sInput = InputBox(Msg, Title, Default, XPosTwips, YPosTwips)
|
|
End If
|
|
|
|
Finally:
|
|
PyInputBox = sInput
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyInputBox
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function PyMsgBox(ByVal Text As Variant _
|
|
, ByVal DialogType As Variant _
|
|
, ByVal DialogTitle As Variant _
|
|
) As Integer
|
|
''' Convenient function to replicate MsgBox() in Python scripts
|
|
''' Args:
|
|
''' Text: String expression displayed as a message in the dialog box
|
|
''' DialogType: Any integer expression that defines the number and type of buttons or icons displayed
|
|
''' DialogTitle: String expression displayed in the title bar of the dialog
|
|
''' Returns:
|
|
''' The pressed button
|
|
''' Example: (Python code)
|
|
''' a = bas.MsgBox ('Please press a button:', bas.MB_EXCLAMATION, 'Dear User')
|
|
|
|
Dim iMsg As Integer ' Return value
|
|
Const cstThisSub = "Basic.MsgBox"
|
|
Const cstSubArgs = "text, [dialogtype=0], [dialogtitle]"
|
|
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
iMsg = -1
|
|
|
|
Check:
|
|
SF_Utils._EnterFunction(cstThisSub, cstSubArgs)
|
|
|
|
Try:
|
|
iMsg = MsgBox(Text, DialogType, DialogTitle)
|
|
|
|
Finally:
|
|
PyMsgBox = iMsg
|
|
SF_Utils._ExitFunction(cstThisSub)
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper.PyMsgBox
|
|
|
|
REM ============================================================= PRIVATE METHODS
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Public Function _PythonDispatcher(ByRef BasicObject As Variant _
|
|
, ByVal CallType As Variant _
|
|
, ByVal Script As Variant _
|
|
, ParamArray Args() As Variant _
|
|
) As Variant
|
|
''' Called from Python only
|
|
''' The method calls the method Script associated with the BasicObject class or module
|
|
''' with the given arguments
|
|
''' The invocation of the method can be a Property Get, Property Let or a usual call
|
|
''' NB: arguments and return values must not be 2D arrays
|
|
''' The implementation intends to be as AGNOSTIC as possible in terms of objects nature and methods called
|
|
''' The method returns the value effectively returned by the called component,
|
|
''' completed with additional metadata. The whole is packaged in a 1D array.
|
|
''' Args:
|
|
''' BasicObject: a module or a class instance - May also be the reserved string: "SF_Services"
|
|
''' CallType: one of the constants applicable to a CallByName statement + optional protocol flags
|
|
''' Script: the name of the method or property
|
|
''' Args: the arguments to pass to the method. Input arguments can contain symbolic constants for Null, Missing, etc.
|
|
''' Returns:
|
|
''' A 1D array:
|
|
''' [0] The returned value - scalar, object or 1D array
|
|
''' [1] The VarType() of the returned value
|
|
''' Null, Empty and Nothing have different vartypes but return all None to Python
|
|
''' Additionally, when array:
|
|
''' [2] Number of dimensions in Basic
|
|
''' Additionally, when Basic object:
|
|
''' [2] Module (1), Class instance (2) or UNO (3)
|
|
''' [3] The object's ObjectType
|
|
''' [4] The object's service name
|
|
''' [5] The object's name
|
|
''' When an error occurs Python receives None as a scalar. This determines the occurrence of a failure
|
|
|
|
Dim vReturn As Variant ' The value returned by the invoked property or method
|
|
Dim vReturnArray As Variant ' Return value
|
|
Dim vBasicObject As Variant ' Alias of BasicObject to avoid "Object reference not set" error
|
|
Dim iNbArgs As Integer ' Number of valid input arguments
|
|
Dim vArg As Variant ' Alias for a single argument
|
|
Dim vArgs() As Variant ' Alias for Args()
|
|
Dim sScript As String ' Argument of ExecuteBasicScript()
|
|
Dim vParams As Variant ' Array of arguments to pass to a ParamArray
|
|
Dim sObjectType As String ' Alias of object.ObjectType
|
|
Dim sServiceName As String ' Alias of BasicObject.ServiceName
|
|
Dim bBasicClass As Boolean ' True when BasicObject is a class
|
|
Dim sLibrary As String ' Library where the object belongs to
|
|
Dim bUno As Boolean ' Return value is a UNO object
|
|
Dim bDict As Boolean ' Return value is a Basic SF_Dictionary class instance
|
|
Dim oDict As Object ' SF_Dictionary class instance
|
|
Dim oObjDesc As Object ' _ObjectDescriptor type
|
|
Dim iDims As Integer ' # of dims of vReturn when array
|
|
Dim sess As Object : Set sess = ScriptForge.SF_Session
|
|
Dim i As Long, j As Long
|
|
|
|
' Conventional special input or output values
|
|
Const cstNoArgs = "+++NOARGS+++", cstSymEmpty = "+++EMPTY+++", cstSymNull = "+++NULL+++", cstSymMissing = "+++MISSING+++"
|
|
|
|
' https://support.office.com/en-us/article/CallByName-fonction-49ce9475-c315-4f13-8d35-e98cfe98729a
|
|
' Determines the CallType
|
|
Const vbGet = 2, vbLet = 4, vbMethod = 1, vbSet = 8
|
|
' Protocol flags
|
|
Const cstPost = 16 ' Requires a hardcoded post-processing
|
|
Const cstDictArg = 32 ' May contain a Dictionary argument
|
|
Const cstDateArg = 64 ' May contain a date argument
|
|
Const cstDateRet = 128 ' Return value can be a date
|
|
Const cstUno = 256 ' Return value can be a UNO object
|
|
Const cstArgArray = 512 ' Any argument can be a 2D array
|
|
Const cstRetArray = 1024 ' Return value can be an array
|
|
Const cstObject = 2048 ' 1st argument is a Basic object when numeric
|
|
Const cstHardCode = 4096 ' Method must not be executed with CallByName()
|
|
' Returned object nature
|
|
Const objMODULE = 1, objCLASS = 2, objDICT = 3, objUNO = 4
|
|
|
|
Check:
|
|
If SF_Utils._ErrorHandling() Then On Local Error GoTo Catch
|
|
_PythonDispatcher = Null
|
|
|
|
' Ignore Null basic objects (Null = Null or Nothing)
|
|
If IsNull(BasicObject) Or IsEmpty(BasicObject) Then GoTo Catch
|
|
|
|
' Reinterpret arguments one by one into vArgs
|
|
' - convert UNO dates/times
|
|
' - identify conventional NoArgs/Empty/Null/Missing constants
|
|
' - convert arrays of property values into Dictionary
|
|
iNbArgs = -1
|
|
vArgs = Array()
|
|
|
|
If UBound(Args) >= 0 Then
|
|
For i = 0 To UBound(Args)
|
|
vArg = Args(i)
|
|
' Are there arguments ?
|
|
If i = 0 And VarType(vArg) = V_STRING Then
|
|
If vArg = cstNoArgs Then Exit For
|
|
End If
|
|
' Is 1st argument a reference to a Basic object ?
|
|
If i = 0 And (( CallType And cstObject ) = cstObject) And SF_Utils._VarTypeExt(vArg) = V_NUMERIC Then
|
|
If vArg < 0 Or Not IsArray(_SF_.PythonStorage) Then GoTo Catch
|
|
If vArg > UBound(_SF_.PythonStorage) Then GoTo Catch
|
|
vArg = _SF_.PythonStorage(vArg)
|
|
' Is argument a symbolic constant for Null, Empty, ... , or a date, or a dictionary ?
|
|
ElseIf VarType(vArg) = V_STRING Then
|
|
If Len(vArg) = 0 Then
|
|
ElseIf vArg = cstSymEmpty Then
|
|
vArg = Empty
|
|
ElseIf vArg = cstSymNull Then
|
|
vArg = Null
|
|
ElseIf vArg = cstSymMissing Then
|
|
Exit For ' Next arguments must be missing also
|
|
End If
|
|
ElseIf VarType(vArg) = V_OBJECT Then
|
|
If ( CallType And cstDateArg ) = cstDateArg Then vArg = CDateFromUnoDateTime(vArg)
|
|
ElseIf ( CallType And cstDictArg ) = cstDictArg Then
|
|
If IsArray(vArg) Then
|
|
If UBound(vArg) >= 0 Then
|
|
If sess.UnoObjectType(vArg(0)) = "com.sun.star.beans.PropertyValue" Then
|
|
' Create a dictionary - keys in Python dicts are case-sensitive
|
|
Set oDict = CreateScriptService("ScriptForge.Dictionary", True)
|
|
oDict.ImportFromPropertyValues(vArg, Overwrite := True)
|
|
vArg = oDict
|
|
End If
|
|
End If
|
|
End If
|
|
End If
|
|
iNbArgs = iNbArgs + 1
|
|
|
|
ReDim Preserve vArgs(iNbArgs)
|
|
vArgs(iNbArgs) = vArg
|
|
Next i
|
|
End If
|
|
|
|
Try:
|
|
' Dispatching strategy: based on next constraints
|
|
' (1) Bug https://bugs.documentfoundation.org/show_bug.cgi?id=138155
|
|
' The CallByName function fails when returning an array
|
|
' (2) Python has tuples and tuple of tuples, not 2D arrays
|
|
' (3) Passing 2D arrays through a script provider always transform it into a sequence of sequences
|
|
' (4) The CallByName function takes exclusive control on the targeted object up to its exit
|
|
' (5) A script provider returns a Basic Date variable as Empty
|
|
' RULES:
|
|
' 1. All methods in any module are invoked with CallByName
|
|
' 2. Properties in any service are got and set with obj.GetProperty/SetProperty(...)
|
|
' EXCEPTIONS:
|
|
' 3. Methods in usual modules are called by ExecuteBasicScript() when they manipulate arrays
|
|
' 4. Methods in class modules using a 2D array or returning arrays, or methods using ParamArray,
|
|
''' are hardcoded as exceptions or are not implemented
|
|
' 5. Due to constraint (4), a predefined list of method calls must be hardcoded to avoid blocking use of CallByName
|
|
' The concerned methods are flagged with cstHardCode
|
|
|
|
With _SF_
|
|
' Initialize Python persistent storage at 1st call
|
|
If IsEmpty(.PythonStorage) Then ._InitPythonStorage()
|
|
' Reset any error
|
|
._Stackreset()
|
|
' Set Python trigger to manage signatures in error messages
|
|
.TriggeredByPython = True
|
|
End With
|
|
|
|
Select case VarType(BasicObject)
|
|
Case V_STRING
|
|
' Special entry for CreateScriptService()
|
|
vBasicObject = BasicObject
|
|
If vBasicObject = "SF_Services" Then
|
|
If UBound(vArgs) = 0 Then vParams = Array() Else vParams = SF_Array.Slice(vArgs, 1)
|
|
Select Case UBound(vParams)
|
|
Case -1 : vReturn = SF_Services.CreateScriptService(vArgs(0))
|
|
Case 0 : vReturn = SF_Services.CreateScriptService(vArgs(0), vParams(0))
|
|
Case 1 : vReturn = SF_Services.CreateScriptService(vArgs(0), vParams(0), vParams(1))
|
|
Case 2 : vReturn = SF_Services.CreateScriptService(vArgs(0), vParams(0), vParams(1), vParams(2))
|
|
Case 3 : vReturn = SF_Services.CreateScriptService(vArgs(0), vParams(0), vParams(1), vParams(2), vParams(3))
|
|
Case 4 : vReturn = SF_Services.CreateScriptService(vArgs(0), vParams(0), vParams(1), vParams(2), vParams(3), vParams(4))
|
|
End Select
|
|
End If
|
|
If VarType(vReturn) = V_OBJECT And Not IsNull(vReturn) Then
|
|
vBasicObject = vReturn
|
|
sObjectType = vBasicObject.ObjectType
|
|
bBasicClass = ( Left(sObjectType, 3) <> "SF_" )
|
|
End If
|
|
|
|
' Implement dispatching strategy
|
|
Case V_INTEGER
|
|
If BasicObject < 0 Or Not IsArray(_SF_.PythonStorage) Then GoTo Catch
|
|
If BasicObject > UBound(_SF_.PythonStorage) Then GoTo Catch
|
|
vBasicObject = _SF_.PythonStorage(BasicObject)
|
|
sObjectType = vBasicObject.ObjectType
|
|
sServiceName = vBasicObject.ServiceName
|
|
|
|
' Basic modules have type = "SF_*"
|
|
bBasicClass = ( Left(sObjectType, 3) <> "SF_" )
|
|
sLibrary = Split(sServiceName, ".")(0)
|
|
|
|
' Methods in standard modules are called by ExecuteBasicScript() when arrays are returned
|
|
If Not bBasicClass And (CallType And vbMethod) = vbMethod And (CallType And cstRetArray) = cstRetArray Then
|
|
sScript = sLibrary & "." & sObjectType & "." & Script
|
|
' Force validation in targeted function, not in ExecuteBasicScript()
|
|
_SF_.StackLevel = -1
|
|
Select Case UBound(vArgs)
|
|
Case -1 : vReturn = sess.ExecuteBasicScript(, sScript)
|
|
Case 0 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0))
|
|
Case 1 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1))
|
|
Case 2 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2))
|
|
Case 3 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2), vArgs(3))
|
|
Case 4 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4))
|
|
Case 5 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5))
|
|
Case 6 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6))
|
|
Case 7 : vReturn = sess.ExecuteBasicScript(, sScript, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7))
|
|
End Select
|
|
_SF_.StackLevel = 0
|
|
|
|
' Properties in any service are got and set with obj.GetProperty/SetProperty(...)
|
|
ElseIf (CallType And vbGet) = vbGet Then ' In some cases (Calc ...) GetProperty may have an argument
|
|
If UBound(vArgs) < 0 Then vReturn = vBasicObject.GetProperty(Script) Else vReturn = vBasicObject.GetProperty(Script, vArgs(0))
|
|
ElseIf (CallType And vbLet) = vbLet Then
|
|
vReturn = vBasicObject.SetProperty(Script, vArgs(0))
|
|
|
|
' Methods in class modules using a 2D array or returning arrays are hardcoded as exceptions. Bug #138155
|
|
ElseIf ((CallType And vbMethod) + (CallType And cstArgArray)) = vbMethod + cstArgArray Or _
|
|
((CallType And vbMethod) + (CallType And cstRetArray)) = vbMethod + cstRetArray Then
|
|
If Script = "Methods" Then
|
|
vReturn = vBasicObject.Methods()
|
|
ElseIf Script = "Properties" Then
|
|
vReturn = vBasicObject.Properties()
|
|
Else
|
|
Select Case sServiceName
|
|
Case "SFDatabases.Database"
|
|
If Script = "GetRows" Then vReturn = vBasicObject.GetRows(vArgs(0), vArgs(1), vArgs(2), vArgs(3))
|
|
Case "SFDatabases.Dataset"
|
|
If Script = "GetRows" Then vReturn = vBasicObject.GetRows(vArgs(0), vArgs(1))
|
|
Case "SFDialogs.Dialog"
|
|
If Script = "Controls" Then vReturn = vBasicObject.Controls(vArgs(0))
|
|
Case "SFDialogs.DialogControl"
|
|
If Script = "SetTableData" Then vReturn = vBasicObject.SetTableData(vArgs(0), vArgs(1), vArgs(2))
|
|
Case "SFDocuments.Document"
|
|
Select Case Script
|
|
Case "ContextMenus" : vReturn = vBasicObject.ContextMenus(vArgs(0), vArgs(1))
|
|
Case "Forms" : vReturn = vBasicObject.Forms(vArgs(0))
|
|
Case "Styles" : vReturn = vBasicObject.Styles(vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5))
|
|
Case "Toolbars" : vReturn = vBasicObject.Toolbars(vArgs(0))
|
|
End Select
|
|
Case "SFDocuments.Base"
|
|
Select Case Script
|
|
Case "ContextMenus" : vReturn = vBasicObject.ContextMenus(vArgs(0), vArgs(1))
|
|
Case "FormDocuments" : vReturn = vBasicObject.FormDocuments()
|
|
Case "Forms" : vReturn = vBasicObject.Forms(vArgs(0), vArgs(1))
|
|
Case "Toolbars" : vReturn = vBasicObject.Toolbars(vArgs(0))
|
|
End Select
|
|
Case "SFDocuments.Calc"
|
|
Select Case Script
|
|
Case "Charts" : vReturn = vBasicObject.Charts(vArgs(0), vArgs(1))
|
|
Case "ContextMenus" : vReturn = vBasicObject.ContextMenus(vArgs(0), vArgs(1))
|
|
Case "Forms" : vReturn = vBasicObject.Forms(vArgs(0), vArgs(1))
|
|
Case "GetFormula" : vReturn = vBasicObject.GetFormula(vArgs(0))
|
|
Case "GetValue" : vReturn = vBasicObject.GetValue(vArgs(0))
|
|
Case "SetArray" : vReturn = vBasicObject.SetArray(vArgs(0), vArgs(1))
|
|
Case "SetFormula" : vReturn = vBasicObject.SetFormula(vArgs(0), vArgs(1))
|
|
Case "SetValue" : vReturn = vBasicObject.SetValue(vArgs(0), vArgs(1))
|
|
Case "Styles" : vReturn = vBasicObject.Styles(vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5))
|
|
Case "Toolbars" : vReturn = vBasicObject.Toolbars(vArgs(0))
|
|
End Select
|
|
Case "SFDocuments.Form"
|
|
Select Case Script
|
|
Case "Controls" : vReturn = vBasicObject.Controls(vArgs(0))
|
|
Case "Subforms" : vReturn = vBasicObject.Subforms(vArgs(0))
|
|
End Select
|
|
Case "SFDocuments.FormControl"
|
|
If Script = "Controls" Then vReturn = vBasicObject.Controls(vArgs(0))
|
|
Case "SFDocuments.FormDocument"
|
|
Select Case Script
|
|
Case "ContextMenus" : vReturn = vBasicObject.ContextMenus(vArgs(0), vArgs(1))
|
|
Case "Forms" : vReturn = vBasicObject.Forms(vArgs(0))
|
|
Case "Toolbars" : vReturn = vBasicObject.Toolbars(vArgs(0))
|
|
End Select
|
|
Case "SFDocuments.Writer"
|
|
Select Case Script
|
|
Case "ContextMenus" : vReturn = vBasicObject.ContextMenus(vArgs(0), vArgs(1))
|
|
Case "Forms" : vReturn = vBasicObject.Forms(vArgs(0))
|
|
Case "Styles" : vReturn = vBasicObject.Styles(vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5))
|
|
Case "Toolbars" : vReturn = vBasicObject.Toolbars(vArgs(0))
|
|
End Select
|
|
Case "SFWidgets.Toolbar"
|
|
Select Case Script
|
|
Case "ToolbarButtons" : vReturn = vBasicObject.ToolbarButtons(vArgs(0))
|
|
End Select
|
|
End Select
|
|
End If
|
|
|
|
' Specific methods in class modules may better not be executed with CallByName() because they do not return immediately
|
|
ElseIf bBasicClass And ((CallType And vbMethod) + (CallType And cstHardCode)) = vbMethod + cstHardCode Then
|
|
Select Case sServiceName
|
|
Case "SFDialogs.Dialog"
|
|
Select Case Script
|
|
Case "Execute" : vReturn = vBasicObject.Execute(vArgs(0))
|
|
End Select
|
|
End Select
|
|
|
|
' Methods in all modules are invoked with CallByName
|
|
ElseIf ((CallType And vbMethod) = vbMethod) Then
|
|
Select Case UBound(vArgs)
|
|
' Dirty alternatives to process usual and ParamArray cases
|
|
' But, up to ... how many ?
|
|
' - The OFFSETADDRESSERROR has 12 arguments
|
|
' - The ".uno:DataSort" command may have 14 property name-value pairs
|
|
Case -1 : vReturn = CallByName(vBasicObject, Script, vbMethod)
|
|
Case 0 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0))
|
|
Case 1 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1))
|
|
Case 2 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2))
|
|
Case 3 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3))
|
|
Case 4 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4))
|
|
Case 5 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5))
|
|
Case 6 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6))
|
|
Case 7 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7))
|
|
Case 8 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8))
|
|
Case 9 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9))
|
|
Case 10 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10))
|
|
Case 11 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11))
|
|
Case 12, 13 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12))
|
|
Case 14, 15 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14))
|
|
Case 16, 17 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16))
|
|
Case 18, 19 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18))
|
|
Case 20, 21 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18) _
|
|
, vArgs(19), vArgs(20))
|
|
Case 22, 23 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18) _
|
|
, vArgs(19), vArgs(20), vArgs(21), vArgs(22))
|
|
Case 24, 25 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18) _
|
|
, vArgs(19), vArgs(20), vArgs(21), vArgs(22), vArgs(23), vArgs(24))
|
|
Case 26, 27 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18) _
|
|
, vArgs(19), vArgs(20), vArgs(21), vArgs(22), vArgs(23), vArgs(24), vArgs(25), vArgs(26))
|
|
Case >= 28 : vReturn = CallByName(vBasicObject, Script, vbMethod, vArgs(0), vArgs(1), vArgs(2), vArgs(3), vArgs(4), vArgs(5), vArgs(6), vArgs(7) _
|
|
, vArgs(8), vArgs(9), vArgs(10), vArgs(11), vArgs(12), vArgs(13), vArgs(14), vArgs(15), vArgs(16), vArgs(17), vArgs(18) _
|
|
, vArgs(19), vArgs(20), vArgs(21), vArgs(22), vArgs(23), vArgs(24), vArgs(25), vArgs(26), vArgs(27), vArgs(28))
|
|
End Select
|
|
End If
|
|
|
|
' Post processing
|
|
If (CallType And cstPost) = cstPost Then
|
|
If Script = "Dispose" Then
|
|
' Special case: Dispose() must update the cache for class objects created in Python scripts
|
|
Set _SF_.PythonStorage(BasicObject) = Nothing
|
|
End If
|
|
End If
|
|
Case Else
|
|
End Select
|
|
|
|
' Format the returned array
|
|
vReturnArray = Array()
|
|
' Distinguish: Basic object
|
|
' UNO object
|
|
' Dictionary
|
|
' Array
|
|
' Scalar
|
|
If IsArray(vReturn) Then
|
|
ReDim vReturnArray(0 To 2)
|
|
iDims = SF_Array.CountDims(vReturn)
|
|
' Replace dates by UNO format
|
|
If iDims = 1 Then
|
|
For i = LBound(vReturn) To UBound(vReturn)
|
|
If VarType(vReturn(i)) = V_DATE Then vReturn(i) = CDateToUnoDateTime(vReturn(i))
|
|
Next i
|
|
ElseIf iDims = 2 Then
|
|
For i = LBound(vReturn, 1) To UBound(vReturn, 1)
|
|
For j = LBound(vReturn, 2) To UBound(vReturn, 2)
|
|
If VarType(vReturn(i, j)) = V_DATE Then vReturn(i, j) = CDateToUnoDateTime(vReturn(i, j))
|
|
Next j
|
|
Next i
|
|
End If
|
|
vReturnArray(0) = vReturn ' 2D arrays are flattened by the script provider when returning to Python
|
|
vReturnArray(1) = VarType(vReturn)
|
|
vReturnArray(2) = iDims
|
|
ElseIf VarType(vReturn) = V_OBJECT And Not IsNull(vReturn) Then
|
|
' Uno or not Uno ?
|
|
bUno = False
|
|
If (CallType And cstUno) = cstUno Then ' UNO considered only when pre-announced in CallType
|
|
Set oObjDesc = SF_Utils._VarTypeObj(vReturn)
|
|
bUno = ( oObjDesc.iVarType = V_UNOOBJECT )
|
|
End If
|
|
If bUno Then
|
|
ReDim vReturnArray(0 To 2)
|
|
Set vReturnArray(0) = vReturn
|
|
Else
|
|
ReDim vReturnArray(0 To 5)
|
|
bDict = ( vReturn.ObjectType = "DICTIONARY" )
|
|
If bDict Then
|
|
vReturnArray(0) = vReturn.ConvertToPropertyValues()
|
|
Else
|
|
vReturnArray(0) = _SF_._AddToPythonSTorage(vReturn)
|
|
End If
|
|
End If
|
|
vReturnArray(1) = V_OBJECT
|
|
Select Case True
|
|
Case bUno : vReturnArray(2) = objUNO
|
|
Case bDict : vReturnArray(2) = objDICT
|
|
Case bBasicClass : vReturnArray(2) = objCLASS
|
|
Case Else : vReturnArray(2) = objMODULE
|
|
End Select
|
|
If Not bUno Then
|
|
vReturnArray(3) = vReturn.ObjectType
|
|
vReturnArray(4) = vReturn.ServiceName
|
|
vReturnArray(5) = ""
|
|
If vReturn.ObjectType <> "SF_CalcReference" And Not bDict Then ' Calc references are implemented as a Type ... End Type data structure
|
|
If SF_Array.Contains(vReturn.Properties(), "Name", SortOrder := "ASC") Then vReturnArray(5) = vReturn.Name
|
|
End If
|
|
End If
|
|
Else ' Scalar or Nothing
|
|
ReDim vReturnArray(0 To 1)
|
|
If VarType(vReturn) = V_DATE Then vReturnArray(0) = CDateToUnoDateTime(vReturn) Else vReturnArray(0) = vReturn
|
|
vReturnArray(1) = VarType(vReturn)
|
|
End If
|
|
|
|
' Tests with non-modal dialogs and sleeping (time.sleep) Python processes show
|
|
' a more fluid reactivity when next statement is present, at a minimal cost.
|
|
Wait 0
|
|
|
|
_PythonDispatcher = vReturnArray
|
|
|
|
Finally:
|
|
_SF_.TriggeredByPython = False ' Reset normal state
|
|
Exit Function
|
|
Catch:
|
|
GoTo Finally
|
|
End Function ' ScriptForge.SF_PythonHelper._PythonDispatcher
|
|
|
|
REM -----------------------------------------------------------------------------
|
|
Private Function _Repr() As String
|
|
''' Convert the Basic instance to a readable string, typically for debugging purposes (DebugPrint ...)
|
|
''' Args:
|
|
''' Return:
|
|
''' "[PythonHelper]"
|
|
|
|
_Repr = "[PythonHelper]"
|
|
|
|
End Function ' ScriptForge.SF_PythonHelper._Repr
|
|
|
|
REM ================================================= END OF SCRIPTFORGE.SF_PythonHelper
|
|
</script:module> |