Skip to Content

Using Classic ActiveX Controls in the ABAP Control Framework

About 6 months back I wrote a weblog on how to integrate Windows .Net Controls with the ABAP Control Framework. Given the age of this technology I was a little surprised at how many interested responses I got to this weblog. Many people wanted to know how to do this same thing in classic VB as opposed to .Net. So for a while I have been planning to write a weblog on how to do this. So in my attempt to get caught up on my weblog backlog, I sat down to write this one.

I want to show how to integrate any ActiveX control with the ABAP control framework. This activeX control might have been written in Classic VB, C++, or any of the .Net CLR Languages. To demonstrate the flexibility of the control framework, I will use a delivered Microsoft ActiveX control as the example. I will show you how to write an ABAP control framework program that will work with the Windows Media Player control.

The Example Program
I wanted to use the Microsoft Windows Media Player Control. So I decided to write an MP3/WMA player in ABAP. Now I can listen to my music while I program! The following is a screen shot:


This application will keep a list of Music files stored on my local drive. I thought about actually uploading the files to the SAP system database, but I thought somebody might notice an overnight 20Gig growth in the database. The playlist however is stored in SAP and controlled via ABAP. When the end of a song is reached, the Media Player control will raise an event. That event will be trapped and processed in ABAP. ABAP is then responsible for choosing the next song and sending the command to the Media Player to start it.

The following is a diagram that shows how the ActiveX control communicates through the SAPGui to the ABAP OO Proxy class.


Let’s talk about what we see in this diagram. On the top we have the scope of the client (SAPGui). The bottom part of the diagram has everything that takes place on the Application Server. Our ActiveX Control will be hosted by an OLE Controller in the SAPGui. The Automation Contoller is piece of functionality built by SAP in the SAPGui. It is responsible for the lifetime of the ActiveX control. It also traps all the events raised by the ActiveX control and communicates them through the Automation Queue. There is an Automation Queue on both the Client and the Server. Since there could be a considerable lag between the Client and the Server it doesn’t make sense to create a complete round trip every time an event is raised. Therefore all events are queued on both sides until the most efficient time to communicate them.

Now back on the Server Side we have the ABAP Control Framework. This set of classes (CL_CFW) provide the low level interface between ABAP and the Frontend. They handle all the dirty work of the OLE Automation. All we are left to write is ABAP proxy class for the ActiveX control itself. This proxy class will contain the methods and events from the ActiveX control that we want to have access to in ABAP as well. It is this proxy class that will in turn interact with the ABAP Control Framework Classes.

Understanding the ActiveX Control
First of all before we can start programming from ABAP, we need to have a good understanding of how our ActiveX control is structured. We need to know what events and methods are available. Since this ActiveX control was created by a Third Party, we may not always have easy access to this information or any documentation about the control. Therefore I like to use the Visual Basic Object Browser to have my first look.


Now as you will see later, knowing the methods and events isn’t going to be enough. We are going to have to know the Hex Codes for the event Ids. The best way I have found to get these is to use the Microsoft OLE/COM Object Viewer.


To do I right mouse click on the object in question and choose View Type Information.


Then the ITypeLib Viewer opens in another window. I change my view in this tool to Group by Type Kind. I then open the Dispinterfaces node. Inside here I find the dispinterface _MediaPlayerEvents. This will list all the events, their parameters, and their event IDs. As you can see in this screen shot, the EndOfSteam event has the ID 0x00000bba.


Now I know that everyone can convert HEX to Integer in their head right? If not, the following is a little bit of ABAP code that I keep around to do the job for me. You should see tht 00000bba is integer 3002

So far we have access to the key pieces of information we will need. We have the names of the methods. We also have the ActiveX control’s ClassID/ProgramID: MediaPlayer.MediaPlayer.1. Finally we have the event Ids we will need: ENDOFSTREAM – 3002. We are ready to start programming from the ABAP side of the world now.

ABAP Proxy Class
From the ABAP side we will need to create our Proxy Class to expose our ActiveX control. We will start by creating a class that inherits from the SAP Control Framework class CL_GUI_CONTROL. We will also need to enter CNTL as a forward declaration.


Next we will create attributes matching up to the properties we saw in the ActiveX control. We can use these local attributes as a cache for the ActiveX control properties. ABAP programs can query these attributes instead of always making a round trip to the frontend. It is also helpful to create constants to match up to the ones declared in the ActiveX Control. This makes programming much simpler.


Now we come to the constructor of the Proxy Class. It is in this area that we make the connection to the control framework. We also instantiate the ActiveX control on the Front-End. The Windows Media Player is only available as an ActiveX control. Therefore if the Control Framework says that we are running in the Java SAPGui (not javabean is initial), we just raise a GUI_TYPE_NOT_SUPPORTED exception.

We will have several different types of methods in the proxy class. First up we need methods that can set properties in the ActiveX control. Most of the functionality is provided by the Control Framework itself.

Now we have the corresponding method that can get properties.

Call methods is just about as simple as working with properties. There are a set number of parameters that can be passed to the Call Method Proxy. You must specify in the p_count method how many proxy parameters you will be using.

Now we come to the subject of events. The first thing we need to code is a method in our proxy class that can allow our programs to set the registered events that we want to respond to. The following is the code to do that. Please note that set_registered_events is an inherited method that must be redefined.

Now we need a method that the Control Framework can call any time that it receives events from the Front-End. This method will be responsible for requesting any parameters that go along with this event. It then can dispatch this event to the proxy events. This is a redefinition of an inherited method.

Now we have a proxy class ready to use in any ABAP Program. This class can be worked with like any other Enjoy Control Class (ALV Grid, Tree Control, etc). The following is my MP3 player program that uses this class.

Of special note in the program is the example of how the automation queue works. Have a look at the following block of code:

As you can see here, we are creating several requests to the front-end control. It would be inefficient to make several round trips. Therefore on the ABAP Application Server all of these request are really only added to the Automation Queue. It is only when you issue the control framework flush, that these requests are sent to the front-end. They are all processed there completely before control returns from the front-end to the application server. Only then will the variables author and title be filled.

In case you want to recreate the complete example here is also a screenshot of my table that I store the play lists in SAP.

I hope that my little MP3 player shows you the power of what can be done with ABAP and the Control Framework. In the past few years, SAP’s focus has shifted away from the SAPGui (Fat Client) to the more socially acceptable Web Based Clients. However in many situations, the Fat Client still has advantages and capabilities that its thiner relative does not.

You must be Logged on to comment or reply to a post.
  • Hi Thomas,
    Thanks for the post.  Do you know if it is possible for a custom control to do an RFC callback into SAP to perform further processing, rather than solely relying on raising events.
    Obviously such a control would be SAP specific but it would be quite useful on odd occassions.  I'd be surprised if there's not some underlying RFC connection at play here.
    • I would think not, at least not in the terms you are thinking about.  From your activeX control you really don't have visibility the hosting object.  Therefore you wouldn't have access to the SAPGui Automation Controller.  That is the level that would be communicating via RFC (and would have callback ability).

      I supose though there is nothing stopping you from integrating say the .Net Connector into your ActiveX control.  You could then call out from the connector to R/3.  You would be executing in a spearate session than the Proxy Hosting session.  I guess it would all depend upon what you were wanting to do. 

  • I create a Abap proxy control just like the one metioned in this topic. But after call construct method of the new proxy control, the MediaPlay doesn't show on the screen. I don't know why.
    Using the Debugger, I can see the object is not NULL after "create object"  call. Can you tell me how to make it go well?
    And there is also something I doesn't clear. In the sample code, you call
    and other method. But I don't know how to implement these method, can you give me the more detail code about it?
    Hope the reply from you, and thanks a lot.
    • If you are having problems you can always turn on the SAPGui trace. Activate all Modes and Detailed Output. You will want to select Automation as the object to trace. You will also want to set Synchronous processing from System->Utilties->Autom. Queue: Synchronous Processing. Have you tried to look at the Media Player object in the OLE viewer to make sure it is installed and that program ID matches the one in my example. Older versions of windows didn't automatically have the Windows Media Player.

      Set_show_display and set_show_status_bar are just property setters and follow the example in the weblog.

      method set_show_status_bar .
      call method set_property
      property = 'ShowStatusBar' "#EC NOTEXT
      value = show_status_bar "#EC NOTEXT
      cntl_system_error = 1
      cntl_error = 2
      others = 3.
      if sy-subrc <> 0.
      raise error_cntl_call_method.

      * echo current property of control in attribute (public, read-only) of
      * class. Thus calls to get method and eventually necessary flushes can
      * be avoided and performance is improved.
      m_show_status_bar = show_status_bar.


    • The constructor parameters should look the same as any of the other SAP Control Proxy Classes.  The following is the definition that I used (Sorry about forgeting that):

      @78\QImporting@     VALUE( STYLE )     TYPE I  DEFAULT 0     control style, if initial a defined value is choosen
      @78\QImporting@     VALUE( PARENT )     TYPE REF TO CL_GUI_CONTAINER     Parent Container
      @78\QImporting@     VALUE( LIFETIME )     TYPE I OPTIONAL     for life time management
      @78\QImporting@     VALUE( NAME )     TYPE STRING OPTIONAL     name for the control
      @03\QException@     ERROR_CNTL_CREATE          Error while performing creation of Multimedia Control!
      @03\QException@     ERROR_CNTL_INIT          Error while initializing Multimedia control!
      @03\QException@     ERROR_CNTL_LINK          Error while linking Multimedia control!
      @03\QException@     ERROR_DP_CREATE          Error while creating DataProvider control!
      @03\QException@     GUI_TYPE_NOT_SUPPORTED          This type of GUI is not supported!

  • Hi Thomas,

    Finally I got some time to play around based on weblog, however I got lost a little bit:-(

    Can you explain me how to set the initial values for class ZCL_ES_GUI_MULTIMEDIA_VIEWER attributes based on OLE/COM Object Viewer?
    I found the 'Windows Media Player' in the tree 'All Objects', with right click I could choose 'View type information...'...then with search I could find 'mpShowFilename = 0', but I couldn't find EndOfStream for example.

    Can you provide also some more info about table ZES_MP3_PLAYLIST?

    Thanks in advance,

      • Thanks a lot for your help.
        It's getting clearer now, but something is still missing, because I still cannot see the Media Player controller. I'll check tomorrow.
          • Hi Thomas and Peter,

            I also got lost, and not only a little bit. I am a very beginner but really interested in this example. So, I would like to seize this opportunity and kindly ask you to email me your complete object transport files, if possible.
            I am also greatly interested in the 'New ABAP editor; too good to wait for' blog. If you have detailed stuff that you could share on this subject, it would really appreciated.
            Thank you very much indeed.



          • Sending transport files isn't really an easy task any longer.  Here in the USA many companies are having to tighten their internal controls because of the Sarbanes Oxley act (thanks alot Enron).

            My company now tightly controls the release and tracking of all transports - making it very difficult to give them out. 

            However I do have a WebAS running on my Home PC that isn't under my company's control.  I can recreate the solution there by hand and cut you a transport from there.  However that process obviously takes time (something that is in sort supply right now).  I can get you transports but you will have to be patient.

  • Hi

    What version of the WAS are you doing this on?
    I am trying this example on WAS 6.20 patch level 44. I get the error 'Method "SET_SHOW_DISPLAY" is unknown or PROTECTED or PRIVATE. I've looked at the class I created and it does not have this method.



    • Actually this example was written years ago on 4.6C.  The SET_SHOW_DISPLAY is a method that you have to code into the control proxy class.  I did not include the complete source code for the class because this was really just intened to be a demo of what is possible. However if you want the complete source code for the proxy class, I can email it to you.  My email address is visible in my SDN business card.
    • What exactly is the error you are getting?  EVT_ENDOFSTREAM should be a constant that represents the ID of the Client event - not a ABAP Objects event.
    • Hi thomas,

        Really a great blog, finally iam able to execute the program, i have tested with vedio files either it is coming , but only problem is iam not able to see the controls of window media player. (like buttons play , pause stop and so on).

      Iam able to see the playlist in the ALV container

      Please help me what could be problem, i have to simulate the same to another appliation.

      Is there any chance to send the transport files.

      Thanks in Advance

      Kishore Yera,

      • There is no email address in your SDN Business Card - so if you want to send me an email (my address is in my Business Card), I can send you text files with the solution coding.

        There was a SAPGui bug quite some time ago that caused the player to be active but not visible.  That could be one possible problem (in your email also send your SAPGui version and patch level); but it could also be a problem in the control proxy implementation. 

  • Hi Thomas,

    I have read your blog with very much interest, and have one question:

    Do you know if it is possible to integrate an activeX component into a web Dynpro application. It is not a absolute demand that the component is embedded in the web Dynpro page, but I have to control it from the web Dynpro application (start it, tranfer parameters, and poll it for status).
    As I see it the Adobe interactive forms are an ActiveX component, so I think that it should be possible, but I would like you to verify and maybe give me some hints where to look for more information/examples/tutorials.

    Best regards,


    • The short answer is no - customers may not integrate their own ActiveX components into Web Dynpro.  This would violate the purpose of the client abstraction that is so central a theme to Web Dynpro.

      Customers may not create their own UI controls, nor can you include any custom HTML or JavaScript.  This is done on purpose to ensure that your investment in creating applications is safe for the future.  When the next great UI/Client technology comes around, you won't have to recode your applications to take advantage of the technology - only the SAP Supplied Web Dynpro Framework will have to change.

      If you need ActiveX integration, then you should consider falling back to BSP or JSP; depending upon which language - ABAP or Java that you want to code in.

  • Hi
        This may not be directly relevant to this example but deals with some basic understanding of Automation controller which is intriguing me for quite a while

    Refer to the Controls tutorial in SAP documentation

    But I find that no matter whether I use flush or not calls are always synchronous. May be this is due to the data provider but then how do I appreciate the importance of flushing as its always being issued implicitly.

    Refer to Lesson 3. Flush Optimization
    Exercise 1 : Using Imported Values
    of Controls Tutorial (BC-CI).

    Screen has a text control.
    The requirement is that whenever user clicks the protect button in the screen all the lines selected in the text control are to be greyed out.

    *Code in PAI module

    Case OKCODE.
          DATA: FROM_IDX TYPE I,
                TO_IDX TYPE I,
                INDEX TYPE I.
    *Determine the area selected by the user with the *mouse:

              FROM_LINE = FROM_IDX
              TO_LINE = TO_IDX
              ERROR_CNTL_CALL_METHOD = 1.

    * Synchronize execution in the control with your ABAP program:

    CALL METHOD cl_gui_cfw=>FLUSH.

    Now I find that even if flush is commented from_idx and to_idx always refers to the actual line index but as per our understanding and the note in SAP help as mentioned below they should have been initial.

    Help text is
    "Without this synchronization, variables FROM_IDX  and TO_IDX  have obsolete values".

    I have run it in debug mode with Automation controller check box  set as well as cleared but no difference.

    Is it possible for me to disable the usage of Data provider through some gui setting so that I can appreciate the flushing better.

    Right now ABAP code is always getting the latest GUI values (even without flushing) as if the code is executed synchronously. Please help. We are in 4.6C and gui version 7.10

    With regards

    • It is possible to active synchronous mode - from the main menu - System->Utilities->Autom. Queue Synchronous Processing.  However if that is set, you probably would be getting horrible performance in every transaction.

      What class is this editor object?  Many of the GUI classes now place a flush within the method calls themselves so that the exporting variables are populated. 

      • HI<br/>  Thomas<br/>   Thanks a lot for the reply.<br/>I am using cl_gui_textedit and Automa queue sync processing isnt turned on. But behaviour is almost that of a sync processing as the control itself seems to issue a flush within the method call. <br/>  <br/>This is the trace (texts are selected and then protect_lines method called)<br/><br/>*************** data to server **************<br/><br/>=1314>Automation: Sending data to server via diag<br/>=1314>Automation:  ==============  Controlmanager DataStream 274 bytes =============== <br/>=1314>Automation: <?xml version="1.0" encoding="sap"?>*************** data from server **************<br/><br/><1315=Automation: SAPAWRFC entering FLUSH with RFC_HANDLE 9<br/><1315=Automation: SET PROPERTY "EnableEditingOfProtectedText" OF <br/>                    #0: LONG "1"<br/><1315=Automation:                    elapsed time for flush = 0.000 sec<br/><1315=Automation: SAPAWRFC leaving FLUSH with return code 0<br/><1315=Automation: -

        <br/><1315=: <br/>
        ************** data to server **************<br/><br/>************** data from server **************<br/><br/><1316=Automation: SAPAWRFC entering FLUSH with RFC_HANDLE 9<br/><1316=Automation: CALL METHOD "ProtectLines" OF <br/>                    #0: LONG "1"<br/>                    #1: LONG "2"<br/>                    #2: LONG "1"<br/><1316=Automation:                    elapsed time for flush = 0.000 sec<br/><1316=Automation: SAPAWRFC leaving FLUSH with return code 0<br/><1316=Automation: -

        <br/><1316=: <br/>
        ************** data to server **************<br/><br/><br/>************** data from server **************<br/><br/><1317=Automation: SAPAWRFC entering FLUSH with RFC_HANDLE 9<br/><1317=Automation: SET PROPERTY "EnableEditingOfProtectedText" OF <br/>                    #0: LONG "0"<br/><1317=Automation:                    elapsed time for flush = 0.000 sec<br/><1317=Automation: SAPAWRFC leaving FLUSH with return code 0<br/><1317=Automation: -

        <br/><1317=: <br/>
        ************** data to server ***************<br/><br/><br/>Actually whats happening is that as soon as user selects some portion of the text control flush happens and after that when get_selection_pos is called it fetches the correct selection index.<br/><br/>That means ABAP tutorial is misleading and all these tutorials probably refer to an old gui where flush wasnt incoporated within the method calls. Hence we cant probably appreciate many of the flush concepts through the tutorials. Isn't it?<br/> 

        • Its not really a new GUI.  The Flush method calls were placed directly in the ABAP coding of the proxy class method.  So when in doubt, just have a look at the inner coding of the method you are calling.  I think the flush method calls were placed in the code to make the proxy classes easier to use.  Yes the documentation does refer to an older situation.
          • Hi
               Thanks a lot for the clarification that it refers to an old situation. I used to be confused as the demo code didnt run as expected.


  • Hi Thomas
    Thanks for a great blog. It helped me to integrate an OCX in the SAP GUI, which sends lengths to a cutting machine via the serial port on the PC. You explained a great example which helped me to deliver this function to my business with great value.
    • Dear Erik,

      i have a requirment in my project to use an OCX in SAP GUI, as you said you've done it i need to do the same thing but with weighing machine.

      Could you please tell me how did you use that OCX in ABAP?


      • Dear Erik / Kholoud,


        I got same kind of requirement to use an OCX in SAP. as you were already implemented, It would be greate help if you suggest me or guide me to do the same thing.

  • Hello Thomas!

    For considerable time I'm trying to integrate a Word Document into a CL_GUI_CUSTOM_CONTAINER. But the method you explained in this blog doesn't work when I'm using Prog_IDs 'Word.Application', 'Word.Basic' etc.
    In case of starting Word with command
    create object go_word 'Word.Application'.
    everything works fine but the window is not embedded in sap gui.
    Do you know any possibility of integrating a word document (apart of classes i_oi_document_proxy)?

    • >Do you know any possibility of integrating a word document (apart of classes i_oi_document_proxy)?

      I can't say that I have ever tried.  If I wanted Word integration I alwasy used the  built in Office Integration.

  • Hi Thomas,

    Thanks for the blog, thats cool that you can play your songs on SAP. I am trying to play around with this, but I am not very comfortable with .NET or VB, so I have a questions as
    if is it possible to call any 3rd party application using this method within SAP or are there any restrictions? Also, can you send me the code snippet to my email id if its ok with you?

    Thanks in advance..

    • >if is it possible to call any 3rd party application using this method within SAP

      No it is not possible. The control framework is designed to work with COM/COM interop controls within the SAPGUI for Windows.  It is not "all purpose" integration.  This is why you need the interface IDs of the COM layer. 

      >Also, can you send me the code snippet to my email id if its ok with you?

      All of the key code parts are listed in the blog.  I've changed jobs (to come to work for SAP) since this blog was originally published and don't have the original development objects any longer.

      This example is quite old now - notice the 2005 publication date.  I don't know if I would advise spending too much more time on the control framework since SAP has moved onto other UI technologies.

      • Thanks for the Prompt response Thomas. Can you suggest any possible SAP techniques which can be used or any SAP blog related to calling or controlling any 3rd party application within SAP.


        • >calling or controlling any 3rd party application within SAP.

          Well most desktop applications aren't designed for such integration.  You can't just take any desktop application and expect it to run inside another desktop application.  The 3rd party application has to be designed to run within another application using specific technologies like OLE or ActiveX.  For instance most of Microsoft Office has such interfaces and SAP uses them for Desktop Integration. 

          What kind of 3rd party applications do you have and what kind of integration technologies do they expose?

          • I am actually trying to call a 3d(JT) viewer within SAP or atleast call its controls from SAP. I believe that it is designed using ActiveX Controls and they have pre-defined API's that I can use and few OCX controls which can also be used if necessary.


          • A 3D viewer (CAD I assume) is the kind of thing that is generally integrated as a control as described here if needed in the SAPGUI.  SAP does delivery a 3D viewer in the SAPGUI for PLM. I'm not PLM expert but you might look into that or look for a partner solution in this space.

            Otherwise you are looking at an ABAP proxy class against the OCX control in the control framework.  Depending upon your release level another consideration might be BSP with the ActiveX control.

    • Hi Thomas,

      Thanks for your great blog, that's so cool that you can play your songs on SAP.I followed step by step, but still got many problems.
      Eg:evt_endofstream is unknown.
      Could you send me the code?Thank you very much!