Sign in to follow this  
Followers 0
funkey

ObjCreate ByRef Method

20 posts in this topic

I found this thread here:

Is it now with 3.3.8.0 possible to use byref arguments with object methods?

Thanks for any information!


Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites



Has no one an answer for me?

It looks like it does not work, but in documentation of ObjCreateInterface there is mentioned passing by reference, but only if you describe your COM interface by your own and not with using IDispatch interface.


Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

funkey,

Do you want me to move this into "Developer Chat"? You might have more luck there.:)

M23


Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind._______My UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Share this post


Link to post
Share on other sites

If you think it is better there, then just feel free to do it. Thanks.


Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

Has no one an answer for me?

It looks like it does not work

Ehh.

What does not work?


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

Hello trancexx! Thanks for answering.

I have to give a BSTR byref to the method, but it does not work. The given string (or empty string) is not beeing changed.

Here is my test code

Global Const $CLSID_SimaticLib_Simatic = "{9A853ACF-BA8E-11D1-BAD8-0060086A411D}"
Global Const $IID_SimaticLib_ISimatic = "{9A853ACE-BA8E-11D1-BAD8-0060086A411D}"

Global $oErrorHandler = ObjEvent("AutoIt.Error", "_ErrFunc")

;~ Global $oSimatic = ObjCreate("Simatic.Simatic.1")
Global $oSimatic = ObjCreateInterface($CLSID_SimaticLib_Simatic, $IID_SimaticLib_ISimatic)

;~ Global $sBSTR = _SysAllocStringByteLen(0, 6) ;define empty string
Global $sBSTR = _SysAllocString("XX")   ; <-- if string is predefined, then after GetSTEP7Language it is the same string

$oSimatic.GetSTEP7Language($sBSTR)  ; should write language (en, de, es, ..) to $sBSTR

;~ $oSimatic.Save() ;just for testing

Global $tTest = DllStructCreate("wchar[6]", $sBSTR)
ConsoleWrite(DllStructGetData($tTest, 1) & @LF)

_SysFreeString($sBSTR)


; User's COM error function. Will be called if COM error occurs
Func _ErrFunc($oError)
    ; Do anything here.
    ConsoleWrite("err.number is: " & @TAB & $oError.number & @CRLF & _
            "err.windescription:" & @TAB & $oError.windescription & @CRLF & _
            "err.description is: " & @TAB & $oError.description & @CRLF & _
            "err.source is: " & @TAB & $oError.source & @CRLF & _
            "err.helpfile is: " & @TAB & $oError.helpfile & @CRLF & _
            "err.helpcontext is: " & @TAB & $oError.helpcontext & @CRLF & _
            "err.lastdllerror is: " & @TAB & $oError.lastdllerror & @CRLF & _
            "err.scriptline is: " & @TAB & $oError.scriptline & @CRLF & _
            "err.retcode is: " & @TAB & $oError.retcode & @CRLF & @CRLF)
EndFunc   ;==>_ErrFunc


Func _SysAllocString($sString)
    Local $aRet = DllCall("OleAut32.dll", "ptr", "SysAllocString", "wstr", $sString)
    Return $aRet[0]
EndFunc   ;==>_SysAllocString

Func _SysAllocStringByteLen($sString, $iLen)
    Local $aRet = DllCall("OleAut32.dll", "ptr", "SysAllocStringByteLen", "ptr", Int($sString), "uint", $iLen)
;~  ConsoleWrite($aRet[0] & @LF)
;~  ConsoleWrite($aRet[1] & @LF)
;~  ConsoleWrite($aRet[2] & @LF)
    Return $aRet[0]
EndFunc   ;==>_SysAllocStringByteLen

Func _SysFreeString($pBSTR)
    DllCall("OleAut32.dll", "none", "SysFreeString", "ptr", $pBSTR)
EndFunc   ;==>_SysFreeString

I hope this is the right way to do this thing.


Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

Try to use a normal AutoIt-String :)


*GERMAN* [note: you are not allowed to remove author / modified info from my UDFs]My UDFs:[_SetImageBinaryToCtrl] [_TaskDialog] [AutoItObject] [Animated GIF (GDI+)] [ClipPut for Image] [FreeImage] [GDI32 UDFs] [GDIPlus Progressbar] [Hotkey-Selector] [Multiline Inputbox] [MySQL without ODBC] [RichEdit UDFs] [SpeechAPI Example] [WinHTTP]UDFs included in AutoIt: FTP_Ex (as FTPEx), _WinAPI_SetLayeredWindowAttributes

Share this post


Link to post
Share on other sites

Try to use a normal AutoIt-String :)

This works exactly the same way, easier, but no result again.

Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

#9 ·  Posted (edited)

From the threads I've just skimmed, I'd say you're going to have to define your own interface for the ObjCreateInterface call (at least to the point of the function you're interested in using. I would conjecture that AutoIt can't determine the type of parameter in an IDispatch interface in order to use ByRef properly??? Anyway, from the beta thread, it seems str / wstr are always passed ByRef, so no need to do str* / wstr*.

Edited by wraithdu

Share this post


Link to post
Share on other sites

This works exactly the same way, easier, but no result again.

Show that code.

♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

No special changes to code above.

Global $sAutoIt = "AA"

$oSimatic.GetSTEP7Language($sAutoIt)    ; should write language (en, de, es, ..) to $sBSTR

ConsoleWrite($sAutoIt & @CR)

Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

That should work. Maybe you are wrong about what function does. Can you show the declaration of that method?


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

I have this to declarations:

Method GetSTEP7Language <37> (ByRef pLang As WString)
HRESULT GetSTEP7Language(BSTR * pLANG)

Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

First try this:

ConsoleWrite($oSimatic.GetSTEP7Language() & @CR)

If that wouldn't work then do something like I would love to see what's there.


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

#15 ·  Posted (edited)

If I try 'ConsoleWrite($oSimatic.GetSTEP7Language() &amp; @CR)' then error handler says something like 'invalid parameter count'.

BTW: I also tried 'ISimatic4'

Here are all informations from your TLB-Viewer:

Edit: code to long, sorry.

Here is some of the information:

xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
SimaticLib; // Simatic 1.0 Type Library
UUID {9A853AC1-BA8E-11D1-BAD8-0060086A411D};
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx



==================================================================================

coclass Simatic; // the central entry-level object of the command interface
CLSID = {9A853ACF-BA8E-11D1-BAD8-0060086A411D}; 

// Implemented interface: <IDispatch> ISimatic4
// Implemented interface: <IDispatch> ISimatic3
// Implemented interface: <IDispatch> ISimatic2
// Implemented interface: <IDispatch> ISimatic
// Implemented interface: <IDispatch> _IS7StdItemInternal

==================================================================================

IDispatch ISimatic4; // Interface for the the central entry-level object of the command interface, supported since version V5.3 SP2
IID = {1419EEE8-3595-4239-9E8F-44BD27B67E34}; 
// Inherits from:  IDispatch  {00020400-0000-0000-C000-000000000046}

    1. Whether no message box may be displayed under any circumstances because no human user would be able to acknowledge the message box.
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT UnattendedServerMode(
            [out,retval] bool* pVal
         );

    2. Whether no message box may be displayed under any circumstances because no human user would be able to acknowledge the message box.
STDCALL PROPERTYPUTREF PUREVIRTUAL;
         HRESULT UnattendedServerMode(
            [in] bool pVal
         );

    3. method GetSTEP7Language
STDCALL FUNC PUREVIRTUAL;
         HRESULT GetSTEP7Language(
             BSTR* pLang
         );

    4. property MsgAssignmentType
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT MsgAssignmentType(
            [out,retval] int* pVal
         );

    5. property MsgAssignmentType
STDCALL PROPERTYPUTREF PUREVIRTUAL;
         HRESULT MsgAssignmentType(
            [in] int pVal
         );

    6. method SetPGInterface
STDCALL FUNC PUREVIRTUAL;
         HRESULT SetPGInterface(
         );

    7. method GetAccessibleNodes
STDCALL FUNC PUREVIRTUAL;
         HRESULT GetAccessibleNodes(
             BSTR storagePath
         );


==================================================================================

IDispatch ISimatic3; // Interface for the the central entry-level object of the command interface, supported since version V5.2
IID = {AA6AC581-1722-11D6-9842-080006247F7D}; 
// Inherits from:  IDispatch  {00020400-0000-0000-C000-000000000046}

    1. The file in which the method compile and other batch-mode operations will log messages in silent mode. Empty string means 'verbose mode', in which error messages are displayed in a user interface.
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT VerbLogFile(
            [out,retval] BSTR* pVal
         );

    2. The file in which the method compile and other batch-mode operations will log messages in silent mode. Empty string means 'verbose mode', in which error messages are displayed in a user interface.
STDCALL PROPERTYPUTREF PUREVIRTUAL;
         HRESULT VerbLogFile(
            [in] BSTR pVal
         );

    3. accesses the S7 Memory Card object
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT MemCard(
            [out,retval] <IDispatch> IS7MemCard** pVal
         );


==================================================================================

IDispatch ISimatic2; // Interface for the the central entry-level object of the command interface, supported since version V5.1 SP3
IID = {D7307A51-5FF9-11D5-97F7-080006247F7D}; 
// Inherits from:  IDispatch  {00020400-0000-0000-C000-000000000046}

    1. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _CreateItem(
            [in] int hObj, 
            [in] <IDispatch> _IS7StdItemInternal* pParent, 
            [out,retval] <IDispatch> _IS7StdItemInternal** ppNewItem
         );

    2. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _CreateCollection(
            [in] <IDispatch> _IS7StdItemInternal* pParentItem, 
            [in] BSTR ID, 
            [out,retval] <IDispatch> _IS7StdCollectionInternal** ppNewCollection
         );

    3. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _CreateChild(
            [in] <IDispatch> _IS7StdItemInternal* pParentItem, 
            [in] BSTR ID, 
            [out,retval] IUnknown* ppNewItem
         );

    4. Frees underlying STEP 7 Objects. This can increase performance and makes it possible to remove projects already accessed by the command interface.
STDCALL FUNC PUREVIRTUAL;
         HRESULT Close(
         );

    5. accesses any collection directly attached to the Simatic object
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT Collection(
            [in] BSTR ID, 
            [out,retval] idispatch* pVal
         );

    6. accesses a directly attached object that can be uniquely determined by its type
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT Child(
            [in] BSTR ID, 
            [out,retval] IUnknown* pVal
         );

    7. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _Save(
            [in,optional,hasdefault] bool bForce
         );

    8. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _UpdateMode(
            [in,optional,hasdefault] bool bUseStdOSet
         );

    9. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _Enter2Update(
            [in] int hObj, 
            [out,retval] int* pNewHObj
         );

    10. 
STDCALL FUNC PUREVIRTUAL;
         HRESULT _Enter2Std(
            [in] int hObj, 
            [out,retval] int* pNewHObj
         );


==================================================================================

IDispatch ISimatic; // Interface for the the central entry-level object of the command interface, supported by all versions
IID = {9A853ACE-BA8E-11D1-BAD8-0060086A411D}; 
// Inherits from:  IDispatch  {00020400-0000-0000-C000-000000000046}

    1. The collection containing the projects and libraries that are also displayed in the project list in the SIMATIC Manager
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT Projects(
            [out,retval] <IDispatch> IS7Projects** pVal
         );

    2. whether the command interface automatically takes care of saving all changes
STDCALL PROPERTYGET PUREVIRTUAL;
         HRESULT AutomaticSave(
            [out,retval] int* pVal
         );

    3. whether the command interface automatically takes care of saving all changes
STDCALL PROPERTYPUTREF PUREVIRTUAL;
         HRESULT AutomaticSave(
            [in] int pVal
         );

    4. saves all changes to STEP 7 Objects done by the command interface
STDCALL FUNC PUREVIRTUAL;
         HRESULT Save(
         );


==================================================================================
Edited by funkey

Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

As you can see there, there is data missing for that function's parameter. If TLB Viewer script can't figure out what flags that parameter has then AutoIt can't also.

Try some other tool for examining TLBs. It would be interesting to see what they show.


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

As you can see there, there is data missing for that function's parameter. If TLB Viewer script can't figure out what flags that parameter has then AutoIt can't also.

Try some other tool for examining TLBs. It would be interesting to see what they show.

Where can I see that there is data missing? Sorry, but I used your TLB-Viewer the first time.

I used also PowerBASIC COM Browser, but there is no additional information.

Then I used OLE/COM Object Viewer from MS, browsed to the automation object and then the app closes (crashes?).

??


Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

Ah, interesting. trancexxx means that for that method, a declaration like

[out,retval]

is missing for the parameter.

Share this post


Link to post
Share on other sites

#19 ·  Posted (edited)

Hm, I just tried out this object with PowerBASIC and it immediately worked fine.

#COMPILE EXE
#DIM ALL

#INCLUDE "SIMATIC.inc"
#INCLUDE "Win32api.inc"


FUNCTION PBMAIN () AS LONG

    LOCAL test AS ISimatic4
    LOCAL stest AS WSTRING

    test = NEWCOM $PROGID_SimaticLib_Simatic1

    IF ISFALSE(ISOBJECT(test)) THEN
      MSGBOX "This Control is not installed."
    END IF

    test.GetSTEP7Language(stest)

    MSGBOX sTest

END FUNCTION
Edited by funkey

Programming today is a race between software engineers striving to
build bigger and better idiot-proof programs, and the Universe
trying to produce bigger and better idiots.
So far, the Universe is winning.

Share this post


Link to post
Share on other sites

#20 ·  Posted (edited)

But AutoIt is not PowerBasic. If PowerBasic is making assumptions about a broken object, that does not mean AutoIt should also make the same assumptions. Better to spend your time reporting the bug to the developers of your component to get it fixed (I think it's a bad sign that it crashes MS's object viewer).

Edited by wraithdu

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0