Page 26 of 39

Posted: Mon Feb 16, 2009 11:34 am
by Kwai chang caine
Excuse me SROD :oops:
Like all the MASTERS of this forum, you have so always the answer :D
That i forget sometimes, that the great SROD is human :shock:

Usually just KCC not have the answer :lol:
KCC it's the best in this discipline :oops:
If you need something.....ask to KCC.....and KCC explain to you, how you can do without :lol:

Then KCC say to him, "It's sure the GREAT SROD run at the four corner of the forum like a "p25 12core at 1256Ghz" and always answer.
Then it's mathematical.....if no answer = no see the question :cry:
Or perhaps sometime....if no answer = too much unnerve the MASTER :oops:

Thanks for your answer even if the reply is negative 8)
I wish you a very good day, and hope for you and this day, none KCC question :D

Posted: Fri Feb 20, 2009 12:55 am
by srod
Update - 19th Feb. 2009.

COMate version 1.3.0.

First, only the version of COMate for PB 4.3 has had this update. COMate for PB 4.2 remains at version 1.1.7

This update massively revamps the way that COMate exposes events from ActiveX controls. So much so that all existing code using COMate to work with ActiveX controls will be broken if dealing with events etc. Only minor modifications will be required though to get your code working with this new version (details below).

Basically, there are two major changes/alterations here :
  1. Event handlers can now be attached to individual 'named' events. For example, you can attach a 'Click' handler to a control (assuming it exposes such an event!) and this handler will be called only when this particular event is raised. Contrast this with the old way of having a single 'global' handler for all events!

    The 'global' handler is still supported, however, as it can be very useful if investigating the full range of events supported by an individual object. Indeed, in cases where a global handler has been declared in addition to an individual handler, then when the underlying event is raised by the ActiveX control, the global handler will be called first, before the individual one.
  2. Many ActiveX controls make available a means for individual event handlers to return a value back to the ActiveX control. The most common method is for the ActiveX control to simply pass a parameter (or two!) 'by reference', thus allowing the client to modify the parameters etc. COMate has been able to handle this since version 1.2.1.

    A second (less common) mechanism employed by some controls is for the event handler to explicitly return a value direct to the ActiveX control itself. COMate now supports this method as well and allows individual event handlers to explicitly return an integer or a real or a string value as appropriate (there are no tricks here, you simply declare your handler as being of a certain type etc.) For return values not covered by this list, you can opt to return a variant type which thus covers all eventualities.

    I have to say though that this is untested at present whilst I endeavour to locate an ActiveX control which offers this! However, this was a simple addition to COMate and so I see no reason why it should fail to work! :)
There is quite a lot more to say about this (e.g. COMate only allows COM objects with a visual interface (such as an ActiveX control) to utilise individual named event handlers. Other objects are restricted to 'global' handlers as before) and so I have to point users towards the fully updated user manual (event handling methods section).

For those wishing to quickly get their code working with version 1.3.0 of COMate, all you need to do is switch your current event handler for a 'global' one. E.g. in the "MSComctlLib_TreeCtrl_WithEvents.pb" demo, you would switch the line :

Code: Select all

treeViewObject\SetEventHandler(@EventProc())
for :

Code: Select all

treeViewObject\SetEventHandler(#COMate_CatchAllEvents, @EventProc())
See the "FlexCellDemo.pb" demo for an example of declaring an individual named event handler (with ByRef parameters).

When I encounter an ActiveX control whose events explicitly return values then I can perhaps knock up a demo of such a handler in action; in the meantime all is detailed within the manual! :wink:

You can access the download through the nxSoftware site.

Posted: Fri Feb 20, 2009 11:18 am
by Kiffi
srod wrote:

Code: Select all

treeViewObject\SetEventHandler(#COMate_CatchAllEvents, @EventProc())
cool. Image

Currently i am working on my first serious project with PB in combination
with ActiveX. Everything works perfect. But now i have a problem to
release an object inside of his own EventProc.

i suspect, the following code is not the right way to solve this, because i
get an invalid memory access after releasing the object (Proc
COMateSinkClass_Release(); line "ProcedureReturn *this\refCount".)

Code: Select all

Procedure EventProc(Object.COMateObject, eventName$, parameterCount)
  
  Select eventName$
    Case "OnDisconnected"
      Object\Release()
  EndSelect
  
EndProcedure
Greetings ... Kiffi

Posted: Fri Feb 20, 2009 11:21 am
by srod
Yes you really do not want to release this object within the handler because at that point COMate has not finished with it. Also, COMate will attempt to dispose of the outgoing connection object at some point which is where you are getting the crash.

It crashes at that line because you have freed the underlying object before time. :)

Remember that in your event proc, object points to the main object. Releasing this in an event proc is simply not a good idea!

Posted: Fri Feb 20, 2009 11:35 am
by srod
Just tested with FlexGrid and I have no problem releasing the object in an eventhandler.

The error you are getting suggests a problem with the reference counting; and I suspect it is with the ActiveX control itself rather than with COMate. It probably does not expect to be released during a call to an event handler.

I'll investigate more when I return from taking my father to the hospital.

Posted: Fri Feb 20, 2009 11:37 am
by Kiffi
srod wrote:Releasing this in an event proc is simply not a good idea!
yes, i see. ;-)

the real problem is a little bit more complex. After getting the message
'OnDisconnected' i want to close the underlying Panelgadged-Tab. (i have
several COMate-Objects of then same type inside of a structured LinkedList)

ok, so i try to solve this on another way.

Thanks for your fast reply & Greetings ... Kiffi

Posted: Fri Feb 20, 2009 1:13 pm
by srod
Yes a slight bug in COMate, which has been fixed. Could you try the new version Kiffi?

After a little investigation, it is clear that releasing an object within one of it's own event handlers does alter the order in which certain associated objects are released; and not for the better it would seem! This could upset things somewhat.

Even if the new version of COMate fixes your problem then I stick by what I said in that I don't think it is a good idea to release an object within one of it's event handlers! :)

Posted: Fri Feb 20, 2009 1:52 pm
by Kiffi
srod wrote:Even if the new version of COMate fixes your problem then I stick by what I said in that I don't think it is a good idea to release an object within one of it's event handlers! :)
thanks for your efforts. i understand, that removing an element inside its
own eventhandler is quite dirty.

i found now a 'cleaner' way to remove the disconnected elements out of
my linkedlist (removing all elements with as special flag inside the
Main-Event-Loop).

Code: Select all

Repeat
  WWE = WaitWindowEvent(100)
  If WWE
   ; do the event-job
  Else
   ; do the cleaner-job
  EndIf
Until ...
(and no: the new version fixes not my problem ;-))

Thanks for your help & Greetings ... Kiffi

Posted: Fri Feb 20, 2009 1:55 pm
by srod
Oh well; worth a try! My fix did have a bug in it and I uploaded a new fix (a fix for the fix!) Worth a try when you get a spare moment. :)

Posted: Fri Feb 20, 2009 2:07 pm
by srod
Another thought.

In your event handler, before releasing the object, try first releasing all event handlers :

Code: Select all

object\SetEventHandler(#COMate_CatchAllEvents, 0)

Posted: Fri Feb 20, 2009 2:37 pm
by Kiffi
mh, your fix for the fix is the same file as the first fix... (same size and timestamp)

did you upload your fix for the fix?

Greetings ... Fixxi ... erm ... Kiffi

Posted: Fri Feb 20, 2009 2:42 pm
by srod
Kiffi wrote:mh, your fix for the fix is the same file as the first fix... (same size and timestamp)

did you upload your fix for the fix?

Greetings ... Fixxi ... erm ... Kiffi
Yes, you may have downloaded after the fixed fix! :) Did you try the above suggestion regarding removing all event handlers?

Posted: Fri Feb 20, 2009 2:48 pm
by Kiffi
srod wrote:Did you try the above suggestion regarding removing all event handlers?
yes. Now i get an IMA in line

Code: Select all

ProcedureReturn 0
in

Code: Select all

Procedure.i COMateSinkClass_Release(*this._COMateEventSink)
:P

Greetings ... Kiffi

Posted: Fri Feb 20, 2009 2:52 pm
by srod
Oh well; never mind! Nothing ventured, nothing gained!

Hang on a cotton picking minute; this "OnDisconnected" event, when is it supposed to fire exactly? If it fires immediately before disconnecting the event sink then this would indeed explain the crash!

Posted: Tue Feb 24, 2009 11:31 pm
by SFSxOI
I've been trying to use the SWbemDateTime object and convert these scripts from the MSDN at: http://msdn.microsoft.com/en-us/library ... S.85).aspx

I've not been able to get it to work yet.

what is the correct way to fit the GetFileTime method into this:

Code: Select all

Procedure QFE_Info()

Define.COMateObject objWMIService, QFEInfo
colQFEInfo.COMateEnumObject
strComputer.s = "." 

objWMIService = COMate_GetObject("winmgmts:\\" + strComputer + "\root\cimv2", "") 
If objWMIService
  colQFEInfo = objWMIService\CreateEnumeration("ExecQuery('Select * from Win32_QuickFixEngineering')")
  If colQFEInfo
    QFEInfo = colQFEInfo\GetNextObject()
    While QFEInfo
      x = x + 1
      id$ = Str(x)
      QFE_Caption$ = QFEInfo\GetStringProperty("Caption")
      QFE_Description$ = QFEInfo\GetStringProperty("Description")
      QFE_FixComments$ = QFEInfo\GetStringProperty("FixComments")
      QFE_HotFixID$ = QFEInfo\GetStringProperty("HotFixID")
            
      QFEInfo\Release()
      QFEInfo = colQFEInfo\GetNextObject()
    Wend
    colQFEInfo\Release()
  EndIf
  objWMIService\Release()
  Else
      MessageRequester("Error", "QFEInfo")  
EndIf

EndProcedure
I need the InstalledOn property of the Win32_QuickFixEngineering class. I know I need to create an object like this first : dateTime = COMate_CreateObject("WbemScripting.SWbemDateTime") but i don't know how to implement the GetFileTime in COMate in relation to the above.

Any help?

Thanks