LET statement   

Purpose

Assign a value to a variable, or assign a Dispatch Interface reference to an object variable in preparation to use a COM interface.

Syntax

[LET] variable = expression

[LET] objvar  = NEW {DISPATCH | InterfaceName} {ON} {ProgramID$}

[LET] objvar  = {DISPATCH | InterfaceName} {ON} ProgramID$

[LET] objvar1 = objvar2

[LET] objvar  = NOTHING

[LET] objvar  = vrntvar

[LET] vrntvar = objvar

[LET] vrntvar = vrntvar

[LET] vrntvar = EMPTY

[LET] vrntvar = ERROR numr

[LET] vrntvar = expression [AS vartype]

[LET] vrntvar = array()

[LET] array() = vrntvar

[LET] vrntvar = BYREF variable

Remarks

The LET keyword is entirely optional.

The following text describes the operations of the enhanced forms of the LET statement:

[LET] objvar  = NEW {DISPATCH | InterfaceName} {ON} {ClassName | ProgramID$}

Upon execution, a new object (instance) is created, and a reference to that object is assigned to the object variable objvar.  If the new object cannot be created (for example, there may be a lack of available memory or the requested interface might not be supported), the object variable is set to NOTHING.  The success or failure of the operation can be tested with the ISOBJECT(ObjVar) and/or ISNOTHING(ObjVar) functions.

objvar

objvar must be dimensioned as an object variable of that Interface name: DIM objvar AS interfacename for early-binding, or DIM objvar AS DISPATCH for late-binding.  Early-binding requires a declaration of the Interface with an INTERFACE/END INTERFACE block.

ProgramID$

ProgramID$ is not case-sensitive and may be a string variable, string literal or string equate. The string expression ProgramID$ is presumed to evaluate to a PROGID name for an external COM Server (COM Object).

Interfacename

Name of the interface from the early binding declaration. Methods and Properties are accessed with the OBJECT statement.

[LET] objvar  = {DISPATCH | InterfaceName} {IN | ON} ProgramID$

objvar

objvar must be dimensioned as an object variable of that Interface name: DIM objvar AS interfacename for early-binding, or DIM objvar AS DISPATCH for late-binding.  Early-binding requires a declaration of the Interface with an INTERFACE/END  INTERFACE block.

ProgramID$

ProgramID$ is not case-sensitive and may be a string variable, string literal or string equate.  The string expression ProgramID$ is presumed to evaluate to a PROGID name for an external COM Server (COM Object) which is currently running and initialized via COM Services.  For example, "Word.Application".  In this case, COM services will be utilized to open an Interface on the existing object, and a reference to that object is assigned to the object variable objvar.

Interfacename

Name of the interface from the early binding declaration. Methods and Properties are accessed with the OBJECT statement.

If the operation is not successful (for example, if the interface specified is not supported on ProgramID$), the object variable objvar is set to NOTHING. The success or failure of the operation can be tested with the ISOBJECT(ObjVar) and/or ISNOTHING(ObjVar) functions.

[LET] objvar1 = objvar2

If both Object Variables have been declared as the same object type (the same interface name), the source variable (objvar2) is copied to the destination variable (objvar1), and the reference count of the object is incremented.  If the object variables are of different object types, a new interface (of the type implied by objvar1) is opened on objvar2, and a reference to it is assigned to objvar1.  If the operation is unsuccessful, objvar1 is set to NOTHING.

[LET] objvar = NOTHING

Destroys an object variable, discontinuing its association with a specific object.  This in turn releases all system and memory resources associated with the object when no more object variables refer to it.

[LET] objvar = vrntvar

Attempts to open an interface of the specified class for objvar on the object of vrntvar, and assigns a reference to objvar.  It assumes that vrntvar contains a reference to an object of type %VT_UNKNOWN or %VT_DISPATCH.

If the desired interface cannot be opened, the object variable objvar is set to NOTHING. The success or failure of the operation can be tested with the ISOBJECT(ObjVar) and/or ISNOTHING(ObjVar) functions.

[LET] vrntvar = objvar

Used to assign an object reference from an object variable to a variant variable.  It attempts to open an IDispatch interface, else an IUnknown interface on the object of objvar, and assigns that reference to vrntvar.

Variant variables cannot contain references to custom interfaces, only IDispatch or IUnknown.

If the assignment is successful, VARIANTVT(vrntvar) will return either %VT_UNKNOWN or %VT_DISPATCH.  If it is unsuccessful, vrntvar is set to %VT_EMPTY.

[LET] vrntvar = BYREF variable

Used to allow a variant to contain a typed pointer  to a specific variable.  Any changes to the variant will cause the variable to be changed, as it is the target of the pointer.  The variable may be of any data type which is supported by variants and COM objects:  Byte, Word, Dword, Integer, Long, Quad, Single, Double, Currency, Variant, and dynamic String.  If you attempt to use an unsupported variable type (like Extended, Bit, ASCIIZ, etc.), PowerBASIC will generate an Error 482 (Data Type Mismatch).  Further, you may not use a register variable (automatic or explicit), or an Error 491 (Invalid Register Variable) will be generated.  Note that strings used with COM objects are expected to be in Unicode format, rather than ANSI.  The ACODE$ and UCODE$ functions may be used to convert the strings as necessary.

Assignments to variants

When working with variant variables, all necessary internals are managed appropriately by PowerBASIC.  When setting a Variant to EMPTY, it is considered to contain no value at all.  It is also possible to assign a specific COM error number (usually a COM specific error, such as %E_NOINTERFACE, etc) using the ERROR numr syntax.

When assigning values to variants, PowerBASIC automatically analyzes the expression and chooses an appropriate numeric or string data type for the internal representation of the Variant.  However, you can specify a particular preferred format by adding the optional AS vartype clause.  For example:

LET xyz = 21.34 AS LONG

In the above example, the Variant would actually contain the value 21, as the programmer forced it to Long-integer representation.  vartype may be one of the following keywords: BYTE, WORD, DWORD, INTEGER, LONG, QUAD, SINGLE, DOUBLE, CURRENCY, STRING.

The fifth and sixth forms allow you to assign an entire array to a Variant, or convert it back to a PowerBASIC array.  In the case of a dynamic string array, the appropriate ANSI/Unicode conversions are handled automatically.  This array assignment is always subject to the type compatibility of each component.  For example, you cannot assign an Extended-precision floating-point array to a Variant, nor can you assign an array with more than eight dimensions to a PowerBASIC array.

Restrictions

LET cannot be used to assign a string to a User-Defined  Type (UDT) or UNION.  Such an assignment must be performed with the CSET, LSET, RSET, or TYPE SET statements.  UDTs and Unions can be directly assigned to string variables.

See also

CSET, CSET$, LSET, OBJECT, RSET, SET, TYPE SET

Example

LET DummyStr$ = "This is a test."

LET TempStr$ = DummyStr$