cancel
Showing results for 
Search instead for 
Did you mean: 

Code in OLE Control Events within PowerBuilder not executing

ricardojasso
Participant
0 Kudos

Hi All,

I’m using PB 12.5 Build 2511 on Windows 10.

I've been using SocketTools' File Transfer Control 8.0 since a long time ago and have been using its ActiveX control with PB with no problems until now. Well, sort of because now I'm trying to do something new.

The way I normally use the control in PB is by declaring an OLEObject variable and calling the pertinent methods from the object. Here is a code example of how I use it and works ok (I excluded error handling):

OleObject lole_ftp

lole_ftp = create OleObject

lole_ftp.ConnectToNewObject("SocketTools.FileTransfer.8")

lole_ftp.Initialize('<product key>')
lole_ftp.ServerName = ‘…’

lole_ftp.ServerPort = 21

lole_ftp.UserName = ‘…’

lole_ftp.Password = ‘…’

lole_ftp.TimeOut = 30

lole_ftp.Options = 1

lole_ftp.Connect()

lole_ftp.GetFile('c:\somefile.zip', 'somefile.zip')

lole_ftp.Disconnect()

lole_ftp.Reset()

Destroy lole_ftp

All this works perfectly, but the thing is, now I want to access the ActiveX control events so I can write some script and show a progress bar of the copy process. I understand I cannot do this by using the current method so I read PB's documentation and learned that I have to create an OLE control inside a Window so that the control events get exposed. I did this and now I can see the OnProgress event which according to the manufacturer’s documentation gets fired once a second or so.

So I inserted a line of code to update a progress static text (see image) but the code in the event doesn’t gets executed even though the file gets copied. It could be a fault in the ActiveX control but I seriously doubt it because the control has been in the market for many years and it even includes code examples for doing this using Visual Basic 6 and C++. PowerBuilder is mentioned as a language that can use the control but there are no examples using it for this case.

Any help would be greatly appreciated.

Ricardo

Accepted Solutions (1)

Accepted Solutions (1)

Former Member
0 Kudos

We're also long time users of the Sockettools controls.

I've just tried this out in PB 12.5.2 build 5801 and it does work.

Steps I took to create test code:

create app

Create window

Create MLE status area (mle_status)

Insert OLE control on the window (SocketTools File Transfer Protocol Control 8.0) (ole_1)

Create button (cb_1)

ole_1.onProgress event
mle_status.text += mle_status.text += string(filename) + ", " + string(filesize) + ", " + string(bytescopied) + ", " + string(percent) + "~r~n"

cb_1.clicked event
long rtn
ole_1.object.Intialize("")
mle_1.text = ""
rtn = ole_1.object.connect("ftp.local.server", 21, "user", "password", "", 10, 11)          // 11 = passive + firewall + keepalive
mle_status.text = "connect = " + string(rtn) + "~r~n"

if rtn = 0 then
     rtn = ole_1.object.GetFile("c:\localfile.psd", "localfile.psd", 0, 0)

     mle_status.text += "xfer = " + string(rtn) + "~r~n"
end if

if ole_1.object.connected() then
     ole_1.object.disconnect()
end if

Result was a mle_status having a couple entries of info in it from the transfer. It's a fast connection (local network), so it doesn't have many events hit.

Result looks like this:

connect = 0
localfile.psd, 15569912, 8192, 0
localfile.psd, 15569912, 15569912, 100
xfer = 0
ricardojasso
Participant
0 Kudos

Brad,

Thank you so much for your time in creating and trying a test case. The fact that it worked for you prompted me to experiment with some changes until I finally got it working too!

Although your code is practically the same as my code I noticed you use an additional parameter in the GetFile function. After a closer look I also noticed you use SocketTools File Transfer Protocol Control 8.0, which comes as part of SocketTools ActiveX set of controls, whereas I use the stand alone SocketTools File Transfer Control 8.0.

So this prompted me to uninstall one control and install the other to see if this was the cause of the problem. In the process, I also changed my strategy by inserting the control directly into the window instead of building an ancestor and here is where I noticed something different. The window painter showed me a different set of properties than the ones I saw in the standard visual object painter:

To make a long story short, the problem was that I was inserting an OLE Control instead of an OLE Custom Control. When using ActiveX controls you must insert them as OLE Custom Controls and not as OLE Controls which are used for OLE automation.

When selecting Create OLE Control from the Window Painter a dialog opens with three tabs: Create New, Create From Files, and Insert Control. I was choosing the Create New tab when I should be choosing the Insert Control tab to select and insert the control.

Incorrect selection method for inserting ActiveX controls:


Correct selection method for inserting ActiveX controls:

After I inserted the control as an OLE Custom Control the status text began showing the progress of the download process.


Again, thank you, and everyone else who commented on this post, for your time.

Regards,

Ricardo Jasso

Answers (2)

Answers (2)

Former Member
0 Kudos

Hello Ricardo,

I noticed that it looks like you also coded onTaskBegin, onTaskEnd and onTaskRun. Do those events get fired as you would expect?

How big is your file, could it be that it takes less than 1 sec to transfer and therefore never fires the onProgress?

ricardojasso
Participant
0 Kudos

Christopher,

Those events are triggered when using AsynGetFile() instead of GetFile(). This command downloads the file asynchronously on the background and triggers those events. I tried it but it didn't work either.

My test file is about 20MB and I put it in a hosted FTP server to test the process. In my environment it takes several minutes to download. Precisely that's why I want to show a progress bar to the user.

I inquired SocketTools about this and this is what they responded:

Q: I need to know what windows event id the OnProgress event is triggering. I use PowerBuilder and could successfully insert an OLE object inside a window using your FTP ActiveX control but when I try to add code to be executed by the exposed OnProgress event within PowerBuilder nothing happens. It's like the event is not triggering although the file gets downloaded from the FTP server. I'm using the Getfile() method to download the file.

A: The event ID for OnProgress is 9, but the actual Windows message ID isn't something that's directly exposed by COM (and not something PowerBuilder should need). Whenever you define the event handler, PowerBuilder should create an event sink using the ISinkEvents interface, then obtain the IConnectionPoint interface from our component and use the Advise method to register itself with the control. When that's done, the PowerBuilder application is notified whenever an event is raised. Generally speaking, this should all be handled transparently for you by PowerBuilder.

I don't have much experience with event id's so any help will be greatly appreciated.

Ricardo

p.s. One of my colleagues suggested that the download process might be running in a separate thread and that that might be the reason the work thread is not seeing the events from the worker thread. But this is just mere speculation.

Former Member
0 Kudos

Hello Ricardo,

I assume you've set a break in onProgress to verify that it gets there?  Was just thinking that if any parameter was null, it would look like the event didn't fire, because st_progress.Text would end up null.  Just clearing the obvious out of the way.

I've seen this before, many, many, many moons ago, but having trouble remembering how I resolved it.

ricardojasso
Participant
0 Kudos

Christopher,

That's a good point. I thought about it before and removed the code and inserted a new one without the variables. The result was the same.

Inserting a break point doesn't make any difference either.

Ricardo

Former Member
0 Kudos

Hello Ricardo, Did you get this resolved?

ricardojasso
Participant
0 Kudos

Christopher,

No I didn't. The last mail exchange I had with the control manufacturer was this:

Q: Is there any way I can trace this lack of connection between PowerBuilder and your control? As I mentioned before everything works fine except the events interface. Maybe I could try a different way in which I would assemble the event interface myself directly in a standard user object inherited from the oleobject.

A: I'm not aware of any way to do this directly. Event sinks are part of the COM API, so theoretically it would be possible but I imagine a fairly complex thing to try and do. This is really something that is the domain of the language or development tool to handle itself, since it has to "wire" the COM event notifications into whatever mechanism it uses for events.

I'm not in a hurry to implement this, though it would be nice to show the progress of the download to the user specially when large files are involved or there is a slow connection.

I guess I'll implement something like Roland Smith's Top Wiz FTP Client where the file is manually handled and sent in parts so I can update a progress bar inside the loop.

Ricardo

Former Member
0 Kudos

Hi Ricardo;

1) You do not need to build a visual OLE container. You can build a non-Visual one instead using the Standard Class User Object painter (File=>New in the IDE).

2) You may need to read the documentation from SocketTools and see what events the OCX sends you. These may only appear once you map in some User Events that correspond to the Message ID's the OCX might send you.

3) You can definitely run the SocketTools OCX visually as well if it supports that mode. Just make sure that you build a proper ancestor for this using the Standard Visual class User Object painter (File=>New).

Regards ... Chris

ricardojasso
Participant
0 Kudos

Chris,

1) This strategy is the one I currently use, although I built a Custom Class instead of a Standard Class inherited from the oleobject type which is what I believe you are suggesting. But the result is the same. I do not have access to the ActiveX events. So I do need to create a visual object inside a window so I can have access to the events. In fact, when I do so I get to see the events (see same image).

2) I'll check this.

3) I don't see the reason to create an ancestor although it surely is a good practice. But inserting the control directly in the Window should work. Unless there is a technical difficulty I'm unaware of.

Ricardo

Former Member
0 Kudos

Hi Ricardo;

  It all depends as well whether the SocketTools OCX exposes any events to you. It may not.

You might want to try this control. It does expose events to PB during FTP operations ....

http://www.dart.com/winsock-activex-tcp-control.aspx

HTH

Regards ...Chris

ricardojasso
Participant
0 Kudos

It all depends as well whether the SocketTools OCX exposes any events to you. It may not.

I mentioned in my original post that the ActiveX control has methods and events (see image), and what I want to do is access the later so I can write code that gets executed when the events are fired by the control.