have most of my ActiveX control features running now, but I cannot figure
out how to pass an Array of numbers. The workspace code is: array := (DOUBLEArray withAll: #( 1 2 3 4)) . myOb addArray: array size yArray: array xArray: array. It crashes the image with "Undefined Object does not understand *". It seems that during a copy operation of the DOUBLEArray one of them is invalid and gives nil as size. I am not shure if I need a DOUBLEArray here, a normal array fails exactly with the same behaviour. here is the condensed VB code sample: Dim MyXArray(4) As Double Dim MyYArray(4) As Double myOb.AddArray UBound(MyYArray), MyYArray(), MyXArray() Ciao ...Jochen P.S. playing with ActiveX is quite a "crashy" experience :-) |
"Jochen Riekhof" <[hidden email]> wrote in message
news:[hidden email]... > have most of my ActiveX control features running now, but I cannot figure > out how to pass an Array of numbers. > The workspace code is: > > array := (DOUBLEArray withAll: #( 1 2 3 4)) . > myOb addArray: array size yArray: array xArray: array. > > It crashes the image with "Undefined Object does not understand *". It seems ... > here is the condensed VB code sample: > > Dim MyXArray(4) As Double > Dim MyYArray(4) As Double > myOb.AddArray UBound(MyYArray), MyYArray(), MyXArray() I have had my own "fun" trying to pass arrays around recently, try this perhaps: array := SAFEARRAY withAll: #( 1 2 3 4) elementClass: DOUBLE You may also want to try sending two different arrays rather than the same one twice. Also see Blair's recent response to my post "Help needed passing an array of float values by refference." for more info. > P.S. playing with ActiveX is quite a "crashy" experience :-) I have been throwing some bad stuff at the ActiveX subsystem in Dolphin, but I have to say it has not once crashed Dolphin for me lately. I am running Windows XP, I am sure 9x versions of Windows may not fare as well. Chris |
Christopher...
Thanks you for the hints. Doesn't work, though. I now get FACILITY_NULL in the title and hresultError/invalidCall in the walkback. SAFEARRAY are safer however as they do not crash my Dolphin anymore, though. >I have been throwing some bad stuff at the ActiveX subsystem in Dolphin, >but I have to say it has not once crashed Dolphin for me lately. I use XP pro. Anyway, contrary to the usual experience with doing plain smalltalk stuff in Dolphin (rock solid IMO), some forms of ActiveX access (e.g arrays) crash reliably when something is done wrong. > I am running Windows XP, I am sure 9x versions of Windows may not fare as well. I shurely can believe that :-). Ciao ...Jochen |
"Jochen Riekhof" <[hidden email]> wrote in message
news:[hidden email]... > Christopher... > > Thanks you for the hints. Doesn't work, though. I now get FACILITY_NULL in > the title and hresultError/invalidCall in the walkback. SAFEARRAY are safer > however as they do not crash my Dolphin anymore, though. > > >I have been throwing some bad stuff at the ActiveX subsystem in Dolphin, > >but I have to say it has not once crashed Dolphin for me lately. > > I use XP pro. Anyway, contrary to the usual experience with doing plain > smalltalk stuff in Dolphin (rock solid IMO), some forms of ActiveX access > (e.g arrays) crash reliably when something is done wrong. Well if you can let us know what they are, then we can see whether anything can be done about them. However you must bear in mind that if you are passing the wrong type (or size) of object so something external, then it is quite possible that an unrecoverable memory fault will occur, and this is really outside our control. In this case you are probably passing a C-style array (DOUBLEArray corresponding to a C array of doubles), where a SAFEARRAY is expected. SAFEARRAYs are the VB form of ARRAYs, and have a completely different format than C style arrays. SAFEARRAYs are almost always used in COM, and exclusively in Automation. If you are having difficulty calling COM methods, then its a good idea to post the IDL, as from that one can usually deduce the form of arguments expected. Regards Blair |
Hi Blair...
> However you must bear in mind that if you are > passing the wrong type (or size) of object so something external, then it is > quite possible that an unrecoverable memory fault will occur, and this is > really outside our control. Yes, I did not mean to blame you for anything, it is just as you say :-). > In this case you are probably passing a C-style array (DOUBLEArray > corresponding to a C array of doubles), where a SAFEARRAY is expected. > SAFEARRAYs are the VB form of ARRAYs, and have a completely different format > than C style arrays. SAFEARRAYs are almost always used in COM, and > exclusively in Automation. Makes perfect sense to me. > If you are having difficulty calling COM methods, then its a good idea to > post the IDL, as from that one can usually deduce the form of arguments > expected. Hum, it is just an OCX. Can you tell me how to get an IDL from this. I have appended what dolphin produced on typelib generation for now. The closest I could imagine is now: array1 := (SAFEARRAY withAll: #( 1 2 3 4) elementClass: DOUBLE) . array2 := (SAFEARRAY withAll: #( 1 2 3 4) elementClass: DOUBLE) . series addArray: array1 size yArray: array1 asVariant xArray: array2 asVariant. but it does not work, either?!? This remembers me of some errrors I had during generation, can you make any sense of them? Error: TC5ISeries>>CalcXSizeValue:Value: at line 9: undeclared 'Value' Error: TC5ISeries>>calcXSizeValue: at line 5: undeclared 'Value' Error: TC5ISeries>>CalcYSizeValue:Value: at line 9: undeclared 'Value' Error: TC5ISeries>>calcYSizeValue: at line 5: undeclared 'Value' Error: TC5ISeries>>XValueToText:Value: at line 9: undeclared 'Value' Error: TC5ISeries>>xValueToText: at line 5: undeclared 'Value' Error: TC5ISeries>>YValueToText:Value: at line 9: undeclared 'Value' Error: TC5ISeries>>yValueToText: at line 5: undeclared 'Value' Error: TC5IValueList>>Locate:Value: at line 9: undeclared 'Value' Error: TC5IValueList>>locate: at line 5: undeclared 'Value' Error: TC5TeeRect class>>defineFields at line 5: undeclared 'Defines' (While AddArray:... is in the TC5ISeries interface, these convert errors seem to be unrelated to the array problem I have, or what do you think?) Ciao ...Jochen ------------------------------------------------------------ AddArray: arraySize YArray: yArray XArray: xArray "Private - Invoke the AddArray() method of the COM object. Helpstring: 'Adds an array of data directly to the Series.' HRESULT __stdcall AddArray( [in] long ArraySize, [in] VARIANT YArray, [in, optional] VARIANT XArray);" <virtual stdcall: hresult 111 sdword variant variant> ^self invalidCall |
In reply to this post by Blair McGlashan
ah yes, and here's the stack trace:
16:29:08, Freitag, 7. Februar 2003: 'HRESULT Error: Schwerwiegender Fehler (FACILITY_NULL)' TC5ISeries(IDispatch)>>hresultError: TC5ISeries(ExternalStructure)>>invalidCall TC5ISeries>>AddArray:YArray:XArray: TC5ISeries>>addArray:yArray:xArray: UndefinedObject>>{unbound}doIt CompiledExpression>>value: SmalltalkWorkspace>>evaluateRange:ifFail:debug: ... |
In reply to this post by Blair McGlashan
Ah weekend, time to do real work :-).
Finally I had time to fire up VC++ and look into the typelib of the ocx. Here is the IDL of the offending method: HRESULT AddArray( [in] long ArraySize, [in] VARIANT YArray, [in, optional] VARIANT XArray); Looks like dolphin did a good job converting so far. Maybe you experts see more... Ciao ...Jochen |
In reply to this post by Jochen Riekhof
"Jochen Riekhof" <[hidden email]> wrote in message
news:3e4397d5$[hidden email]... > [Blair McGlashan wrote] > > If you are having difficulty calling COM methods, then its a good idea to > > post the IDL, as from that one can usually deduce the form of arguments > > expected. > > Hum, it is just an OCX. Can you tell me how to get an IDL from this. Well you can use various tools (e.g. OleView from MS) or Dolphin itself. In the Active-X Component Wizard right click on a type library or interface and choose 'Browse IDL'. Dolphin will reverse engineer IDL from the type library. Be warned, however, that the IDL generated by any tool may not match the original IDL because the type library format is "lossy" and so does not necessarily contain all the original information, though this is rarely an issue. >...I have > appended what dolphin produced on typelib generation for now. The closest I > could imagine is now: > array1 := (SAFEARRAY withAll: #( 1 2 3 4) elementClass: DOUBLE) . > array2 := (SAFEARRAY withAll: #( 1 2 3 4) elementClass: DOUBLE) . > series addArray: array1 size yArray: array1 asVariant xArray: array2 > asVariant. > > but it does not work, either?!? You might like to read my most recent posting in the thread entitled "Help needed passing an array of float values by refference." It is possible your control is expecting the arrays to be passed by reference, and so they need to be wrapped up into the variant slightly differently than Dolphin's default conversion. > > This remembers me of some errrors I had during generation, can you make any > sense of them? > Error: TC5ISeries>>CalcXSizeValue:Value: at line 9: undeclared 'Value' > Error: TC5ISeries>>calcXSizeValue: at line 5: undeclared 'Value' >[...snip...] > (While AddArray:... is in the TC5ISeries interface, these convert errors > seem to be unrelated to the array problem I have, or what do you think?) These suggest a bug in the type library analyzer - it shouldn't generate methods that cannot be compiled. Is the OCX in question available for me to investigate it? Regards Blair |
Hi Blair...
> Well you can use various tools (e.g. OleView from MS) or Dolphin itself. In > the Active-X Component Wizard right click on a type library or interface and > choose 'Browse IDL'. Dolphin will reverse engineer IDL from the type > library. Be warned, however, that the IDL generated by any tool may not > match the original IDL because the type library format is "lossy" and so > does not necessarily contain all the original information, though this is > rarely an issue. I posted IDL generated from OCX with VC++6 in another post to the same ancestor message, but it shows the same code that dolphin wrote in the comment of the corresponding generated method. > You might like to read my most recent posting in the thread entitled "Help > needed passing an array of float values by refference." It is possible your > control is expecting the arrays to be passed by reference, and so they need > to be wrapped up into the variant slightly differently than Dolphin's > default conversion. Of course, I have immediately tried that out, but it did not work, either. I used array1 := VARIANT new. array2 := VARIANT new. array1 arrayRef: (SAFEARRAY withAll: #(1 2 3 4) elementClass: FLOAT). array2 arrayRef: (SAFEARRAY withAll: #(1 2 3 4) elementClass: FLOAT). series addArray: 4 yArray: array1 xArray: array2. > These suggest a bug in the type library analyzer - it shouldn't generate > methods that cannot be compiled. Is the OCX in question available for me to > investigate it? That would be really cool! I believe so. It is a very popular charting component: TeeChart 5 ActiveX. You can get a free evaluation version from http://www.teechart.com/download/Downloadindex.htm#TeeAXTrialver. Be shure to get the ActiveX version. It is probably a great test ocx for the interface generator, as it contains a lot of interfaces and methods. I can send you a piece of workspace code to set up a chart if you like, so that you do not need to dig through all the complex docs. Also, I recognized that while a chart set up in the workspace gives back the correct interface type calling controlDispatch, this is not true for an AXControlSite loaded from a resource? Here, I had to change the code back to MyInterface queryOn: ax controlDispatch. However, it works this way, so I don't bother much. Ciao and thank you for support! ...Jochen |
"Jochen Riekhof" <[hidden email]> wrote in message
news:[hidden email]... [ re: Compilation error on transcript running Active-X component wizard] > > These suggest a bug in the type library analyzer - it shouldn't generate > > methods that cannot be compiled. Is the OCX in question available for me > to > > investigate it? > > That would be really cool! > > I believe so. It is a very popular charting component: TeeChart 5 ActiveX. > You can get a free evaluation version from > http://www.teechart.com/download/Downloadindex.htm#TeeAXTrialver. Be shure > to get the ActiveX version. > It is probably a great test ocx for the interface generator, as it > a lot of interfaces and methods. I can send you a piece of workspace code to > set up a chart if you like, so that you do not need to dig through all the > complex docs. > The code generation/compilation errors are caused by the helpstrings in the IDL. D5.01 is copying these directly into the method comment, but as they can contain double quotes (which some of these do), the syntax of the generated method can be incorrect. This bug (#1118) has been fixed in the latest version of PL2, which is now available via Live Update. When running with PL2 installed, I didn't get any errors generating from this library. By all means send me the workspace, I'd like to see it. > > Also, I recognized that while a chart set up in the workspace gives back the > correct interface type calling controlDispatch, this is not true for an > AXControlSite loaded from a resource? Here, I had to change the code back to > MyInterface queryOn: ax controlDispatch. However, it works this way, so I > don't bother much. Hmm, thanks for that. This is caused by an oversight in the control recreation that occurs when the progId is changed. The site attempts to reuse the existing interface object so that clients can hold on to it. However when the progId is changed in the view composer, the old interface pointer object should be discarded completely. The patch below fixes this. In order to get it to take for any existing resource, you'll have to go into the view composer and evaluate an expression like this. self controlDispatch become: self controlDispatch asImplType Alternatively if you don't mind losing the control configuration, just change the progId to some other control, and then switch it back. Regards Blair --------------------- "#1144"! !AXControlSite methodsFor! createControl "Private - Create the embedded control in its initalized state." self free. "We must discard the old controls interface pointer, as it is probably of the wrong type" dispControl := nil. self safeCreateControlFromStream: nil! ! !AXControlSite categoriesFor: #createControl!public!realizing/unrealizing! ! |
In reply to this post by Jochen Riekhof-3
"Jochen Riekhof" <[hidden email]> wrote in message
news:[hidden email]... > .... > Of course, I have immediately tried that out, but it did not work, either. > I used > array1 := VARIANT new. > array2 := VARIANT new. > array1 arrayRef: (SAFEARRAY withAll: #(1 2 3 4) elementClass: FLOAT). > array2 arrayRef: (SAFEARRAY withAll: #(1 2 3 4) elementClass: FLOAT). > series addArray: 4 yArray: array1 xArray: array2. It occurred to me that the problem might be that the TeeChart control is expecting the arrays to have a lower bound of zero. SAFEARRAYs support an arbitrary lower bound, and for no particular reason, other than conceptual compatibility with Smalltalk arrays, we chose to use a lower bound of 1. For the most part this does not matter, as users of SAFEARRAYs are supposed to check the bounds and adjust indexing calculations to suit, however in this case it would appear to be the root of the problem. If you modify the SAFEARRAY class>>createVector:vt:extra: method to pass 0 as the lLbound: parameter ot the SafeArrayCreateVectorEx() API call, then you should find that you can successfully evaluate (for example): n := 10. series addArray: n yArray: ((1 to: n) collect: [:each | each squared]) xArray: (1 to: n) It seems that the control is only choosy about the lower bound being zero, and despite the fact that the SAFEARRAYs passed as a result of Dolphin's automatic coercion of (1 to: 4) will be safe arrays of variants holding integers, that still works as it should. The default lower bound in VB is almost certainly zero, so it probably makes sense to change Dolphin to use that as well. I don't believe that changing it to zero will cause any problems in Dolphin itself, since the SAFEARRAY wrapper class is independent of the lower bound - it has to be able to support the arbitrary bounds it may get back from the various sources that might create SAFEARRAYs. Certainly it runs our (limited) SAFEARRAY tests fine after the change. Also this doesn't affect the use of the array from within Smalltalk, as the #at: method offsets off the lower bound correctly so it always one-based inside Dolphin. Regards Blair ------------------ !SAFEARRAY class methodsFor! createVector: lenInteger vt: vtInteger extra: pvExtra "Private - Answer a pointer to a new vector (single dimensioned) SAFEARRAY of the specified size and element type, allocated by the OLE Automation Library. The lower bound is defaulted to zero for compatibility with VB." | answer | answer := OLEAutLibrary default safeArrayCreateVectorEx: vtInteger lLbound: 0 cElements: lenInteger pvExtra: pvExtra. answer isNull ifTrue: ["Unfortunately we don't know why it failed, because the call does not return an HRESULT, and doesn't SetLastError() either" ^self error: 'Failed to create vector']. answer beFinalizable. ^answer! ! !SAFEARRAY class categoriesFor: #createVector:vt:extra:!helpers!private! ! |
Blair...
> It occurred to me that the problem might be that the TeeChart control is > expecting the arrays to have a lower bound of zero. SAFEARRAYs support an > arbitrary lower bound, and for no particular reason, other than conceptual > compatibility with Smalltalk arrays, we chose to use a lower bound of 1. For > the most part this does not matter, as users of SAFEARRAYs are supposed to > check the bounds and adjust indexing calculations to suit, however in this > case it would appear to be the root of the problem. Yep, this helps! With the SAFEARRAYS internally starting from 0 the array passing works perfectly! It is probably a very good idea to use zero-based as default, as it is almost always used in practise (it's VB default as well). As some environments, e.g. VB-Script, can only handle zero-based arrays, Dolphin is also compatible here in this case. (and maybe sometimes a creation method that allows specification of lower bounds is useful). Thanks a lot! Ciao ...Jochen |
Free forum by Nabble | Edit this page |