Programming Guide:xppguide

Basic usage Foundation

Identifying COM/ActiveX components

Every installed COM/ActiveX component is listed in the Windows registry under the key HKEY_CLASSES_ROOT. It appears as follows:

ApplicationName.ObjectName.Version 

Additionally, all of those keys have a subkey called CLSID. The default value of this subkey can also be used to identify the COM/ActiveX component. The Microsoft Word Application can be accessed in the following way, for example:

oWord := CreateObject( "{000209FF-0000-0000-C000-000000000046}" ) 

Creating COM/ActiveX components

A COM/ActiveX component can be created using the function CreateObject(). CreateObject() returns an object of class AutomationObject(), which is connected to the newly created COM/ActiveX component. The Xbase++ application then uses the AutomationObject to interoperate with the COM/ActiveX component.

The functionality made available by a COM/ActiveX component may actually be supplied by another (non-Xbase++) application! Often, the AutomationObject obtained through CreateObject() can be used to control the supplying application itself. This process is known as Automation and is illustrated in the following example.

#pragma library( "ascom10.lib" ) 
PROCEDURE MAIN 
LOCAL oWord 

// 
// Create a new Word application. 
// The object returned can subsequently be used to 
// automate the new copy of Word. 
// 
oWord := CreateObject( "Word.Application" ) 
IF NIL == oWord 
   ? "Error" 
   ? ComLastError() 
   ? ComLastMessage() 
   WAIT 
   RETURN 
ENDIF 
oWord:quit() 
RETURN 

Using existing COM/ActiveX components

For accessing a COM/ActiveX component that has already been created, the function GetObject() is used. A character string passed as a parameter identifies the class of the COM/ActiveX component. Similar to the function CreateObject(), GetObject() returns an instance of class AutomationObject().

If a corresponding COM/ActiveX component has not been created yet, then GetObject() creates a component, applying the same method as CreateObject().

#pragma library( "ascom10.lib" ) 
PROCEDURE MAIN 
LOCAL oWord 

// 
// Access an existing Word Application. 
// Run a new copy of Word only if it 
// hadn't been started yet 
// 
oWord := GetObject( NIL, "Word.Application" ) 
IF NIL == oWord 
   ? "Error" 
   ? ComLastError() 
   ? ComLastMessage() 
   WAIT 
   RETURN 
ENDIF 
oWord:quit() 
RETURN 

Accessing COM/ActiveX functionality

Similar to an object in Xbase++, a COM/ActiveX component offers functionality through methods and properties. Xbase++ provides access to the properties and methods of a COM/ACtiveX component through the class AutomationObject(). Whenever a COM/ActiveX component is requested using functions such as GetObject() or CreateObject(), the component will be supplied as an instance of class AutomationObject.

To invoke a method on an COM/ActiveX component, an application calls a method of the AutomationObject. The AutomationObject then forwards the method call to the COM/ActiveX component to which it is connected to. It also takes care of converting parameters and handling errors that may result from the COM/ActiveX method invoked. An AutomationObject always provides the same methods as the connected COM/ActiveX component.

Similarly, the AutomationObject provides a member variable of the same name for each property provided by the connected COM/ActiveX component. Reading or writing the value of a COM/ActiveX property is done through manipulation of the AutomationObject's member variable.

#pragma library( "ascom10.lib" ) 
PROCEDURE MAIN 
LOCAL oWord 

oWord := GetObject( NIL, "Word.Application" ) 
IF NIL == oWord 
   ? "Error" 
   ? ComLastError() 
   ? ComLastMessage() 
ENDIF 

// 
// Use the AutomationObject to 
// access the COM/ActiveX property 
// "visible" 
// 
oWord:visible := .T. 

WAIT 

// 
// Use the AutomationObject to 
// call the COM/ActiveX method 
// "quit" 
// 
oWord:quit() 

RETURN 



COM/ActiveX components sometimes implement properties that use multiple parameters. Such a property can be seen as a member variable that stores a complex type and thus requires additional information to manipulate its value. The cells contained in a spreadsheet document may be maintained as a multi-parameter property, for example. In Xbase++, the syntactical equivalent to such a property is a method. Consequently, an application uses methods of the connected AutomationObject to access the multi-parameter COM/ActiveX property. The special method :getProperty() is used whenever you intend to retrieve the value of the property. Alternatively, a method call can be performed to obtain the property value. This is similar to calling an ACCESS method defined for a member variable directly.

To write the value of a multi-parameter COM/ActiveX property, the method :setProperty() must be used.

#pragma library( "ascom10.lib" ) 
PROCEDURE MAIN() 
LOCAL oExcel, oSheet, oCell 

oExcel := CreateObject( "Excel.Application" ) 
IF NIL == oExcel 
   ? "Error" 
   ? ComLastError() 
   ? ComLastMessage() 
ENDIF 
oExcel:visible := .T. 

oSheet := oExcel:workbooks:add():activeSheet 

// 
// Access the property "cells" that takes two 
// parameters. Syntactically, this looks like 
// a method call. In this case, the value of 
// the property is another AutomationObject. 
// Alternatively, the following code can 
// be used: 
//   oSheet:getProperty( "Cells", 1, 1 ) 
oCell := oSheet:Cells( 1, 1 ) 

// 
// Manipulate the AutomationObject retrieved 
// 
oCell:Value := "Hallo" 

WAIT 

oExcel:quit() 

RETURN 

Feedback

If you see anything in the documentation that is not correct, does not match your experience with the particular feature or requires further clarification, please use this form to report a documentation issue.