You are on page 1of 93

US 2002O124054A1

(19) United States


(12) Patent Application Publication (10) Pub. No.: US 2002/0124054A1
DOrn et al. (43) Pub. Date: Sep. 5, 2002
(54) MEDICAL SYSTEMARCHITECTURE BASED (30) Foreign Application Priority Data
ON MICROSOFT OLE/OCX AND
AUTOMATION OR, RESPECTIVELY, Jun. 27, 1996 (DE)........................................ 1962.5841.3
ATOMC
Publication Classification

(76) Inventors: Karlheinz Dorn, Kalchreuth (DE); (51) Int. Cl." .............................. G06F 15/16; G06F 9/46
Detlef Becker, Moehrendorf (DE); (52) U.S. Cl. ............................................ 709/217; 709/313
Dietrich Quehl, Erlangen (DE)
(57) ABSTRACT
Correspondence Address:
SCHIFF HARDIN & WATE A medical System architecture with a modality (1 through 4)
6600 SEARS TOWER for the acquisition of images, a means (5 through 8, 11, 12)
233 SWACKER DR for processing the images and a means (9) for the transmis
CHICAGO, IL 60606-6473 (US) sion of the images. The means (5 through 8, 11, 12) for
processing comprises a digital image System with a com
puter that works according to a method for data eXchange
(21) Appl. No.: 09/881,492 between various application programs (OLE) with graphic
control elements and a standard for OLE Custom Controls
(22) Filed: Jun. 14, 2001 (OCX), whereby an OCX software component (18) is allo
cated to every individual process limited by boundaries,
these OCX Software components being expanded with an
Related U.S. Application Data OLE Automation or ATOMIC remote control component
(19, 22, 27 through 31, 35 through 41) so that the devices
(63) Continuation-in-part of application No. 08/883,303, and processes can be remote controlled without any limita
filed on Jun. 27, 1997, now abandoned. tions caused by address Space or computer boundaries.

View
DL
Proc
Server

Automation interface
LOCa Controller FSM 21 Control
Server 20 - : Automation
--
interface 27

Automation interface 28

Sever
23
\t
is as
a lice

Automation interface F-29


SA
Model

Automation interface 30
local ev, ce. Model

Automation interface -31;


Patent Application Publication Sep. 5, 2002 Sheet 1 of 6 US 2002/0124054 A1

1 2 3 4

471
Rosa
N. MY

22
2
2. 261
E.
2 242
/
-5 G-6 7 -8
9
15

NETWORK F)
NETWORK
INTERFACE

11 ses
-12
See 10

LOCAL MAGE STORE CENTRAL MAGE STORE

FIG 1
Patent Application Publication Sep. 5, 2002 Sheet 2 of 6 US 2002/0124054A1

Container Application Exe


18

18
w

OCX View
DLL- Automation interface 19
InProc
Server Pucal

Automation interface 22
LOCal Controller FSM 21 Control
Server 20 - Automation interface
--- -27.

Automation interface 28:


seawicz Model
LOCal Sevice 25
23
Server \ Automation interface
A F-29,

Automation Interface 30
LOcal : Sea V ca. Model
Sevice
Automation interface
S
Patent Application Publication Sep. 5, 2002 Sheet 3 of 6 US 2002/0124054A1

Container Application Exe


18 17
CX

F
18

View
DLL- Autonnation interface 19
is
Server a rows
Automation interface 22.
DLL Controller FSM 21 Control
Automation interface -27

Automation Interface 28
Jaa l/a Ca.
B s 25 Model
LOCal 23\
Server Automation interface u29:
S. A. S.

Automation interface 30
LOCal 24 4A3 WCell Model
Server N 26 l
: Automation interface 3
Patent Application Publication Sep. 5, 2002 Sheet 4 of 6 US 2002/0124054 A1

DLL View
nProC
Server

Automation interface 22:


Local 33 Controller FSM 21: Control
Server i Automation Interface 27.

Automation interface 28
DLL &ea V (Ca. 25 : Model

29:

: Automation interface 3o:


Local 24 Sé as vice : Model
Server N 26.
w

Automation interface
SA A
Patent Application Publication Sep. 5, 2002 Sheet 5 of 6 US 2002/0124054 A1

Container Application Exe


Roox X

y
f
V
18
OCX View
DLL
nProC Automation interface 19
Server

Automation interface
DLL N Controller FSM 21 Control
Automation interface
S t

Automation interface
DLL

40 ab
St
po as a a
i.
Sé/gvica.

Automation interface
AS
is a as as p - - -
Model

Automation Interface
Local
Server
t
S4 (3 v/ca

Automation Interface
Model
Patent Application Publication Sep. 5, 2002 Sheet 6 of 6 US 2002/0124054 A1

DLL View
nProC
Server

20N COnnectable/Remote 36:t


LOCal Controller FSM 21 Control
Server : Connectable/Remote
O 37

23 38.
\ 25, Model
Local
Server 39

24\ 40
LOCal Model
Server 26
US 2002/O124054A1 Sep. 5, 2002

MEDICAL SYSTEMARCHITECTURE BASED ON 0010. The transfer of medical images between self-con
MICROSOFT OLE/OCX AND AUTOMATION OR, tained components (and other programs as well) is carried
RESPECTIVELY, ATOMIC out by usage of the DICOM protocol. The DICOM protocol
enables image transfer between imaging modalities of dif
CROSS-REFERENCE TO RELATED ferent manufacturers. DICOM (Digital Imaging and Com
APPLICATION munications in Medicine) is an industrial standard which
was developed by the American College of Radiology
0001. The present application is a Continuation-In-Part (ACR) and the National Electrical Manufacturers Associa
Application of Ser. No. 08/883,303, Filed Jun. 27, 1997. tion (NEMA). DICOM 3.0 is implemented by the Radiology
Society of North America (RSNA) Electronic Communica
BACKGROUND OF THE INVENTION tions Committee. DICOM is discussed at http://www.r-
Sna.org/practice/DICOM/dicom.html on the internet.
0002) 1. Field of the Invention
0011. The design of the self-contained software compo
0003. The present invention is directed to a medical nents (especially non-GUI components) follows the rules of
System architecture with a modality for acquiring images, a the Software ICS for high level application frameworks,
device for processing the images and a device for the which is the Subject of co-pending application Ser. No.
transmission of the images, whereby the device for proceSS 09/773,949, filed Feb. 1, 2001, which is a CIP application of
ing comprises a digital imaging System with a computer that the application Ser. No. 08/675,846, filed Jul. 6, 1996, and
WorkS according to a method for data eXchange between which is incorporated herein by reference.
various application programs (OLE) with graphic control
elements and a standard for OLE Custom Controls (OCX), 0012. The components are coupled loosely by means of
whereby an OCX software module is loaded into the virtual an location transparent (invisible) event propagation mecha
address Space of every process. nism. The reference to invisible connections refers to loca
tion-transparent connections, Such as that disclosed in
0004 2. Description of the Related Art ATOMIC (Asynchronous Transport Optimizing observer
pattern-like approach Supporting several Modes (client/
0005. As described, for example, in the book by Heinz server-push/pull) for an IDL-less Conmnunication Sub
Momeburg, “Bildgebende Systeme fuir medizinische Diag System, which is the Subject of co-pending patent
nostik, Erlangen, Publicis MCD-Verlag, 3rd Edition 1995, application Ser. No. 08/676,859, filed Jul. 7, 1996, and
pages 680-697, medical Systems are becoming more and which is incorporated herein by reference).
more complex, whereas the degree of expansion of medical
Systems increases to the same proportion. As a result thereof, 0013 The above and other objects and advantages are
however, an extremely flexible architecture is required. inventively achieved in that the System architecture is fash
ioned such that the OCX software components are-extended
0006 Previously known architectures were not designed by a remote control component, which Supports an asyn
in compliance with distributed, asynchronous Software and chronous working model needed for non-blocking GUIs.
reusable, Self-contained Software components. In other The self-contained components can be distributed within a
words, a monolithic Software architecture approach was Single computer as well as over a network of computers
used. without the limitations found in previous Software architec
0007. Despite the use of object orientation, further, the tures. A good Solution of the objects derives by combination
Simple use of class libraries prevents the design of flexible of Software components (or objects) and a distributed event
and re-employable components since, in reality, classes are propagation mechanism.
not truly re-employable on a large Scale. One of the reasons 0014. It has proven advantageous when the remote con
of this lack of reusability is the outgrowth of C++ inherit trol component is an OLE Automation interface and the
ance where lots of different classes derive from others and remote control ensues according to the OLE Automation
result in huge unmaintainable Software blockS. Standard. Inventively, the remote control component can be
an automation interface module.
SUMMARY OF THE INVENTION 0015. An alternative advantageous solution derives when
0008. The present invention is based on the object of the remote control ensues with Software-IC connections, for
providing Software components (or objects) that exhibit a example according to the ATOMIC Standard. According to
behavior that is independent from other components as far as the invention, the remote control component can be a
possible. Further the connections between the components connectable/remote interface module in this case.
should be invisible in relationship to the location of these 0016. It has proven advantageous when the method for
components (or objects), So that they can either all be data exchange is the Microsoft standard OLE and the
combined in one process (local server), or combined in standard for OLE Custom Controls is the Microsoft standard
different processes (local Servers) of a computer, or can be OCX.
distributed into different processes (local servers) located at 0017. The present invention provides that the medical
Several computers connected to a network.
system architecture can employ Microsoft OCX for produc
0009 For purposes of the present invention, an indepen ing components for graphic user Surfaces within a MicroSoft
dent component is defined as a Substantially Self-contained container process, whereby Microsoft OCX can be com
component-having-no link-time (by design) dependency on bined with OLE Automation and/or with software ICs (for
other Software components and generally capable of opera example, the ATOMIC standard) for distributed propagation
tion independent from the execution of other components. of events within all levels of the architecture.
US 2002/O124054A1 Sep. 5, 2002

0.018. An important new feature is the combination of example, the images generated in the modalities 1 through
Microsoft OLE Custom Controls (OCX), a newly created 4 can be Stored in a central image Store, or memory, 10 or
Software technology, with another, general MicroSoft Script can be forwarded to other work stations 5 through 8.
ing Standard interface that serves as a fully distributable
network-wide mechanism for the propagation of an event 0028. Further work stations that can be connected to a
(referred to as an event propagation mechanism) as Soon as local image Store, or memory, 13 and 14, which is for
network-wide OLE is available in order to obtain a realistic example a jukebox, can be connected to the image commu
Model View Controller concept (MVC) based system archi nication network as diagnosis consoles 11 and 12. The
tecture. images that are acquired and deposited in the central image
Store 10 can be Subsequently called in the diagnosis consoles
0019 Preferably, Microsoft OCX can also be employed 11 and 12 and be deposited in the local image store 13 and
for producing components for graphic user Surfaces (Graphi 14 from which they can be directly available to a diagnos
cal User Interface (GUI) components) within a Microsoft tician working at the diagnosis consoles 11 or 12.
container process. As a result thereof, one obtains truly
binarity compatible, re-employable GUI components. 0029) A network interface 15 via which the internal
image communication network 9 is connected to a global
0020) Further, Microsoft OCX can be inventively com data network can be connected to the image communication
bined with OLE Automation and with Software-IC connec network 9, So that the Standardized data can be exchanged
tions for the distributed propagation of an event (referred to worldwide with different networks.
as an event propagation) with local between all components.
This provides the flexibility for the distribution of compo 0030 This image data exchange via the image commnu
nents over the network combined with binary-compatible nication network 9 thereby ensues according to the DICOM
interfaces based on shared libraries. Objects which are Standard that is widespread in medical Systems, which is an
distributable and GUI dependent as well as not GUI-depen industrial Standard for the transmission of images and other
dent are thus obtained. medical information between computers for enabling digital
communication between diagnostic and therapy apparatus of
0021. This combination of software-ICs and OCX/Auto different manufacturers.
mation interfaces enables an execution architecture to define
executable processes not by design but mainly by configu 0031. The complexity of medical imaging systems is
ration of shared program components (shared libraries (or increasing rapidly. Thus a major requirement on a System
DLLs-dynamic link libraries)) at runtime together with the architecture is the reuse of proven parts of the Software.
possibility of Scripting. More and more imaging modalities are connected to a
clinical network and must be able to inter-operate with each
BRIEF DESCRIPTION OF THE DRAWINGS other. This requires that a System architecture enables the
0022. The present invention is explained in greater detail Software to use network wide Services Such as image Stores
on remote computers. Although the image acquisition Sys
below on the basis of exemplary embodiments shown in the tems of the modalities (MR, CT, etc.) are completely dif
drawing. Shown are: ferent, there is a lot of functionality which is identical for all
0023 FIG. 1 is a block diagram of a medical computer modalities (e.g. patient registration, archiving, networking,
network of the related art; image Viewing, image processing, filming, etc.). The System
0024 FIGS. 2, 34 and 5 are functional block diagrams architecture must provide means for reuse of Such com
monly used functionality designed for one of the modalities
showing the inventive collaboration of the software com on otherS modalities without programming. This requires
ponents according to a first exemplary embodiment, and that this Software does not depend on modality Specific
0.025 FIG. 6 is a functional block diagram illustrating environment.
the inventive collaboration of the Software components 0032. The present invention deals with these require
according to a Second exemplary embodiment. ments by defining a System architecture according to the
DETAILED DESCRIPTION OF THE MVC concept (Mode View Controller). A functionality or
PREFERRED EMBODIMENTS So-called application (e.g. patient registration) is divided
into three parts (i.e. 3 tiers), the view (a thin client) which
0.026 FIG. 1 shows the system architecture of a medical provides means for a graphical user interface, a controller
computer network. The modalities 1 through 4 serve for the that contains the business logic (validation of patient data
acquisition of medical images and can comprise, for like Sex, weight, age, etc.), and one or more models (ser
example a CT unit 1 for computer tomography, an MR unit vices) like database Systems or network connections. These
2 for magnetic resonance, a DSA unit 3 for digital Subtrac three parts (tiers) of an application are build according to the
tion angiography and an X-ray unit 4 for digital radiography Software-IC concept, which allows distribution and runtime
as image-generating Systems. Work Stations 5 through 8 with configuration in different processes. These three parts (tiers)
which the modalities 1 through 4 can be controlled and the of an application are coupled tightly as a result of their
acquired medical images can be processed and Stored can be Semantics.
connected to these modalities 1 through 4. For example, 0033. The coupling of different applications is loosely by
such work stations 5 through 8 are very fast small computers means of events. An example of loosely coupling is the
having one or more fast processors. event propagated by the image acquisition application after
0027. The work stations 5 through 8 are connected to an the acquisition finished. The image viewing application can
image communication network 9 for the distribution of the display the newly acquired imageS as a reaction of this
generated images and for communication. Thus, for event. If there is no image viewing application configured on
US 2002/O124054A1 Sep. 5, 2002

this modality, the event is ignored. Tight coupling of these ponents 25 and 26 are coupled to one another via further
applications (e.g. by link-time dependencies) would always Automation Interface components 27 through 31.
require the image viewing application to be installed on this 0040. The structure is essentially the same in FIGS. 3
computer. This loosely coupling between applications through 5; the configuration of the components into pro
allows them to be reused all together or in parts by other cesses is merely different. Whereas all MVC components in
modalities by simply configuring these components (Soft the first case according to FIG. 2 are respectively arranged
ware-ICs) at runtime. in a separate process, the View and control components in
0034. The present invention combines the advantages of the example according to FIG.3 are arranged in one process
both, the software-ICs and the OLE/OCX technology by and the model components are arranged in Separate pro
applying a remote control component. The Software-ICS cesses. This means that the control level of the controller 21
provide means for building self-contained and fully distrib is already located in the same dynamic link library (DLL) of
utable components with a location transparent and asynchro a in-process Server 32 as the application program 17 of the
nous (non-blocking) event propagation mechanism. The View component.
OCX technology allows the usage of different progratming 0041. In the subject matter according to FIG. 4, the
languages (e.g. Visual C++, Visual Basic, etc.). The remote control and model components are combined in one process
control comrponent uses the event propagation mechanism and are located in the same dynamic link library (DLL) of
according to ATOMIC as the external asynchronous inter the local server 33. Preferably, there is also the possibility of
face to be used for communication between components and configuring the View, control and model components accord
the Synchronous OLE automation interface as the internal ing to FIG. 5 into one process in the dynamic link library
interface to the component. The Synchronous internal auto (DLL) of an in-process server 34, whereby a further service
mation interface of the remote control component allows component is contained in a further local Server 24.
non-thread-Safe programming of the component while the
asynchronous (non-blocking) external interface provides 0042 FIG. 6 shows a second example according to the
means for queuing of the input and output events. Another MVC concept (model view controller) that is similar to the
advantage of the remote control component is it's role as a example of FIG. 2. Here, too, the View area is again located
mediator between the external and the internal interface and in a dynamic link library (DLL) of the in process server 16.
thus allows the modification of the component's program What are referred to as software-IC connection 35 (connect
code (business logic) without the risk of changes of the able/remote) are coupled to the OCX software components
external interface. 18 of the application program 17 loaded in the server 16 as
0035 FIG. 2 shows a first example of a software archi remote control components instead of the Automation Inter
tecture according to the MVC concept (Model View Con face components 19. The communication with other local
troller) wherein the view, control and model components are servers 20, 23 and 24 is enabled with these components. The
respectively contained in different processes. The View area controller 21 in the local server 20 can thus be for coupling
is located in a dynamic link library (DLL) of an in-process the View component with the model component. This con
server 16. troller is likewise coupled to corresponding Software-IC
connections 36 and 37. The model component is arranged in
0036) A dynamic link library is a collection of object files the local servers 23 and 24 in which the service components
that are (dynamically) linked (made available) at the run 25 and 26 are contained via further Software-IC connections
time of a proceSS and that can be simultaneously shared by 38 through 41, which is the subject of co-pending patent
a plurality of processes. The implementation of a Service is application Ser. No. 09/773,949, filed Feb. 1.2001, which is
realized Such that given the in-proceSS Server 16 this Service a CIP application of the application Ser. No. 08/675,846,
must always run in the same proceSS as the client who filed Jul. 6, 1996, and which is incorporated herein by
requires this Service. DLLS are particularly Suitable therefor reference.
Since they make the Service dynamically available to the 0043. These connectable/remote software-IC remote
proceSS on demand. control components are fully distributable input/output
0037. The application program, which comprises a plu events based on an event-communicating network that is
rality of OCX software components 18, is loaded in the dynamically loadable and configurable by input/output con
server 16. Automation Interface components 19 of the OLE nections points.
Automation Standard are coupled to the OCX components 0044) The advantage of this inventive proposal is its
18 as remote control components. These components make flexibility and, even more, its productivity for achieving
it possible to communicate with other local Servers. A Software components which are re-employable in various
controller 21 for coupling the view level with the model medical System product architectures.
level can thus be stored in a second local server 20. This
controller 21 is likewise coupled to a corresponding Auto 004.5 The software-IC connections allow a truly arbitrary
mation Interface component 22. distribution of the components in executable processes with
out ending up in lock-up States as can be the case in other
0.038. The controller 21 is a component from the model communication mechanisms (for example, Corba) without
view component (MVC) world. The view thereby represents Source code modification. The components can even be
a way of viewing the model. Model and view are coupled via arbitrarily combined at the run time as a result thereof.
a controller component. This controller component is essen Another advantage is that the connections can be n:m
tially composed of an automatic State unit, what is referred connections (n Suppliers and m consumers), which is usually
to as a fmite state machine (FSM). not possible in traditional Systems, whereby the connection
0.039 The model component can be contained in two parties anonymously find one another at the run time accord
further local servers 23 and 24 in which the service com ing to ATOMIC.
US 2002/O124054A1 Sep. 5, 2002

0046. In addition, the component connections also differ cation and includes Structure corresponding to the figures of
from traditional connections in that event data are transmit the present application. Further, GUIs and a complete Source
ted on the connections and no remote methods are called. code for all three tiers and the ATOMIC based communi
The usage of remote methods makes it difficult to adapt the cation Source code for the remote control component is
busineSS logic of a component to the needs of new imaging presented.
Systems without braking the Signature and the Semantic of 0048 Although other modifications and changes maybe
the component's external interface. Suggested by those skilled in the art, it is the intention of the
0047. An example of a use case for the present medical inventors to embody within the patent warranted hereon all
System architecture is shown in an Appendix, attached changes and modifications as reasonably and properly come
hereto. The example utilizes the terms of the present appli within the scope of their contribution to the art.
US 2002/0124054 A1 Sep. 5, 2002

APPEND IX
CONTINUATION-IN-PART APPLICATION
entitled: MEDICAL SYSTEMARCHITECTURE BASED ON MICROSOFT OLE/OCXAND
AUTOMATION OR, RESPECTIVELY, ATOMIC
US 2002/0124054 A1 Sep. 5, 2002

1 Medical Software Architecture based on a 3-tier component model


and asynchrony Remotecontrol Component to prevent blocking
User Interfaces
This paper gives a use case example for a proposed Software Architecture concept which
guarantees asynchron communication between software parts totally implemented as
components based on standards like SOFTWARE IC, ATOMIC or OCX.
A fundamental part besides of the architecture concept is a RemoteControlComponent which
guarantees non-blocking beaviour.
1.1 Remotecontrol ComponentOCX Responsibilies

o Send/Retrieve stringified data as key/value pairs to/from backend components


(with asynchrony command channel and multiple replies).
a Retrieve update event changes initiated by the backends business logic (read-only
ATOMIC event channel per command channel.
o Send/Retrieve ATOMIC events on arbitrary event channels.
O Inbuilt GenericMain ability for the containerware e.g. load components, dispatch
ATOMIC events & commands.

The Remotecontrol ComponentOCX class collaborates with the ATOMIC standard classes to
attach to Application and Modality channels or to the command handling system that
implements proxies,command objects and returns. It runs typically within the context of a
MacroOCX as a non-visual MicroOCX all dispatched via a generic CapGM frontend container
executable. In case that a different 3-rd-party container is used, the
Remote(ControlComponentOCX can be switched into a mode where it is able to do all
necessary dispatching (behaving like a CapGM without a GUI) in addition to its other roles.
A generalized RemotecontrolComponentOCX is depicted in the figure below, along with the
general User Interface and Backend objects that it collaborates with. The
RemoteControlcomponentOCX uses the Command-, Proxy- and Command Mediator-Design
Patterns.

The picture below shows the architecture. In this case the UI is connected to a controller component mediated via
the help of the Remotecontrol ComponentOCX. The controller component is configured component which can
run even in generic Container executable. The controller could then connect to a model component(s) and deal
with the proxies and returns as well as AT event channels bound to these models. Each of these components are
allowed to run all within individual containers or grouped altogether and running within a single container. This
means, that the execution architecture is totally configurable and not fixed at configuration but configurable even
at runtime.
US 2002/O124054A1 Sep. 5, 2002

HTML, VisualBasic, C++, ...


View (GUI) (Language 11ndependent)

log 1. - Atomic events


Remote Control
Component Command
Mediator (Atomic)
Atomic events
Xy
-

Command
Controller FSM Object (Atomic)
Component loi is Atolnic events

Command
Model (Service) Object (Atomic)
Component
Atomic events
US 2002/O124054 A1 Sep. 5, 2002

9. The User Interface code updates its presentation logic.


1.3 Controller initiated asynchrony Cls command communication to User Interface
In this generalized scenario, the data in the backend has changed, and the User Interface is
expected to update and to reflect the changes.
1. Some outside force changes data/state in a controller component.
2. The controller component sends an ATOMIC event (with the inbuilt update channel) to
the RemotecontrolComponentOCX.
3. The RemotecontrolComponentOCX receives the ATOMIC event and passes it to the
Command Mediator.
4. The Command Mediator sends an OLE event to the User Interface code indicating the
data change.
5. If the OLE event included the data as parameter, the UI code may use that data to
update its presentation. Otherwise, the User Interface code follows the same data
retrieval steps as in the first scenario above.

1.4 Event Propagation

These are the general steps when a User Interface Component participates on the ATOMIC
Event communication subsystem:
1. User Interface code makes a request for information via the OLE method interface on
the RemotecontrolComponentOCX to initialize dispatching subsystem (only when it is
not running within a CapGM GenericMain executable, e.g. in 3-rd-party executable).
2. User Interface code makes a request for information via the OLE method interface on
the Remote(ControlComponentOCX to create an event channel with a stringified
pattern (see ATOMIC standard).
3. The logic in the RemotecontrolcomponentOCX determines using an Event Mediator
that creates an ATOMIC event channel.
4. The thread of control in the Remotecontrol ComponentOCX returns to the User
Interface code.
5. User Interface code makes a request for information via the OLE method interface on
the RemoteControlComponentOCX to send an event to a previously created channel
via Supplying a stringified event.
6. Whenever the EventMediator within the Remotecontrol ComponentOCX logic
receives an event belonging to the same stringified channel pattern it sends an OLE
event to the User Interface code indicating that an ATOMIC event has arrived.

The following chapter offers a detailed description of the OLE Automation interface the
RemotecontrolComponentOCX provides as API to the user. Additionally the backend
consumer API will be explained. As the picture above is showing, the Asynchron
Communication Component consists of two parts, a frontend part (the
US 2002/O124054A1 Sep. 5, 2002

Automation-Method Description Mode


BSTR loadCommand Mediator(BSTRsName) SName specifies the name of the All modes
CommandMediator to be loaded. The
method return an id which does
unique identify this laoded
CommandMedaitor (CM) instance,
and which should be used to refer to
this Command Mediator instance.
This call can be made multiple times
from within an execution unit, even
with the same sName. Each call
creates a new separate channel to a
backend components command
consumer peer.
BSTR unloadCommandMediator (BSTRSID) See method above, just for unloading All modes
a specific Command Mediator
instance.
BSTR setCurrentCommand Mediator (BSTRsID) The sid does specify the CM instance All modes
which will then be used for further
calls.
BSTR getChannelName (BSTRsD) This method return the nametag for All modes
the in-build update event channel
BSTR callCustomCMMethod (BSTR sID, BSTRsMethod, This method does directly invoke a All modes
BSTRsParams) method at the CM interface
BSTR callProxyMethod (BSTR sID, BSTRsMethod, BSTR This method does directly invoke a All modes
sParams) method at the in-build proxy of the
selected CM. 'SetNameTag” is the
only sMethod parameter which
US 2002/O124054A1 Sep. 5, 2002
10

- should be used for now.


BSTR callReturnMethod (BSTRsID, BSTRsMethod, BSTR Method to directly invoke a method All modes
sParams) at the in-build return of the selected
CM
boolean setChannelName (BSTRsID, BSTRsName) The sid selects the proper CM and set All modes
the name tag of the inbuild AT event
channel. This channel is used for
update events, which are initiated by
the server. This channel is a oneway
channel from the server to the client
only
boolean setNameTag (BSTR sID, BSTR tag) This method sets the nametag of the All modes
communication framework (proxy,
return and command object). This is
necessary if more than one command
is running within the application.
void proxyAddKeyValue (BSTR sID, BSTRkey, BSTR value) This method adds a new key value All modes
pair to the key value list of the proxy.
void proxyClearkeyValueList (BSTR sID) Clears the key-value list of the proxy. All modes
This method should be called before
a new request to the backend is set up
via calling proxyAddKeyValue
multiple times.
void returnSetKeyValueToFirst (BSTR sID) Sets the pointer to the beginning of All modes
the key-value list within the return.
Typically used on the client side
when a return event has been fired
and the result key-value pairs have to
be processed, and after processing
one returnCetNextkeyValue should
|- be called later on.
boolean returnGetNextKeyValue (BSTR sID) Retrieves the next key-value pair of All modes
the key-value list of the return object.
The retrieved value and key are
stored internally and you can query
them with the following two
methods.
BSTR returnGetCurrentkey (BSTRs) See above All modes
BSTR returnCetCurrentValue (BSTR sID) See above All modes
boolean returnFindFirst (BSTRsID, BSTR key) This method searches the key value All modes
list until it detetics the first occurrence
of the specified key.
boolean returnFindNext (BSTRsID, BSTR key) Similar to the above method but just All modes
continious the search throgh the key
value list.
BSTRWaitupdateEvent (BSTRsD) Get the next update event out of the C
queue. In this case update event
queueing typically has been switched
O.
void QueueUpdateEvent (BSTR sID, BSTR qup, long anz) Enables that the update events which C
arrive in the Itfocx are internally
queued, as a consequence there is not
a OLE event fired for each incoming
update event
void initispatch (BSTR svc) This does switch on the container B
US 2002/O124054A1 Sep. 5, 2002
11

mode, one has to specify the


configuration file which contains the
components the vbgmaincompocx
has to load then. Please register the
WBGmain CompCCA when using the
interfaceCC in initi Pispatch movie
void exit Dispatch O This method does signal the leavage B
of the container mode
void QueueReturnEvent (BSTRsld, BSTRqup, longanz) Thius method enables the C
RemotecontrolcomponentOCX to
queu up internally the arriving key
value pairs. Please noie, that if this node is
eighieri, the picked node for the key-value
retti in pairs is also necessary and epialed as
is ei. is tears, that the event keyyal pairs are
ail criting in a single sing
BSTR WaitReturnEvent (BSTR sID) Get the next key value pair out of the C
intrual queue. . In this case return
event queueing typically has been
switched on.

void packReturnevent (boolean mode) Get all the internally queued key
value pairs of the return and pack
them into one string, which gets then
delivered via the ReturnBventiata
Event to the user. This could be
helpful on environments which
cannot callback into the
RemotecontrolComponentOCX
within the event firing method.
boolean initATEvtChan (BSTR ChanName) In addition to the inbuild oneway AT- D
event channel of the CM, there can be
additional arbitrary AT event
channels be created. This call is
forwarded to the EventMediator
which does manage these channels.
You should specify the string you
want inclusive delimiters for
hierarchies etc. There is no
application or modality pattern added
internally.
boolean exitATEvtChan (BSTR ChanName) Refere the channel you want to be D
destroyed.
void QueueATEvtChan (BSTR ChanName, BSTR qup, long Does queue up the incomming AT C
anz) events internally until a number of
anz events. All events not consumed
when a overrun occurs are lost.
BSTR WaitAtEvtChan (BSTR ChanName) Get the next AT event from the queue C
with the specified AT channel
pattern. The pattern is not bound to a
component pointer internally. This
cal does not block. It is intended for
environments that are not able to
receive events. In this case AT event
queueing typically has been switched
O
US 2002/O124054A1 Sep. 5, 2002
12

boolean sndAtEvtChan (BSTR ChanName, BSTR evt) Send the event-string evt to the
channel ChanName
boolean cancelCmdld (BSTRs.ID, BSTR cID) Cancel a command in channel sid All modes
with the commandid cid. The
backend has react with a call to
isTerminatedO
BSTR executeEx (BSTRsID) Execute a command in channel sid in All modes
async callback mode. The command
id cid is returned.
BSTR executeModeEx (BSTR sID, BSTR mode) Execute a command in channel sid in All modes
a specified mode. The commandid
cid is returned.
CALLBACK MODE,
FUTURE MODE or
ONEWAY MODE are allowed
boolean suspendCmdId (BSTRsID, BSTR cID) Suspend a command in channel sid All modes
with the command id cid. The
backend has react with a call to
isPause(true)
boolean resumeCmdId (BSTR sID, BSTR cID) Resume a command in channel sid All modes
with the command id cid. The
backend has react with a call to
isPause(false)
boolean continuecmdid (BSTR sID, BSTR cID, BSTR res) Continue a command in channel sid All modes
with the commandid cid and hand
out a user result res. The backend has
called co->suspendO previously to
ask the user for more information
(e.g. long running job is missing

boolean WaitCmdd (BSTR sID, BSTR clD, long timeoutsec)


resources and backend tries to ask
how to proceed).
Wait synchron for a command in
channel sid with the commandid cid
for up to timeout seconds. If the
als
timeout value is '-1', we are waiting
until a reply comes in. This API
makes only sense when the execute
command was activated in
FUTURE MODE for the given cID.
boolean DestroyCmdId (BSTRsID, BSTR cID) Destroy the return object internally All modes
kept within the
RemotecontrolComponentOCX via
the given commandid cID. This
makes sense for shutdown Scenarios
in combination with a following
cancelCmdid in order to destroy
queued objects on an immediate
shutdown request.
Automation-Events Description
void ReturnEvent (BSTRsID) This automation event gets raised All Modes
when a return object does arrive
internally. You get the id of the CM
delivered. Within the event handler
one can refer to the right Cn and
access the key value pairs of the
US 2002/O124054A1 Sep. 5, 2002
13

retrun object.
void UpdateEvent (BSTR sID, BSTRsMessage) This automation event gets raised
when the backend does send an AT
event on the in-build EventChannel
void Return EventBata (BSTRsID, BSTRsMessage) OLE-Event which gets delivered,
when a return arrives, but in contrast
to the FireReturnEvent all the key
value pairs are contained in the data
string. For the seperation tokens used
within the data string please refer to
the packReturnvent method
void ATEvtChan (BSTR ChanName, BSTR evt) This automation event gets raised
when on one of your own registered
AT channels an At event is received.
The event does deliver the naen of
the channel and the event string
US 2002/O124054A1 Sep. 5, 2002
14

FOOOOOOSOOO8.

WebBrowser Enableded Asynchronm:m Ewent Propagation Communication


Pattern

The page starts with some HTML headerstatements.

<head>
<body onload="Calc Onload ()" onunload="Calc. On Jnload ()" background =
"E: \Src\calcasp5V calcasp5 Local Vimages\Syngo. ppt background.jpg">
Afterwards a very thin UI part is following in HTML as well.
&HRs
<pa <FONT color=redd <STRONG >WebBrowser Enableded Asynchron 1 : 1
Client/Server Communication Patterna/STRONGc z/FONT> <Ap>
<ps <input name="Text 1" size="9" value="3" >
<input type="button" value="Add" name="Add" on click="Add Click ()"
></p>
<ps (input name="Text2" size="9" value="2" >
</p>
US 2002/O124054A1 Sep. 5, 2002
15

<ps (input name="Text3" size="9" >


<input type="button" value="Cancel" name="Cancel"
onclick="Cancel Click () " >
<input types "button" value="Suspend" name="Suspend"
onclick="Suspend Click () " >
<input type="button" value="Resume" name="Suspend"
onclick="Resume Click ()" >
</p>
kHR
<P> <FONT color=red> <STRONG-WebBrowser Enableded Asynchron&nbsp; n : m
Event Propagation Communication Pattern C/STRONG ></FONTs </Ps
<Ps & TNPUT name=send ChanTxt size="24" readOnly> Channnel name</P>
<PskINPUT type=button size="100" onclick="SendChanEvt Click () " value="Send
Event with Channel Name" name=Send Evt ></P>
<Ps (INPUT name=send EvtTxt size = "24"> Event send to Channel name</P>
<P><INPUT name=rcvd EvtTxt size=" B6"> Event from Channel name</P>
&HRs

The RemotecontrolComponentOCX has to be embedded on a HTML page via the object tag
as shown below ...

OBJECT classidic sid:B7AFED6F-E886-11D2 - A3E6-OOO4AC963AO1


id=RemotecontrolcomponentOCXi><PARAM NAME=" Version"
VALUE="65536"> <PARAM NAME="ExtentX" VALUE="2646"> <PARAM
NAME=" Extenty" VALUE="1323"><PARAM NAME="StockProps" VALUE="0">
</OBJECT

The RemotecontrolComponentOCX fires OLE events which can be sinked on the HTML
page as shown below ...

<script LANGUAGE-- "JAVASCRIPT" FOR="Remotecontrol ComponentOCX1"


EVENT="Return Event (ID)">
k --
returnevent (ID)
-->
</scripts
<script
LANGUAGE="JAVASCRIPT" FOR="Remotecontrol ComponentOCX1"
EVENT="Updatevent (ID, SUpdate.Param) ">
a --
updateEvent (ID, sUpdate Param)
-->
</scripts
<script
LANGUAGE-- "JAVASCRIPT FOR="Remotecontrol ComponentOCX1"
EVENT="ATEvtChan (chan, evt)">
a --
ATEvtChan (chan, evt)
-->
</scripts
US 2002/O124054A1 Sep. 5, 2002
16

Other unimportant GUIHTML primitives (like object tags with a lot of params) are ignored
for now, but the action handlers finally activated by these UI items are shown within some
script code below ...
<SCRIPT LANGUAGE = "JavaScript">
var sSid
var key
War wall
var key1
var val1
Var reto
War X.

As soon as the backend talks to the frontend, the RemotecontrolComponentOCX fires OLE
Automation events which will be forwarded to the two methods below (see also the object tag
above).
function return Event (ID)
Remote control ComponentOCX1 Return Event ( ID )

function updateEvent (ID, sparam)


Remotecontrol ComponentOCX1 UpdateEvent (ID , sparam )

When any component fires an AT event to a channel we pattern we used as Well, the OLE
Automation event below is fired.

function ATEvt Chan (chan , evt)


Remotecontrol ComponentOCX1 ATEvt Chan (chan, evt)

As soon as the UI will be loaded the RemoteControlComponentOCX has to be initialized


accordingly, and dispatching has to be switched on when not running within a syngo based
CapGM executable (which does AT needed dispatching automatically), but in a 3-rd-party
executable, for instance. This is shown in the code piece below. The call to
LoadCommand Mediator specifies a unique command mediator module via a string and gets
back an identifier (ssid) for the internally created command mediator instance. This id has to
be used for all calls to the Remote(Control ComponentOCX later on which are referring to this
channel. The call to SetChannelName specifies a unique command request channel string. We
will see that the backend site has to use exactly the same channel string in order to be able to
communicate via an UI channel created within the RemoteControlComponentOCX. The
method Call ProxyMetod with SetNameTag designates to a specific Update Event Channel
which has to be initialized on the backend site accordingly otherwise. This enables the
backend to find all the clients when it notifies a state change.
function Calc Onload ()
US 2002/O124054A1 Sep. 5, 2002
17

War retb
War ?ets
War
calc. ProgressBar1. Min = 0
calc. ProgressBarl. Max = 100
calc. ProgressBari. Value = 0
document. Remote Control ComponentOCX1. initDispatch (" ")
ssid =
document. Remotecontrol ComponentOCX1. loadCommand Mediator ("CKeyValueCM
)
retb = document. Remote Control ComponentOCX1. set ChannelName (ssid,
"VVKeyValueProxy VVMEDCOM1 \\ S.")
rets = document. Remotecontrol ComponentOCX1. callProxy Method (ssid,
"SetNameTag", "WWKeyValueProxy\\MEDCOM1\\S")
retb =
document. Remotecontrol ComponentOCX1. initATEvtChan (document. calc. send
ChanTxt. value) ;
Calc. Text 1. value = 4"
Calc. Text 2. Value = "9"
Calc. Text3. Value = " '

The sequence of these three commands can be called more than once and for every call a new
internal channel gets created. The parameter for loadCommandMediator should be always
*CKeyValueCM’ for now. The parameters of the other two methods should be different for all
individual channels but it should have the same value string for setChannelName and
callProXyMethod of a given channel SSid. Only this guarantees that the update event channel
(1:n) which can be triggered on server site correlates exactly with the command channel (1:1).
In the Xample below this name is"MEDCOM MOD" which creates both, an event and a
command channel only for the local machine. If a channel should be created for distributed
machines, the string pattern should be constructed according to a network pattern (take a look
into the AT user's guide for more information on creating AT local or network patterns. For
instance, if instead of "MEDCOM MOD" a different pattern, like "\MEDCOM MOD\S"
would have been used as parameter for both APIs, the communication would be possible even
across machine boundaries. Another precondition is that now on both machines the NPS
deamon has to be running. The NPS deamon itself is an software IC compliant backend
component which can be started with a CsaGenericMain backend container. An example
configuration file for the NPS deamon is shown below.
i ==============================================
# Example configuration file for the NPS daemon.
# =================s============================
# The daemon supports the following options:
# - d <Domain Name> : The logical domain name in which the NPS daemon is
located
# -j <joined Domains : Additional domain to which the NPS daemon is to be
joined
# - c <Cycle time> : Time in seconds between each broadcast the daemon makes
to
establish and keep contact to the other NPS daemons.
(default 60s)
US 2002/O124054A1 Sep. 5, 2002
18

# -b <broadcast ports : TCP/IP communication port to be used (default:


56251)
The port should have a value > 1024 and < 65536.
dynamic CsaNPS Service Object * CsaNPS's GMDLL3: make CsaNPSComp () "-A
OSCSYS & COMPUTERNAME% -b 64518 -d test Domain"

Keep in mind, that the backend site of the Remotecontrol ComponentOCX, the KeyValueCO
consumer class which runs typically in a CsaGenericComponent, uses the same string as
parameter in the Consumer initialize method and as the fifth parameter of the KeyValueCO
CommandObject's create method. This is necessary, otherwise the communication endpoints
would not be connected properly (see below).
myKeyValueCO = CKeyValueCO: : create ( (const chair
*) 0, true, CapAtcmdNoWBox Ta, (void *) O, "WWKeyValueProxy \\MEDCOM1 \\S");
// command channel
myKeyValueCO->initialize (this, "VVKeyValueProxyWWMEDCOM1\\S") ; // update
event channel

Additionally to the client / server communication mode, the Remote(ControlcomponentOCX


provides event propagation mode additionally. The initATEventChan method creates a bi
directional AT event channel via the help of the RemoteControl ComponentOCX. It supports
creating an arbitrary number of AT event channels and fires a proper OLE Automation event
when a subscribed channel received an event or allows sending an AT event via the subscribed
channel.
When a button has been pressed, typically a request will be activiated via calling the OLE
automation interface of the Remote(ControlcomponentOCX, as shown below.
The example shows that the Remote(Control ComponentOCX accepts an arbitrary number of
stringified key/value pairs after the list pointer has been reset and will send this current state of
the list of key/value pairs to its backend whenever the execute method is called. The method
will not block until the request has been processed on the backend site. In oter Words, the UI is
non-blocking. When execute has been called the return parameter is either 'C' or a real
command sequence request identifier (cmdid) is returned.
In the first case it indicates that on the backend site there is a controller component (suppose
an application architecture model based on frontend, controller, backend instead of just using
frontend, backend) and not a real business component. In this case the commandid is useless
for the client in the moment when execute has been called. The real command id will come
back later, via a reply event.
In the second case there is a real business component running on the backend and the
commandid can be queued. ...

function Add Click ()


US 2002/O124054A1 Sep. 5, 2002
19

calc. Text3 - value = ""


document. Remotecontrol ComponentOCX1.proxyClearKeyValueList (SSid)
key = "cmd."
wa. = "Add
document. Remotecontrol ComponentOCX1. proxyAdd KeyValue (ssid, key, val)
key = "sumA"
val = calc. Text 1. value
document. Remotecontrol ComponentOCX1.proxyAddKeyValue (ssid, key, val)
key = "sumB"
val = calc. Text2 . . value
document. Remotecontrol ComponentOCX1. proxyAdd KeyValue (ssid, key, val)
//document. Remotecontrol ComponentOCX1. execute (ssid)
val = document. Remotecontrol ComponentOCX1. executeModeEX
(ssid, "CALLBACK MODE")
if (val = 'C' )
AddOueued Result ("", Val)

The same command can be exuted also in future mode, where a wait call is used to reSync to a
previously activated command.
This has the same effect as a synchronous activation...
function. Add Click ()
calc. Text3. Value = ""
document. Remotecontrol ComponentOCX1. proxy ClearKeyValue List (ssid)
key = "cmd."
wall = ''Add'
document. Remote control ComponentOCX1. proxyAdd KeyValue (ssid, key, vall)
key = "sumA"
val = calc. Text 1. value
document. Remotecontrol ComponentOCX1.proxyAdd KeyValue (ssid, key, val)
key = "sumB"
val. = Calc. Text 2. value
document. Remotecontrol ComponentOCX1.proxyAddKeyValue (ssid, key, val)
val = document. Remotecontrol ComponentOCX1. executeModeEx
(ssid, "FUTURE MODE")
if (val = "C")
{
AddOueued Result ("", vall)
}
for (i = 0; i <10; i++)
rval1 = document. Remotecontrol ComponentOCX1. WaitCmdId (ssid,
calc. Combo 1. value, -1)
}
As we have seen above, a commandid that came back as a result of an execute method can be
stored anywhere in the frontend and later on used to cancel, suspend, resume or continue a
running job via the command id. A situation where cancel, suspend and resume are is used is
shown below. ...
US 2002/0124054 A1 Sep. 5, 2002
20

function Cancel Click ()


{
if (calc. Combo 1. List Count > 0)
{
rval1 = document. Remotecontrol ComponentOCX1. cancel CmdId (ssid,
calc. Combol. Value)

function Suspend Click ()


if (calc. Combol. value = " ")
rval1 = document. Remotecontrol ComponentOCX1. SuspendCmdId (SSid,
calc. Combo1. value)

function Resume Click ()


{
if (Calc. Combo 1. value = " ")
rval1 = document. Remotecontrol ComponentOCX1. resumecmdId (ssid,
calc. Combo 1. value)
}

Whenever a job has been executed or canceled, all these are asynchronous calls typically, the
results will came back from the backend some times later and will be delivered to the UI via
an OLE event fired by the RemoteControlComponentOCX, as shown below. The first
example shows an OLE Automation event called when a subscribed AT event channel has a
new value to deliver.

function SendChanEvt Click ()


// send AT event evt to AT channel chan
document. Remotecontrol ComponentOCX1. SindAtEvt Chan
(document. calc. sendChanTxt. value, document. calc. send EvtTxt. value) ;

The Second example shows an OLE Automation event called when command has a new reply
result value to deliver.
function Remotecontrol ComponentOCX1 Return Event (sID )
{
document. Remotecontrol ComponentOCX1.setCurrentCommand Mediator (sID)
document. Remotecontrol ComponentOCX1. return SetKeyValueToFirst (sID)
retb = document. Remotecontrol ComponentOCX1. returnGetNextKeyValue (SID)
key = document. Remotecontrol ComponentOCX1. returndet Current Key (sID)
val = document. Remotecontrol ComponentOCX1. returnCetCurrentValue (SID)
if ( (key == "reply") &&. (val == "Add") )
US 2002/O124054 A1 Sep. 5, 2002
21

retb =
document. Remotecontrol ComponentOCX1. returngetNextKeyValue (SID)
key = document. Remotecontrol ComponentOCX1. returnGetCurrentKey (sID)
Val =
document. Remotecontrol ComponentOCX1. returngetCurrentValue (SID)
if (key == "cooky")
AddOueued Result ("", vall)
}
if (key == "percent")
{
retio =
document. Remotecontrol ComponentOCX1 . . returngetNextkeyValue (SID)
key 1 =
document. Remotecontrol ComponentOCX1. returnGetCurrentKey (SID)
Vali =
document. Remotecontrol ComponentOCX1 . . returnGetCurrentValue (sID)
AddMoreResult (val, val1)
}
if (key == "NewState")
retb =
document. Remotecontrol ComponentOCX1 . returngetNext KeyValue (SID)
key1 =
document. Remote Control ComponentOCX1 . returngetCurrentkey (SID)
Val1 =
document. Remotecontrol ComponentOCX1 . returnGetCurrentValue (sID)
AddMoreResult (val val1)
if (key == "result")
reto -
document. Remote Control ComponentOCX1. returngetNextkeyValue (sID)
key1 =
document. Remotecontrol ComponentOCX1 .returngetcurrentKey (SID)
Wall =
document. Remotecontrol ComponentOCX1 . . returngetCurrentValue (SID)
AddEnd Result (val val1)
}

These events can indicate different reply situations as sent by the backend. The example below
shows an event, the example backend called, to indicate that it queued the request but did not
process it, finally. ...

function AddOueued Result (res, cmdid )


calc. Text3. value = SS
cal C. Combo1. Addltem (Cmdid)
if (calc. Combol. List Count == 1)
{
calc. Combo1. Value = Cmdid
}
US 2002/O124054 A1 Sep. 5, 2002
22

The next function shows a situation where the backend indicates some progress while it is
currently executing a request.....
function AddMoreResult (res , cooky )
{
// not the last reply! More are expected later on!
if (res == "suspended")
{
calc. Text3. value "suspended, press Resume . . . "
calc. Combo 1. value = cooky // select first member in list
return;
}
if (res == "resumed")
{
calc. Text3. value = "Add Cmd resumed."
return;
}
if (res == "delayed")
{
var theResponse
calc. Text3. value = "cmd delayed . . . "
theResponse = "10"
theResponse = window. prompt ("Suml is O ! Please enter a new
value greater O !", the Response) ;
calc. Text 1. value = theResponse
if (calc. Combo1. value = "")
retb = document. Remotecontrol ComponentOCX1. continuecmdId (ssid,
calc. Combo1. Text, theResponse)
return;
if (res == "continued")
{
war result;
calc. Text3. value = "Add cmd continued!"
return;
f / more replies expected, adjust progressbar
Calc. ProgressBari. Value = res
calc. Text3. Value = ""

The last function shows a situation where the backend indicates the end result of a request it
has performed completely... ...
function AddEnd Result (res , cooky)
// rem last one, no more replies expected, adjust progressbar
War x
Calic. Text3. value = res
calc. ProgressBar1. Value = 0
if (calc. Combo.1. List Count > = 1)
for ( x = 1 ; x <= calc. Combo 1. List Count ; x++ )
US 2002/O124054 A1 Sep. 5, 2002
23

if (calc. Combol. List (x - 1) == cooky)


{
callic. Combo1. Remove.Item (x - 1)
if (calc. Combo1. List Count > = 1)
calc. Combol. text = calc. Combo 1. List (O)
else
Calc. Combo. text = ""

The backend could come into idle time situations, where no client has a request running, but
the backend could detects a situation where it needs to inform the clients. For this reason, it
has to send an event via an update channel, which will be received by the
RemoteControlComponentOCX. The RemotecontrolComponentOCX fires an OLE Event
which can be sinked, as shown below...

function Remotecontrol ComponentOCX1 UpdateEvent (sID , sm )


document. Remotecontrol ComponentOCX1. SetCurrentCommand Mediator (sID)
if (sm == "ADD xoff")
{
AddSuspend ()
}
if (sm == "ADD xon")
{
AddResume ()
}
}
The UI could use this information to disable a button in order to react to the Xoff-event from
the backend...
function AddSuspend ()
{
calc. Add. disabled = true
}
... or the UI could use the resume information to re-enable a button to react on the Xon event
from the backend.
function AddResume ()
{
calc. Add. disabled = false
}
When the UI gets shutting down, the RemotecontrolComponentOCX should close all its
running command mediator channels and AT event channels which is been initiated at the
beginning, and finally shutting down the dispatching subsystem, when activated previously as
well, which is shown below.
US 2002/O124054 A1 Sep. 5, 2002
24

function Calc. On Unload ()

War rets
var retb
// shutdown gracefully when things are yet running
for ( X = 0 , x < call C. Combol. List Count : x++ )
// first destroy the local return object
rval1 = document. Remotecontroli ComponentOCX1. Destroy CmdId (ssid,
calc. Combo.1. List (x))
// Second stop the running Commands in BE -> Since return are dead,
no replies will come.
rval1 = document. Remotecontrol ComponentOCX1. cancelCmdId (ssid,
calc. Combo.1. List (x))
rets document. Remotecontrol ComponentOCX1. unloadCommand Mediator (SSid)
reto
document. Remotecontrol ComponentOCX1. exitATEvtChan (document. calc. send
ChanTxt. value);
document. Remote control ComponentOCX1. exitDispatch ()

</SCRIPTs
</body>
</html>
US 2002/0124054 A1 Sep. 5, 2002
25

The sample used for all examples is the Calc Application described in more detail after a short review the
application design.
The example Calc Application used for this purpose should simulate a calculator which uses a frontend and a
backend for adding two numbers and presenting the result. The application allows to demonstrate most critical
parts of an asynchronous communication environment, reaching from non-blocking GUIs over multiple replies to
indicate progress, to flow control events indicating that the backend needs some rest to follow all the requests
queued for the asynchronously running frontends
The sample demonstrates these essential communication aspects:
Asynchronous, non-blocking activation request.
None, one or multiple replies as a result to a single request.
Cancellation of running requests.
Flow control when backend request queue reached a high-water-mark
Fire asynchronous events in to indicate flow control limits.
Suspend a running backend job.
Resume a running backend job.
Continue a delayed backend job.
The figure below shows an example application View GUI component (MacroOCX) and how it accesses its
controller FSM component via the proxy and return objects, which are based on ATOMIC standard internally.
The according model or services component (backend), called calcbe, and command object projects (testcmd
prox/ret and testcmd-cmd) are shown at the end of this paper.
The picture below shows what features the Remotecontrol ComponentOCX addresses in form
of a Design Pattern.
US 2002/O124054A1 Sep. 5, 2002
26

he Calc App
simple asynchron Web Application Example

C++ Enabled Asynchron min Event Propagation Communication Patterri


MEDCOMMOD Charine Name .

joint:53:5.
US 2002/O124054A1 Sep. 5, 2002
27

FFOOOOO1 tacBOOOO3O3S

C++ Enabled Asynchron min Ewent Propagation Communication Pattern


Chanellate

A/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
W/ The interesting part of the MacroOCX cntrl class
US 2002/O124054A1 Sep. 5, 2002
28

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
#include <AT/CapFxtRep.h>
Class CCalcctlfecppDlg;
class CCalcctlfecppCtrl : public CapMacroOCXBase
DECLARE DYNCREATE (CCalcctlfecppCtrl)
// Constructor
public:
CCalcctlfecppCtrl ();
// Overrides
// Class Wizard generated virtual function overrides
//{{AFX VIRTUAL (CCalcctlfecppCtrl)
public:
virtual void OnDraw (CDC* pdic, const CRect & rocBounds,
const CRect & rocInvalid);
virtual void DoPropBExchange (CPropExchange pPX) ;
virtual void OnReset State () ;
// AFX VIRTUAL
// Implementation
protected:
afx msg. BSTR GetName (LPCTSTR tokenld);
~ CCalcctlfecppCtrl () ;

DECLARE OLECREATE EX (CCalcctlfecppCtrl) // Class


factory and guid
DECLARE OLETYPELIB (CCalcctlfecppCtrl) A/
GetTypeInfo
DECLARE PROPPAGEIDS (CCalcctlfecppCtrl) // Property
page IDs
DECLARE OLECTLTYPE (CCalcctlfecppCtrl) // Type name
and misc status

// Message maps
//{{AFX MSG (CCalcctlfecppCtrl)
afx msg. int. OnCreate (IPCREATESTRUCT lpCreateStruct) ;
afx msg. void OnSize (UINT nType, int Cx, int cy);
afx msg. void OnDestroy () ;
afx msg. void OnClose () ;
//}}AFX MSG
US 2002/O124054A1 Sep. 5, 2002
29

DECLARE MESSAGE MAP ()


// Dispatch maps
//{{AFX. DISPATCH (CCalcctlfecppCtrl)
afx msg. void exit Dispatch () ;
afx msg. void initDispatch (LPCTSTR svcfile) ;
//}}AFX. DISPATCH
DECLARE DISPATCH MAP ()
// Event maps
//{{AFX EVENT (CCalcctlfecppCtrl)
//}}AFX EVENT
DECLARE EVENT MAP ()
// Interface maps
public:
// Dispatch and event IDS
enum {
//{{AFX. DISP ID (CCalcctlfecppCtrl)
dispidExitDispatch = 1L,
dispidlnitDispatch = 2L,
//}}AFX. DISP ID
};
private:
CCalcctlfecppDlg *m Calcctlfecpp. microdlig;
public:
long CapGet ClientId (VARIANT FAR* signature) ;
long ModalityEvent (LPCTSTR eventString in);
long ApplicationEvent (LPCTSTR event String in) ;
long SetAdapterObject (long objPtr) ;
long Set StatusBarDispPitr (long FAR* arg1) ;
protected:
long my CompAdapter;
};
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// CalcCtlifecppCtl. Cpp: implementation file
//
CCalcictlfecppCtrl : ; CCalcctlfecppCtrl ()
US 2002/O124054A1 Sep. 5, 2002
30

InitializeIIDs (&IID DCalcctlfecpp.,


&IID DCalcctlfecppEvents);
EnableSimpleFrame () ; // nested controls
//MEDSW ArT : Init Dlg
In CalcCtlifeCpp microdig = NULL;
// TODO : Initialize your control's instance data here.

CCalcctlfecppCtrl : : - CCalcctlfecppCtrl ()
// TODO: Cleanup your control's instance data here.
if (m Calcctlfecpp. microdlig) delete
m Calcctlfecpp. microdlig;
m Calcctlfecpp. microdlg. = NULL;

int CCalcctlfecppCtrl :: Oncreate (TLPCREATESTRUCT lipCreateStruct)


if (CapMacroOCXBase: ; OnCreate (lpCreateStruct) == -1)
return - l;
m menu->LoadMenu (IDR CALCCTLFECPP MENU) ;
//MEDSW ArT : Bring up MicroOCX Dig
In CalcCtlifecpp. microdlig = new CCalcCtlifeCppDlg;
if (m Calcctlfecpp. microdlig)
if (m Calcctlfecpp. microdlig
>Create (IDD DIALOG CALCCTLFECPP, this) )
m Calcctlfecpp. microdlig- >ShowWindow (SW SHOW);
return O;

void CCalcctlfecppCtrl :: OnSize (UINT nType, int cx, int cy)


CapMacroOCXBase : : OnSize (nType, cx, cy) ;
//MEDSW ArT: Resize Dlg
if (m Calcctlfecpp. microdlig)
m Calcctlfecpp. microdlig- >MoveWindow (O , O, Cx, cy);
void CCalcctlfecppCtrl :: OnDestroy ()
CapMacroOCXBase: ; On Destroy () ;
// TODO : Add your message handler code here
if (m Calcctlfecpp. microdlig)
US 2002/O124054A1 Sep. 5, 2002
31

//AfxMessageBox (T("s"));
m CalcCtlifeCpp IniCrOdlg-> Stop () ;
m CalcCtlifeCpp microdlig->Destroy Window () ;
delete m Calcctlfecpp microdlig;
m Calcctlfecpp. microdlig = NULL;
}
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// dispatching subsystem for 3-ro-party executables Only
void CCalcctlfecppCtrl :: exitDispatch ()
{
// TODO: Add your dispatch handler code here
In CalcCtlifecpp. microdilig- >eDisp () ;
void CCalcctlfecppCtrl :: initDispatch (LPCTSTR Svcfile)
// TODO: Add your dispatch handler code here
CString sf = T ("");
sf=svcfile;
m Calcctlfecpp microdlig- >iDisp (Sf);

?/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// The dialog Class
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
class CCalcCtlifecppDl g : public CDialog
{
// Construction
public :
CCalcctlfecppDig (CWind pParent = NULL); // standard
COnStruct Or
~ CCalcct fecppDlg () ;
void stop () ;
void start () ;
void iDisp (CString & finam) ;
void eDisp () ;
// Add cmd. Return event reaction handlers
void AddEnd Result (CString &res, CString &cooky) ;
void Add MoreResult (CString &res, CString & Cooky);
void AddOueued Result (CString &res, CString &cmdid);
// Add cmd. Update event reaction handlers
void AddSuspend ();
Void AddResume () ;
US 2002/O124054A1 Sep. 5, 2002
32

// Add cmd. Update events


CString Add NotifyXoff;
CString AddNotifyxon;

// Dialog Data
//{{AFX DATA (CCalcctlfecppDlg)
enum ( IDD = IDD DIALOG CALCCTLFECPP };
CEdit m chan;
CEdit m esnd;
CEdit mercv;
CComboBox m combol;
CEdit ma;
CEdit mb;
CEdit mo;
CRemotecontrol ComponentOCX m it focx;
//}}AFX DATA

// Overrides
// ClassWizard generated virtual function overrides
//{ (AFX VIRTUAL (CCalcctlfecppDlg)
protected:
virtual void DoDataFXchange (CDataExchange pDX); //
DDX/DDV support
//}}AFX VIRTUAL
// Implementation
protected:
// Generated message map functions
//{{AFX MSG (CCalcctlfecppDlg)
afx msg. void
OnReturn EventRemotecontrol ComponentOCXctrl.1 (LPCTSTR
sID) ;
afx msg. void
OnUpdateEventRemotecontrol ComponentOCXctrl.1 (LPCTSTR
SID, LPCTSTR sMessage) ;
afx msg. void
OnReturn EventDataRemotecontrol ComponentOCXctrl.1 (LPCTSTR
SID, LPCTSTR sMessage) ;
afx msg. void
On ATEvt Chan.Remotecontrol ComponentOCXctrl.1 (LPCTSTR
ChanName, LPCTSTR evt) ;
virtual BOOL OnlinitDialog () ;
afx msg. void OnCancel ();
afx. Insg void. On Add ();
US 2002/O124054A1 Sep. 5, 2002
33

afx msg. void OnDestroy () ;


afx msg. void OnClose () ;
afx msg. void OnCancel 1 ( ) ;
afx msg. void OnSuspend ( ) w
afx msg. void OnResume ();
afx msg. void OnSendEvent () ;
DECLARE EVENTSINK MAP ()
//}}AFX MSG
DECLARE MESSAGE MAP ()
public :
CProgressBar *m WindProgressCtrl;
CButton *m add;
CString SSid;
private:
bool initiated;
};
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// CalcctlfecppDlg. cpp : implementation file
//
include "Stdafx.h"
#include "Calcctifecpp.h."
#include "CalcctlfecppDlg.h"
# include "ed Diac. h."
# include <CsaCommon/CsaString Convert.h>
Hifdef DEBUG
#define new DEBUG NEW
#undef THIS FILE
static char THIS FILE) = FILE ;
fiendlif
/////// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcctlfecppDlg dialog

CCalcctlfecppDlg: ; CCalcctlfecppDlg (CWind pParent /* =NULL* /)


CDialog (CCalcctlfecppDlg: ; IDD, pParent)
{
//{{AFX DATA INIT (CCalcctlfecppDlg)
//}}AFX DATA INIT
AddNotifyxoff= T ("ADD xoff");
Add NotifyXon= T ("ADD xon");
initiated=false;
US 2002/O124054A1 Sep. 5, 2002
34

CCalcCtlifecppDlg: : -CCalcCtlifecppDlg ()
{
}
void CCalcctlfecppDlg::DoDataExchange (CDataExchange pDX)
{
CDialog: : DoDataExchange (pDX) ;
//{{AFX DATA MAP (CCalcctlfecppDlg)
DDX Control (pDX, IDC CHANNEL, m chan) ;
DDX Control (pDX, IDC EVENT SND, mesnd);
DDX Control (pDX, IDC EVENT RCV, mercv);
DDX Control (pDX, IDC COMBO1, m. combo1);
DDX Control (pDX, IDC EA, ma) ;
DDX Control (pDX, IDC EB, mb) ;
DDX Control (pDX, IDC EC, mc) ;
DDX Control (pDX, IDC REMOTECONTROLCOMPONENTOCXCTRL1,
m it focx) ;
// AFX DATA MAP

BEGIN MESSAGE MAP (CCalcctlfecppDlg, CDialog)


//{{AFX MSG MAP (CCalcctlfecppDlg)
ON BN CLICKED (IDC ADD, OnAdd)
ON WM DESTROY ()
ON WM CLOSE ()
ON BN CLICKED (IDC SUSPEND, OnSuspend)
ON BN CLICKED (IDC RESUME, OnResume)
ON BN CLICKED (IDC CANCET, OnCancel)
ON BN CLICKED (IDC SEND EVENT, OnSendEvent)
//}}AFX MSG MAP
END MESSAGE MAP ()
// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcctlfecppDlg message handlers
BEGIN EVENTSINK MAP (CCalcctlfecppDlg, CDialog)
//{{AFX EVENTSINK MAP (CCalcctlfecppDig)
ON EVENT (CCalcctlfecppDlg,
IDC REMOTECONTROLCOMPONENTOCXCTRL1, 1 /* Return Event
* /, OnReturn EventRemotecontrol ComponentOCXctrl 1,
VTS BSTR)
ON EVENT (CCalcctlfecppDig,
IDC REMOTECONTROLCOMPONENTOCXCTRL1, 2 /* UpdateEvent
* /, OnupdateEventRemotecontrol ComponentOCXctrl.1,
VTS BSTR VTS BSTR)
US 2002/O124054A1 Sep. 5, 2002
35

ON EVENT (CCalcctlfecppDlg,
IDC REMOTECONTROLCOMPONENTOCXCTRL1, 3 /*
Return EventData */
OnReturn EventDataRemotecontrol ComponentOCXctrll,
VTS BSTR VTS BSTR)
ON EVENT (CCalcctlfecppDlg,
DC REMOTECONTROLCOMPONENTOCXCTRL1, 4 /* ATEvt Chan */,
OnATEvt Chan.Remotecontrol ComponentOCXctrl 1, VTS BSTR
VTS BSTR)
//}}AFX EVENTSINK MAP
END EVENTSINK MAP ()
//- - - - - - - - - RemoteControl ComponentOCX OLE Events - - - - - - - - - -
Void
CCalcctlfecppDlg: : OnReturn Event Remotecontrol ComponentOC
Xctrl.1 (LPCTSTR sid)

// TODO: Add your control notification handler code


here
// handles all (multiple) replys of Commands
m it focx. setCurrent Command Mediator (Sid);
m it focx. returnSetKeyValueToFirst (sid);
BOOL ret = m it focx. returngetNext KeyValue (sid) ;
CString key;
CString val;
key=m it focx. returnGetCurrentKey (Sid) ;
vall=m it focx. returnGetCurrentValue (sid);
if ( (key == T ("reply")) &&. (val == T ("Add")))
{
ret=m it focx. returnGetNext KeyValue (Sid) ;
key=m it focX. returnCet Current Key (Sid);
vall=m it focX. returnGet CurrentValue (sid);
if (key == T ("Cooky")) // magic cooky as request id
of queued Add commands
{
CString v= T ("");
AddOuelled Result (v, vall) ;
return;

if (key == T ("percent")) // reply with more flag =


true means percent of work done
ret=m it focx. returnGetNextKeyValue (Sid) ;
CString key1=m it focx. returnGetCurrent Key (sid);
A/ cooky"
US 2002/O124054A1 Sep. 5, 2002
36

CString
val1=m it focx. returngetCurrentValue (Sid);
Add MoreResult (val, Val1) ;
return;

if (key == T ("NewState")) // reply with more flag =


true means percent of work done
{
ret=m it focx. returnGetNext KeyValue (sid) ;
CString keyl=m it focx. returngetCurrent Key (Sid);
// "cooky"
CString
vall=m it focx. returnGet CurrentValue (sid);
AddMoreResult (val, val1) ;
return;
}
if (key == T ("result") )
{
ret=m it focx. returngetNextKeyValue (Sid) ;
CString key1=m it focX. returngetCurrent Key (Sid);
// "cooky"
CString
Val1=In it focX. returnGetCurrentValue (Sid) ;
AddEnd Result (val, val1) ;
return;
} // reply with more flag = false means complete Add
done

void
CCalcCtlifecppDlg: : OnupdateEventRetnotecontrol ComponentOC
Xctrl.1 (LPCTSTR sid, LPCTSTR smessage)
// TODO : Add your control notification handler code
here
// handles update events for the command channel (only
receivable for Remote control ComponentOCX)
// here used for flow control events from the business
Components request queue.
In it focX. SetCurrentCommand Mediator (Sid) ;
CString msg=sMessage;
if (msg==AddNotifyXoff) AddSuspend () ;
if (msg==AddNotifyxon) AddResume () ;
US 2002/O124054A1 Sep. 5, 2002
37

void
CCalcctlfecppDlg: : OnReturn EventDataRemotecontrol Compone
intoCXCtrl.1 (LPCTSTR sID, LPCTSTR sMessage)
// TODO : Add your control notification handler code
here
// handles all (multiple) replys of commands and has
all data packed in
// just a single string even if there are multiple
key/vals
// This is for poor environments like java or asp

Void
CCalcCtlifecppDlg: : On ATEvtChan Remotecontrol ComponentOCXc
tril1 (LPCTSTR ChanName, LPCTSTR evt)
// TODO : Add your control notification handler code
here
// handles AT event channel events that has been
created vis the
// Remotecontrol ComponentOCX before.
this->m ercv. SetWindowText (evt) ;

A/- - - -
void CCalcctlfecppDlg: : start ()
//AfxMessageBox ( T ("start"));
ssid = m it focx. loadCommand Mediator ( T ("CKeyValueCM"));
// Create a new event propagation channel for
especially for this Cmd channel
BOOL ret =
m it focx. SetChannelName (ssid, T ("MEDCOM MOD"));
// Set the name tag method of the one and only c/s
PrOXy of this channel
CString rets =
m it focx. callProxy!Method (ssid, T ("SetNameTag"), T ("\\Ke
yValueProxy VVMEDCOM1 \\SOD")) ;
CString chan;
this->m chan. GetWindowText (chan) ;
ret=m it focx. initaTEvt Chan (chan) ;
initiated = true;
US 2002/O124054A1 Sep. 5, 2002
38

void CCalcctlfecppDlg: : stop ()


A / TODO : Add your message handler code here and/or call
default
m it focx. unloadCommandMediator (ssid);
CString chan;
this->m chan. GetWindowText (chan);
BOOL ret=m it focx. exitATEvt Chan (chan) ;
}
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
BOOL CCalcctlfecppDlg: : OnlinitDialog ()
CDialog: : Onlinitialog ();
// TODO: Add extra initialization here
m windProgress Ctrl = (CProgressBar k)
GetDlgItem (IDC PROGCTRL1) ;
m WindProgress Ctrl->SetMin (O);
m WindProgress Ctrl->SetMax (100) ;
m WindProgress Ctrl->SetValue (O) ;
this->m chan. SetWindowText ( T ("MEDCOM MOD"));
this->ma. SetWindowText ( T ('7"));
this->mb. SetWindowText ( T ("8"));
this->UpdateData (FALSE) ;
return TRUE; // return TRUE unless you set the focus
to a Control
A / EXCEPTION: OCX Property Pages should
return. FASE

Void CCalcctlfecppDlg: : OnCancel ()


f / TODO: Add your control notification handler code
here
CString val;
m combol. GetLBText (m Combol. GetCurSel (), vall) ;
if (val = T (" ") )
{
BOOL ret=m it focx. cancel CmdId (ssid, vall) ;
if (! ret)
{ // error, not the right proxy and/or no
Controller
US 2002/0124054 A1 Sep. 5, 2002
39

void CCalcctlfecppDlg:: On Add ()


if (! initiated)
start () ;
return;

this->mc. SetWindowText ( T (" "));


CString key;
CString val;
m it focx.proxyClearKeyValueList (ssid);

key= ( T ("Cmd"));
vall= ( T ("Add"));
m it focx.proxyAdd KeyValue (ssid, key, vall) ;
key= ( T ("sumA"));
this->ma. GetWindowText (val) ;
m it focx.proxyAdd KeyValue (ssid, key, vall) ;

key= ( T ("sumB"));
this->mb. GetWindowText (val) ;
In it focx.proxyAdd KeyValue (ssid, key, vall) ;
CString cmdid= T (" ") ;
CString v = T (" ") ;
cmdid =
m itfocx. executeModeEx{ssid, T ("CALLBACK MODE"));
//AfxMessageBox (cmdid);
if (cmdid== T ("C") || cmdid== T (" ") )
{
// do not add the cmdid here, it is wrong for a
controller
// and the right one will come later via a separate
reply
}
else

// we have a direct business component , not a


controller
// there will be no special reply coming !
US 2002/O124054 A1 Sep. 5, 2002
40

AddOueued Result (v., cmdid);

void CCalcctlfecppDlg: : OnSuspend ()


{
// TODO: Add your control notification handler code
here
CString val;
m combo1. GetLBText (m combo1. GetCurSel () , vall) ;
if (val! = T (" ") )
BOOL ret=m it foCX. SuspendCmdId (ssid, vall) ;
if (! ret)
{ // error, not the right proxy and/or no
controller
}
}

Void CCalcctlfecppDlg: : OnResume ()


// TODO: Add your control notification handler code
here
CString val;
m combol. GetLBText (m combo1. GetCurSel (), vall) ;
if (val! = T (" ") )
BOOL ret=m it focX. resumeCmdId (ssid, vall) ;
if (! ret)
{ // error, not the right proxy and/or no
controller
}
}

void CCalcctlfecppDlg: : OnSend Event ()


{
// TODO : Add your control notification handler code
here
CString chan;
CString evt;
this->m chan. GetWindowText (chan) ;
this->m esnd. GetWindowText (evt);
BOOL ret=tm it focx. SindAtEvtChan (chan, evt) ;
if (ret)
{ // error, not the right channel?
US 2002/O124054 A1 Sep. 5, 2002
41

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Void CCalcCtlifecppDlg: : AddOueued Result (CString &res, CString
&cmdid)
{
this->mc. SetWindowText (res) ;
m combo.1. AddString (cmdid);
if (m combo1. Get Count () == 1)
{
m combo1. Select String (-1, cmdid);
}

void CCalcctlfecppDlg: : AddMoreResult (CString &res, CString


& COOky)
{
if (res== T ("suspended"))
{
this->mc. SetWindowText ( T ("suspended, press
Resume . . . "));
n combol. SetCurSell (0); // select first member in
list
this->UpdateData (FALSE) ;
this->ShowWindow (SW SHOWNA);
return;

if (res== T ("resumed") )
this->mc. SetWindowText ( T ("Add cmd resumed"));
this->UpdateData (FALSE) ;
this->Show.Window (SW SHOWNA);
return;

if (res== T ("delayed"))
m combo 1. SetCurSell (O); // select first member in
list
this->mc. SetWindowText ( T ("delayed . . . "));
this->UpdateData (FALSE) ;
this-> ShowWindow (SW SHOWNA);
//AfxMessageBox ( T ("Add Command asks a question:
stop (yes/no) 2"));
edidiag mydiag;
US 2002/O124054A1 Sep. 5, 2002
42

Imydiag. DOModal () ;
CString result = T ("10") ;
result = mydiag. m res. m txt;
CString val;
this->ma. SetWindowText (result) ;
m combo.1. SetCurSell (O); // select first member in
list
In combO1. GetLBText (m Combo1. GetCurSel (), vall) ;
if (val = T (" ") )
BOOL ret=In it focx. ContinuecmdId (ssid,
val, result) ;
if (! ret)
{ // error, not the right proxy and/or no
controllier
}
return;

if (res== T ("continued") )
this->mc. SetWindowText ( T ("Add cmd continued"));
this->UpdateData (FALSE) ;
this->Show Window (SW SHOWNA) ;
return;
int progress;
chair txt 200;
CSA CSTRING TO ASCII (res, &txt Ol) ;
SScanif (txt, "%d", &progress);
this - >m WindProgress Ctrl = (CProgressBar *) this
>GetDlgItem (IDC PROGCTRL1);
this - >m WindProgress Ctrl->SetValue ( (float) progress);
this >mc. SetWindowText ( T (" "));
this - > UpdateData (FALSE) ;
this - > Show Window (SW SHOWNA) ;

Void CCalcCtlifecppDlg::AddEnd Result (CString &res, CString


& COOKy)
this->mc. Set WindowText (res) ;
this->m WindProgress Ctrl->SetValue (O) ;
int ind;
ind=m combol. Select String (-1, cooky );
if (ind! =CB ERR)
US 2002/O124054A1 Sep. 5, 2002
43

m combol. DeleteString (ind);


m combo.1. SetFoit Sell (O, -1);
m combo1. Clear ();
m combol. ShowDropDown ( TRUE ) ;
m combol. ShowDropDown ( FALSE );
m combol. SetCurSell (O) ; // select first member in list
}
this->UpdateData (FALSE) ;
this-> Show Window (SW SHOWNA) ;

void CCalcctlfecppDlg::AddSuspend ()
this->m add = (CButton *) this->GetDlgItem (IDC ADD) ;
this->m add-> Show Window (SW HIDE) ;

Void CCalcctlfecppDlg: : AddResume ()


this->m add = (CButton *) this->GetDlgItem (IDC ADD) ;
this->m add->Show Window (SW SHOW);

Void CCalcctlfecppDig: ; OnDestroy ()


CDialog: : Onldestroy () ;
// TODO: Add your message handler code here

void CCalcctlfecppDig: ; OnClose ()


// TODO: Add your message handler code here and/or call
default
CDialog: : OnClose () ;

void CCalcctlfecppDlg: : iDisp (CString & finam)


// TODO : Add your message handler code here and/or call
default
mitfoCX. initDispatch (fnam) ;

void CCalcCtlifecppDlg: : eDisp ()


US 2002/O124054A1 Sep. 5, 2002
44

// TODO: Add your message handler Code here and/or call


default
m it focx. exitDispatch () ;

1.6.1.2 View Component with RemotecontrolComponentOCX - Example: frontend part in Visual


Basic running as a OCX on a MacroOCX-HTML-Page within the CapGM GUI container generic
executable

calcbe: MEDSWArT Modality Ewant E vent from Channel Name

// The interesting part of the Visual Basic OCX class


//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Dim SSid AS String
Dim initialized As Boolean
Dim result. As String
US 2002/O124054A1 Sep. 5, 2002
45

Private Sub Command 1 Click ()


Add
Dim key As String
Dim Val As String
If (initialized = False) Then
Start
GoSub ende
End. If
Text3 Text as ""
Remotecontrol ComponentOCX1.proxyClear KeyValueList (SSid)
key = "cmd."
val. = "Add"
Remotecontrol ComponentOCX1.proxyAdd KeyValue ssid, key, val
key = "sumA"
val = Text 1. Text
Remotecontrol ComponentOCX1.proxyAdd KeyValue ssid, key, val
key = "SumB"
Val = Text 2. Text
Remotecontrol ComponentOCX1.proxyAddKeyValue S Sid, key, val
val = Remotecontrol ComponentOCX1. executeModeEx (ssid, "CALLBACK MODE")
If ( (val = "C"). Or (val = " ") ) Then
Else
AddOueued Result "", val
End Tf
ende :
End Sub

Private Sub Command 2 Click ()


Cancel
If (Combo.1. List Count > 0) Then
p1i = p1i - 1
Dim retb As Boolean
retb = Remotecontrol ComponentOCX1. cancel CmdId (ssid, Combo.1. Text)
End if
End Sub

Private Sub Command2 Click ()


send AT event evt to AT channel chan
Dim retb As Boolean
retb = RemotecontrolComponentOCX1. sndAtEvtChan (Text 4.Text, Text5.Text)
End Sub

Private Sub AddSuspend ()


Command 1. Visible False
End Sub

Private Sub AddResume ()


Command 1. Visible = True
End Suo

Private Sub Remotecontrol ComponentOCX1 ATEvtChan (ByVal ChanName As String,


ByVal evt As String)
Text 6 Text = evt
End Sub
US 2002/0 124054 A1 Sep. 5, 2002
46

Private Sub RemotecontrolComponentOCX1 ReturnEvent (ByVal SID As String)


Achtung; hier sind Ausgaben kritisch, anderer Thread und nur am stack
valid
Dim retb As Boolean
Dim key As String
Dim val. As String
Dim key 1. As String
Dim val1 As String
RenoteControl ComponentOCX1. setCurrentCommand Mediator (SID)
Remotecontrol ComponentOCX1. return SetKeyValueToFirst (sID)
retb = Remotecontrol ComponentOCX1. returngetNextKeyValue (sID)
key = Remotecontrol ComponentOCX1. returngetCurrentKey(sID)
val = Remotecontrol ComponentOCX1. return Get CurrentValue (SID)
If ( (key = "reply") And (val = "Add") ) Then
retb = Remotecontrol ComponentOCX1. returnGetNextKeyValue (SID)
key = Remotecontrol ComponentOCX1. returnCetCurrentkey (sID)
Val = Remotecontrol ComponentOCX1. returnGetCurrentValue (sID)
If (key = "cooky") Then
AddOueued Result "", val
End if
If (key = "percent") Then
retb = Remotecontrol ComponentOCX1. returnGetNextKeyValue (SID)
key1 = RemotecontrolComponentOCX1. returngetCurrentKey (sID)
val1 = Remotecontrol ComponentOCX1. returnGetCurrentValue (SID)
Add MoreResult val val1
EInd. If
If (key = "NewState") Then
retb = RemotecontrolComponentOCX1. returnGetNextKeyValue (sID)
key1 = Remote Control ComponentOCX1. returnGetCurrentKey (sID)
val1 = Remote Control ComponentOCX1. returnCetCurrentValue (sID)
AddMoreResult vall, val1
EIC. If
If (key = "result") Then
retb = Remote Control ComponentOCX1. returnGetNextKeyValue (sID)
key1 = RemoteControl ComponentOCX1. returngetCurrentkey (sID)
val1 = Remote Control ComponentOCX1. returnGetCurrentValue (sID)
Add End Result val val1
End. If
End. If
End Sub

Private Sub Remotecontrol ComponentOCX1 UpdateEvent (ByVal sID As String,


ByVal smessage As String)
Remotecontrol ComponentOCX1. SetCurrentCommand Mediator (SID)
If (SMessage "ADD XOff") Then
AddSuspend
End If
If (sMessage = "ADD xon.") Then
AddResume
End If
End Sub

Private Sub AddOueued Result (ByVal res. As String, ByVal cmdid. As String)
TeX t3. Text es
Combol. Addltem (cmdid)
(Combo.1. List Count 1) Then
Combo 1. Text Cmdid
US 2002/O124054A1 Sep. 5, 2002
47

End. If
End Sub

Private Sub AddMoreResult (ByVal res. As String, ByVal cooky As String)


"more replies expected, adjust progressbar or any other evt processing
Dim Message, Title, Default, MyValue
If (res = "suspended") Then
Text3. Text = "suspended, press Resume . . . "
Combol. Text = cooky
GoSub e1
End. If
If (res = "resumed.") Then
TeXt3. Text s "Add Cmd resumed
GoSub e1
End. If
If (res = "delayed.") Then
Text3. Text = "cmd delayed . . . "
Message = "Sum1 is 0 ! Please enter a new value greater O !"
Title = "Sum1 InputBox."
Default = 'O'
result = InputBox (Message, Title, Default)
TeXt1. Text = result
Dim retb As Boolean
If (Combo1. Text ke " ' ) Then
retb = Remotecontrol ComponentOCX1. continuecmdId (ssid,
Combo1. Text, result)
End if
GoSub e1
End. If
If (res = "continued") Then
Text3. Text = "Add Cnd continued "
GoSub e1
End. If
ProgressBarl. Value res
Text3, Text = ''
e1 :
End Sub

Private Sub AddEnd Result (ByVal res. As String, ByVal cooky As String)
'last One, no more replies expected, adjust progressbar
Dim x. As Integer
Text3. Text = res
Progress Bar1. Value = 0
If (Combol. List Count > = 1.) Then
For X = 1 To Combo1. List Count
If (Combol. List (x - 1) = cooky) Then
Combol. Remove Item (x - 1)
If (Combol. List Count > = 1.) Then
Combo.1. Text = Combo.1. List (O)
Else
Combo. Text =
End if
End. If
Next
End. If
End Sub
US 2002/0124054A1 Sep. 5, 2002
48

Public Sub initDispatch (ByVal svcf. As String)


Remotecontrol ComponentOCX1. initDispatch svcf
End Sub

Public Sub exitDispatch ()


Remote control ComponentOCX1. exitDispatch
End Sub

Private Sub Start ()


Dim retb As Boolean
Dim rets As String
ssid = Remotecontrol ComponentOCX1. loadCommand Mediator ("CKeyValueCM")
retb = Remotecontrol ComponentOCX1. setChannelName (ssid, "MEDCOM MOD")
rets = RemotecontrolComponentOCX1. callProxyMethod (ssid, "SetNameTag",
"\KeyValueProxy\MEDCOM1\S")
retb = Remotecontrol ComponentOCX1. initATEvtChan (Text 4.Text)
initialized = True
End Sub

Private Sub Stopp ()


Dim rets As String
Dim retb As Boolean
rets = Remote Control ComponentOCX1. unloadCommand Mediator (ssid)
retb = Remote Control ComponentOCX1. exitATEvtChan (Text 4. Text)
End Sub

Private Sub Resume Click ()


Resune
If (Combo.1. Text (a " ") Then
Dim retb As Boolean
retb = Remotecontrol ComponentOCX1. resumecmdId (ssid, Combol. Text)
End. If

End Sub

Private Sub Suspend Click ()


'Suspend
If (Combol. Text (> " ") Then
Dim retb As Boolean
retb = Remotecontrol ComponentOCX1. suspendCmdid (ssid, Combol. Text)
End. If
End Sub

Private Sub UserControl Initialize ()


Text 4.Text = "MEDCOM MOD"
Progress Bar 1. Min = 0
ProgressBarl. Max = 100
ProgressBar 1. Value = 0
initialized = False
Text 1. Text = 3
Text 2 Text = 7
Text3. Text = " "
End Sub

Private Sub UserControl Terminate ()


Stopp
US 2002/O124054 A1 Sep. 5, 2002
49

End Sub

1.6.1.3 View Component with Remotecontrol ComponentOCX - Example: frontend part on HTML
Page running in CapGM GUI container generic executable

7FOOOOO1 iOacSiOOOO8030 St.

Web-CapGM Enableded Asynchron n:m Event Propagation Communication Pattern


MEDCOMMOD Channnel name

alcbe: MEDSwaT Modality Event

f/ The complete HTML example Web frontend


W/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

<head>
US 2002/0124054 A1 Sep. 5, 2002
50

<title>Calc CalcCapGM-HTMLC/title>
</head>
<body onload="Calc Onload ()" onunload="Calc Onunload ()" background =
"E: \src\calcasp5\calcasp5 Local \images\Syngo. ppt background.jpg">
<!-- //============================================================== -->
<!-- //- - - - - - - - - - Very Thin GUI for the calc application-->
< -- //============================================================== -->
<form method="post" action-" - -WEBBOT-SELF-- " name=" calc" >
<!-- webbot bot="SaveResults" U-File="fpweb :/// private/form results.txt."
S-Format="TEXT / CSV" S-Label-Fields - "TRUE." -->
<HRs
<ps <FONT color= redd <STRONG:-Web-CapGM Enableded Asynchron 1 : 1
Client/Server Communication Patternz /STRONG ></FONT></p>
<p <input name="Text 1" size="9" value="3" >
<input type="button" value="Add" name="Add" onclick="Add Click () "
></p>
<pa <input name="Text 2" size="9" value="2" >
<OBJECT classid=clsid: 35053A22-8589-11D1-B16A- OOCOFO283628 height=15
id=ProgressBarl width=70>
<PARAM NAME=" ExtentX" VALUE="1588 ">
<PARAM NAME="Extent Y." VALUE="397">
<PARAM NAME=" Version" VALUE="393216">
<PARAM NAME="BorderStyle" VALUE="0">
<PARAM NAME="Appearance" VALUE="1">
<PARAM NAME="MousePointer" VALUE="0">
<PARAM NAME="Enabled." VALUE="1">
<PARAM NAME="OLEDropMode" VALUE="O">
<PARAM NAME = "Min" VALUE="O">
(PARAM NAME = 'Max VALUE-100">
<PARAM NAME="Orientation" VALUE="0">
<PARAM NAME="Scrolling" VALUE="0">
</OBJECTs
</p>
<pa <input name="Text3" size="9" >
<input type="button" value="Cancel" name="Cancel."
onclick="Cancel Click () " >
<input type="button" value="Suspend" name="Suspend"
onclick="Suspend Click ()" >
<input type= "button" value="Resume" name="Suspend"
</p> onclick="Resume Click () " >
<pa &nbsp;
<OBJECT classid=clsid: 8BD21D3 O-EC42-11CE-9EOD-OOAAOO 6002 F3 height=24
id= Combol
width=169>
<PARAM NAME="VariousPropertyBits" VALUE="7466 04571">
<PARAM NAME- "BackColor" VALUE="2147483.653">
<PARAM NAME="ForeColor" VALUE="2147483.656">
<PARAM NAME="MaxLength." VALUE="0">
<PARAM NAME="BorderStyle" VALUE="O">
<PARAM NAME="ScrollBars VALUE-O is
<PARAM NAME="DisplayStyle" VALUE="3">
<PARAM NAME="MousePointer" VALUE="0">
<PARAM NAME="Size" VALUE="3413 ; 635">
US 2002/0124054 A1 Sep. 5, 2002
51

<PARAM NAME= "Password Chair" VALUE 'O' >


<PARAM NAME=ListWidth" VALUE= Od
< PARAM NAME="BoundColumn" VALUE=1">
<PARAM NAME=TextColumni VALUE=65535">
< PARAM NAME = Column Count VALUE=1">
< PARAM NAME="List Rows " VALUE="8">
&PARAM NAME = "CColumn Info" VALUE="0">
<PARAM NAME="Match Entry" VALUE="1">
<PARAM NAME="ListStyle" VALUE="0">
< PARAM NAME="ShowDropButton When" VALUE="2">
<PARAM NAME = "ShowListWhen" VALUE="1">
<PARAM NAME="DropButtonStyle" VALUE="1">
<PARAM NAME="MultiSelect" VALUE= i O">
&PARAM. NAME = "Walle VALUE=''
<PARAM NAME="Caption" VALUE=" ">
<PARAM NAME="PicturePosition." VALUE="458753">
<PARAM NAME = "BorderCoor" VALUE="2147483. 654">
<PARAM NAME="Special Effect" VALUE="2">
<PARAM NAME="Accelerator" VALUE="O">
<PARAM NAME="GroupName" VALUE="">
<PARAM NAME= "FontName" VALUE="MS Sans Serif">
(PARAM NAME = ''FontFffects VALUE="107374.1824">
<PARAM NAME="FontHeight" VALUE="165">
<PARAM NAME = "Font Offset" VALUE="0">
&PARAM NAME- "Font ClairSet VALUE= O's
<PARAM NAME="FontPitch AndFamily" VALUE="2">
<PARAM NAME="Paragraph Align" VALUE="1">
<PARAM NAME="FontWeight" VALUE="4 O O">
</OBJECTs

<Ps CFONT color=redd <STRONG >Web-CapGM Enableded Asynchron&nbsp;n: m


Event Propagation Communication Pattern.</STRONG ></FONT></P>
<P><INPUT name=send ChanTxt size = "24" readOnly> Channnel name</P>
<P><INPUT type=button size="100" onclick="SendChan Evt Click () " value="Send
Event with Channel Name" name=Send Evt ></P>
<P> <INPUT name=send EvtTxt size= "24"> Event send to Channel name</P>
<P> <INPUT name=rcvd EvitTxt size="56"> Event from Channel name</P>
CHRs

</forma

k --//============================================================== -->
<!-- //- - - - - - - - - - Remotecontrol ComponentOCX Ole Event Handler declaration --
>

<! - -//============================================================== -->

<OBJECT classid=c sid: B7AFED6F-E886-1D2 - A3E6 - OOO4AC963AO1


id=Remotecontrol ComponentOCX1s <PARAM NAME=" Version"
VALUE="65536"><PARAM NAME="ExtentX" VALUE="2646"><PARAM
NAME=" Extent Y " VALUE="1323"><PARAM NAME=" StockProps" VALUE="O">
</OBJECTs
US 2002/0124054 A1 Sep. 5, 2002
52

<script LANGUAGE="JAVASCRIPT" FOR="RemotecontrolcomponentOCXl"


EVENT="Return Event (ID)">
return Event (ID)
-->
</scriptid
<script
LANGUAGE = "JAVASCRTPT" FOR="Remotecontrol ComponentOCX1."
EVENT="UpdateEvent (ID, supdateParam) ">
updateEvent (ID, supdate Param)
-->
</scripts
<script
LANGUAGE="JAVASCRIPT" FOR="Remotecontrol ComponentOCX1"
EVENT="ATEvt Chan (chan, evt) ">
<! --
ATEvt Chan (chan evt)
-->
</scripts

<SCRIPT LANGUAGE="JavaScript">
//=====================================================================
//- - - - - - - - - - GUI Adapter to Web Business Logic via Scripting Language
//=====================================================================
var sSid
var key
var val
var key1
war wall
var retb
Val X

//=====================================================================
A/- - - - - - - - - - GUI Adapter for single command activation
A/=====================================================================
function Add Click ()
{
f/rem. Add
//window. alert ( navigator. appName );
calc. Text3 - value = ""
document. Remotecontrol ComponentOCX1.proxyClearKeyValueList (ssid)
key = "cmd."
val. s "Add."
document. Remote Control ComponentOCX1.proxyAdd KeyValue (ssid, key, vali)
key = "sumA"
val = calc. Text 1. value
document. Remote Control ComponentOCXl.proxyAddKeyValue (ssid, key, val)
key = "sumB"
vali = catc. Text2 . . value
document. Remotecontrol ComponentOCX1.proxyAdd KeyValue (ssid, key, val)
f / document. Remotecontrol ComponentOCX1. execute (ssid)
val = document. Remotecontrol ComponentOCX1. executeModeFX
(ssid, "CALLBACK MODE")
if (val - "C")
US 2002/O124054A1 Sep. 5, 2002
53

Addiqueued Result ("", val)

function Cancel Click ()


{
//rem Cancel
if (calc. Combol. List Count > 0)
rval1 = document. Remotecontrol ComponentOCX1. cancelCmdId (ssid,
calc. Combo1. value)

function Suspend Click ()


//rem Cancel
if (calc. Combol. value = "")

rval1 = document. Remotecontrol ComponentOCX1. suspendCmdid (ssid,


calc. Combo1. value)

function Resume Click ()


//rem Cancel
if (calc. Combol. value ! = "")

rval1 = document. RemoteControl ComponentOCX1. resumecmdId (ssid,


calc. Combo1. value)

//=====================================================================
//- - - - - - - - - - GUI Adapter for event propagation
A/=====================================================================
function SendChanEvt Click ()
// send AT event evt to AT channel chan
document. Remotecontrol ComponentOCX1. SindAtEvt Chan
(document. calc. sendChanTxt. value, document. call C. send EvtTXt. value) ;
}
//=====================================================================
//- - - - - - - - - - Remotecontrol ComponentOCX Ole Event handlers
//=====================================================================
function return Event (ID)
{
Remotecontrol ComponentOCX1 ReturnEvent ( ID )
}
function updateEvent (ID, Sparam)
US 2002/O124054 A1 Sep. 5, 2002
54

Remotecontrol ComponentOCX1 UpdateEvent (ID, sparam)

function ATEvtChan (chan , evt)


{
Remotecontrol ComponentOCX1 ATEvtChan (chan, evt)
}

function Remotecontrol ComponentOCX1 ATEvtChan (chan , evt)


{
document. Calc. rocvd EvitTxt. Value = evt
}
function Remotecontrol ComponentOCX1 Return Event (sID )
//window. alert ( "return")
// rem Achtung: hier sind Ausgaben kritisch, anderer Thread und nur am
stack valid
document. Remote Control ComponentOCX1. setCurrentCommand Mediator (sID)
document. Remotecontrol ComponentOCX1. returnsetKeyValueToFirst (SID)
retb = document. Remotecontrol ComponentOCX1. returngetNextKeyValue (SID)
key = document. Remotecontrol ComponentOCX1. returngetCurrent Key (SID)
val = document. Remotecontrol ComponentOCX1. returngetCurrentValue (SID)
if ( (key == "reply") && (val == "Add") )
{
retb =
document. Remotecontrol ComponentOCX1. returngetNextkeyValue (sID)
key = document. Remotecontrol ComponentOCX1. returnCetCurrentKey(sID)
Val =
document. Remotecontrol ComponentOCX1. returnCetCurrentValue (SLD)
if (key == "cooky")
{
AddOueuedResult ("", val)
}
if (key == "percent")
{
retb =
document. Remotecontrol ComponentOCX1. returngetNextKeyValue (SID)
key1 =
document. Remote control ComponentOCX1. returnGetCurrentkey (SID)
val1 =
document. Remotecontrol ComponentOCX1. returngetCurrentValue (SID)
Add MoreResult (val, val1)
}
if (key == "NewState")
{
retb =
document. Remotecontrol ComponentOCX1. returngetNextKeyValue (sID)
key1 =
document. Remotecontrol ComponentOCX1. returngetCurrentKey (sID)
Val1 =
document. Remotecontrol ComponentOCX1. returnCetCurrentValue (sID)
Add MoreResult (val, vall)
if (key == "result")
US 2002/O124054A1 Sep. 5, 2002
55

retb =
document. Remotecontrol ComponentOCX1. returnGetNextKeyValue (SID)
key1 =
document. Remotecontrol ComponentOCX1. returngetCurrentKey (sID)
Val1 =
document. Remotecontrol ComponentOCX1. returngetCurrentValue (sID)
AddEnd Result (val, vall)

function Remotecontrol ComponentOCX1 UpdateEvent (sID , sm )


document. Remotecontrol ComponentOCX1. setCurrentCommand Mediator (sID)
if (sm == "ADD Xoff")
AddSuspend ()
if (sm == "ADD xon")
{
AddResume ()
}

//=====================================================================
// - - - - - - - - - - GUI Adapter for single command callbacks
// =====================================================================
function AddOueued Result (res, cmdid )
calc. Text3. Value = res
calc. Combol. Additem (Cmdid)
if (calc. Combo 1. List Count == 1)
{
calc. Combol. value = cmdid
}
}
function AddMoreResult (res , cooky )
{
if (res == "suspended")
{
calc. Text3. value = "suspended, press Resume . . . "
calc. Combol. value = cooky // select first member in list
return;
}
if (res == "resumed")
{
calc. Text3. value = "Add cmd resumed."
return;
}
if (res == "delayed")
var theResponse
calc. Text3. value = "cmd delayed . . . "
theResponse = "10"
US 2002/O124054A1 Sep. 5, 2002
56

theResponse = window. prompt ("Sum1 is O ! Please enter a new


value greater O !", theResponse) ;
callic. Text 1. value = the Response
if (calc. Combo1. value = " ")
retb = document. Remote Control ComponentOCX1. continueCmdld (ssid,
Calc. Combol. Text, theResponse)
return;

if (res == "continued")
var result;
calc. Text3. value = "Add cnd continued!"
return;

// more replies expected, adjust progressbar


calc. ProgressBarl. Value = res
CaC, Text3. Value = ""

function AddEnd Result (res , cooky)


// rem last One, no more replies expected, adjust progressbar
War X
Calc. Text3. value = res
calc. ProgressBarl. Value = 0
if (calc. Combo1. List Count > = 1)
for ( x = 1 ; x <= calc. Combol. List Count ; x++ )
if (calc. Combol. List (x - 1) == cooky)
{
Calc. Combo1. Remove Item (x - 1)
if (calc. Combo. List Count > = 1)
Calc. Combol. text = calc. Combol. List (O)
else
calc. Combo. text = ''

function. AddSuspend ()
calc. Add. disabled = true
}
function. AddResume ()
{
calc. Add. disabled = false
}

//=====================================================================
f/- - - - - - - - - - Init / Exit Handlers
US 2002/O124054A1 Sep. 5, 2002
57

function Calc Onload ()


{
var retb
War retics
War
calc. ProgressBarl. Min = 0
calc. ProgressBarl. Max = 100
calc. ProgressBar1. Value = 0
document. calc. sendchanTxt. value = "MEDCOM MOD";
//document. Remotecontrol ComponentOCX1. initDispatch ("")
ssid =
document. Remotecontrol ComponentOCX1. loadCommand Mediator ("CKeyValueCM
it)
retb = document. Remotecontrol ComponentOCX1. set ChannelName (ssid,
"MEDCOM MOD")
rets = document. Remotecontrol ComponentOCX1. callProxyMethod (ssid,
"SetNameTag", "WWKeyValueProxy\\MEDCOM1\\S")
reto =
document. Remotecontrol ComponentOCX1. initATEvt Chan (document. calc. send
ChanTxt. Value);
calc. Text 1. value = "4"
Calc. Text2 . . value it 9 it
Calc. Text3. value = ""

function Calc. On Unload ()

war rets
var retb
rets = document. Remotecontrol ComponentOCX1. unloadCommand Mediator (ssid)
retb =
document. Remotecontrol ComponentOCX1. exitATEvtChan (document. calc. Send
ChanTxt. value) ;
f/document. Remotecontrol ComponentOCX1. exitDispatch ()

</SCRIPTs
</body>
</html>

1.6.2 Controller (FSM) Component with RemotecontrolComponentBackend


The backend part is plugable typically in form of a syngo backend component (CsaGenericComponent derived
class) which allows dynamic loading using the concepts of AT. Another possibility is to connect the backend part
of the RemotecontrolComponentOCX into a non-visual MacroOCX. Note, all frontend parts written in different
languages shown above (only the C++ one was really shown, of course) are able to run with one of the backends
shown here, without additional programming, just via configuration, even within the same executable. That
means, in all these mixed languages for frontend and backend, there is no process boundary needed in between
when not explicitely wished. If it is wished to have this boundary, it can be reached just via reconfiguration.
The frontends we have seen so far, are all allowed to connect to the following controller
component without any modifications.
US 2002/0124054 A1 Sep. 5, 2002
58

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// The Controller MacroOCX Ctrl class
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the MacroOCX header file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// CalcctCtl.h:
// Declaration of the CCalcict Ctrl ActiveX Control class.

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / //
// CCalcctCtrl : See CalcctCtl.cpp for implementation.
# include "stdafx. h."
#include <AT/CapExtRep.h>
// ACE Guard
#include <ace/Synch.h>
//cmd
#include <At/CapAtCmdObjBase.h>
Class p1;
class r1;
class con1;
A / ifock
class mycon;
class CKeyValueReturn;
// running object map of upper layer and lower layer proxy/ret requests
class roe : public CObject
public:
CString cmdidu;
CapAtCmdIdType idu;
CKeyValueReturn *ru;
// Operations

// typedef CMap<CString, CString, roe, roe&> CroeMap ;


class CCalcctCtrl : public CapMacroCCXBase
DECLARE DYNCREATE (CCalcctctrl)
// Constructor
public:
CCalcct Ctrl () ;
// controller functions
BSTR AddExecCB (CString &s1, CString & s2, CKeyValueReturn ret) ;
void AddCancel (CString & cooky, CKeyValueReturn ret) ;
void AddSuspend (CString & cocky, CKeyValueReturn * ret) ;
US 2002/O124054A1 Sep. 5, 2002
59

void AddResume (CString & Cooky, CKeyValueReturn *ret) ;


void AddContinue (CString &cooky, CString &r, CKeyValueReturn ret) ;
void Add AppEvents (LPCTSTR evt) ;
void Add Mod Events (LPCTSTR evt) ;
bool. Addlnit ();
bool AddExit () ;
A / Overrides
// Class Wizard generated virtual function overrides
//{{AFX VIRTUAL (CCalcctctrl)
public:
virtual void OnDraw (CDC* pdc, const CRect& rcBounds, Const CRect &
rcInvalid);
virtual void DoPropBxchange (CPropExchangek pPX) ;
virtual void OnResetState () ;
//}}AFX VIRTUAL
// Implementation
protected:
afx msg. BSTR GetName (LPCTSTR tokenId);
-CCalcict Ctrl () ;

DECLARE OLECREATE EX (CCalcctCtrl) // Class factory and guid


DECLARE OLETYPELIB (CCalcctctrl) // GetType Info
DECLARE PROPPAGEIDS (CCalcctCtrl) // Property page IDs
DECLARE OLECTLTYPE (CCalcctctrl) // Type name and misc status
// Message maps
//{{AFX MSG (CCalcctCtrl)
f / NOTE - Class Wizard will add and remove member functions
here.
DO NOT EDTT what you see in these blocks of generated
code
afx msg. int. Oncreate (LPCREATESTRUCT lpCreateStruct) ;
afx msg. void OnSize (UINT nType, int CX, int Cy);
//}}AFX MSG
DECLARE MESSAGE MAP ()
// Dispatch maps
//{{AFX. DISPATCH (CCalcictctrl)
// NOTE - Class Wizard will add and remove member functions
here.
// DO NOT EDIT what you see in these blocks of generated
code
//}}AFX. DISPATCH
DECLARE DISPATCH MAP ()
// Event maps
//{{AFX EVENT (CCalcctCtrl)
// NOTE - ClassWizard will add and remove member functions
here.
A/ DO NOT EDIT what you see in these blocks of generated
code
f / AFX EVENT
US 2002/O124054A1 Sep. 5, 2002
60

DECLARE EVENT MAP ()


// Interface maps
public:
f / Dispatch and event IDs
enum
//{{AFX. DISP ID (CCalcctCtrl)
// NOTE: Class Wizard will add and remove enumeration elements
here.
A/ DO NOT EDIT what you see in these blocks of generated
code
//}}AFX. DISP ID
private :
f / cmd
p1 *mpl;
r1 kmr1;
con1 *mcon1;
bool exited;
public:
// lock for pxy->execute + rom->add (cmdid) method (cmd-proc-thread),
f / against conil->take method (mfc-main-thread)
ACE. Thread Mutex Lock;
public:
f / interface OCX
mycon kmc;
f / running object map
enum (MAX ROE = 20);
CMap String Toob rom;
public :
long CapGetClient Id (VARIANT FAR* signature) ;
long ModalityEvent (LPCTSTR eventString in);
long ApplicationEvent (LPCTSTR event String in);
long SetAdapterObject (long objPtr) ;
long SetStatus BarDispPitr (long FAR* arg1);
BOOT Shutdown Request (BOOL RequestType);
long Shutdown (long tif, const VARIANT FAR& f) ;
protected:
long my Compadapter;

//{{AFX INSERT LOCATION }}


// Microsoft Developer Studio will insert additional declarations
immediately before the previous line.
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the MacroCCX implementation file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// Calcct Ct). Cpp:
// Implementation of the CCalcctCtrl ActiveX Control class.
include "stdafx.h"
US 2002/O124054 A1 Sep. 5, 2002
61

Hinclude "calcct. h."


#include "CalcctPpg. h."
#include "CalcctCtl.h"
include <AFXPRIV. His
#include "capstatusbar. h."
#include <CsaCommon/CsaString Convert. h>
?/ ifock
#include "mycon.h"
//cmd achtung, die 2 zeilen muessen vor dem unteren debug new sachen
stehen
#include "Testcmd prox. h."
#include "Testcmd ret.h"
iinclude <CsaCommon/CsaString Convert.h>
Class Con1;
#ifdef DEBUG
#define new DEBUG NEW
#undef THIS FILE
static char THIS FILEI) = FILE ;
tendilf

IMPLEMENT DYNCREATE (CCalcctCtrl, CapMacroOCXBase)


// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Message map
BEGIN MESSAGE MAP (CCalcctCtrl, CapMacroOCXBase)
//{{AFX MSG MAP (CCalcctCtrl)
f / NOTE - Class Wizard will add and remove message map entries
A/ DO NOT EDIT what you see in these blocks of generated code
ON WM CREATE ()
ON_WM SIZE ()
//}}AFX MSG MAP
ON OLEVERB (AFX IDS VERB PROPERTIES, OnProperties)
//#define AT MESSAGEMAP DEFINES
ON COMMAND RANGE ( IDM ADD FIRST ENTRY, IDMADD LAST ENTRY,
On DynMenuItems )
ON UPDATE COMMAND UI RANGE (IDM ADD FIRST ENTRY, IDM ADD LAST ENTRY,
On JpdateLayout)
END MESSAGE MAP ()

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Dispatch map
BEGIN DISPATCH MAP (CCalcctCtrl, CapMacrooCXBase)
//{{AFX. DISPATCH MAP (CCalcctCtrl)
// NOTE - Class Wizard will add and remove dispatch map entries
?/ DO NOT EDIT what you see in these blocks of generated code !
DISP STOCKPROP FONT ()
US 2002/O124054A1 Sep. 5, 2002
62

//}}AFX. DISPATCH MAP


END DISPATCH MAP ()

///////// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Event map
BEGIN EVENT MAP (CCalcct Ctrl, CapMacroOCXBase)
//{{AFX EVENT MAP (CCalcctCtrl)
f / NOTE - Class Wizard will add and remove event map entries
// DO NOT EDIT what you see in these blocks of generated code
//}}AFX EVENT MAP
END EVENT MAP ()

/ / / / / / / / / / // // / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / // / / // / / / / / // / / / // / / /
A / Property pages
// TODO: Add more property pages as needed. Remember to increase the
COunt
BEGIN PROPPAGEIDS (CCalcctCtrl, 1)
PROPPAGEID (CCalcctPropPage : : guid)
END PROPPAGETDS (CCalcictotrl)

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
A / Initialize class factory and guid
IMPLEMENT OLECREATE EX (CCalcctctrl, "CALCCT. CalcctCtrl.1",
0x318b7 da7, Ox8213, Ox46cb, 0x83, Ox74, Oxc5, Ox64, Ox60, Oxal,
Oxla, OX4b)

W// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Type library ID and version
IMPLEMENT OLETYPELIB (CCalcctotrl, tiid, wVerMajor, wVerMinor)

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Interface IDs
Const IID BASED CODE IID DCalcct =
{ OX318b7 da5 OX8213, Ox46cb, { OX83, OX74, OXC5, 0x64 0x60
Oxall, OX1a, Ox4b } };
COISt TD BASED CODE IID DCaCC tEvents
{ 0x318b7da6, Ox8213, Ox46cb, { 0x83, Ox74, Oxc5, Ox64, Ox60,
Oxal, Ox1a, OX4b } };
A / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /A A/ / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// Control type information
Static Const DWORD BASED CODE dwCalcctoleMisc =
OLEMISC SIMPLEFRAME A / for nested controls
OLEMISC ACTIVATEWHENVISIBLE
OLEMISC SETCLIENTSITEFIRST
OLEMISC INSIDEOUT
US 2002/O124054 A1 Sep. 5, 2002
63

OLEMISC CANTLINKINSIDE
OLEMISC RECOMPOSEONRESIZE;
IMPLEMENT OLECTLTYPE (CCalcctotrl, IDS CALCCT, dwCalcctOleMisc)

f / / // / // ///// / / / ///// / / / / /// / / / / / /// / / / / / /// / / / / //// / / / / / / // / / / //// / // /


// CCalcctCtrl : ; CCalcctCtrlFactory: : UpdateRegistry -
// Adds or removes system registry entries for CCalcct Ctrl
BOOL CCalcctCtrl: : CCalcictCtrl Factory : : UpdateRegistry (BOOL, bRegister)
// TODO: Verify that your control follows apartment-model threading
rules.
A / Refer to MFC TechNote 64 for more information.
// If your control does not conform to the apartment-model rules,
then
// you must modify the code below, changing the 6th parameter from
// afxRegApartment Threading to 0.
if (bRegister)
return AfxOleRegisterControl Class (
AfxGet InstanceHandle () ,
m clsid,
m lps zProgID,
IDS CALCCT,
IDB CALCCT,
afxRegInsertable afxRegApartmentThreading,
dwCalcctOleMisc,
tlid,
wVerMajor,
wVerMinor) ;
else
return AfxOleUnregisterClass (m Clsid, m lipsz ProgID) ;

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcct Ctrl : : CCalcct Ctrl - Constructor
CCalcctCtrl : ; CCalcct Ctrl ()

InitializeIIDs (&IID DCalcct, &IID DCalcctEvents) ;


// TODO: Initialize your control's instance data here.

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
A / CCalcctCtrl: : -CCalcctCtrl - Destructor
CCalcct Ctrl : : - CCalcct Ctrl ()

// TODO: Cleanup your controls instance data here.


if (! exited)
AddExit () ;
US 2002/0124054 A1 Sep. 5, 2002
64

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcctCtrl: ; On Draw - Drawing function
void C.Cacct Ctrl : : On Draw (
CDC's polic, const CRect& rcBounds, const CRect& rclinvalid)
A / TODO : Replace the following code with your own drawing code.
//pdc->FillRect (rcBounds,
CBrush: : FromHandle ( (HBRUSH) GetStockObject (WHITE BRUSH)));
//pdc->Ellipse (rc Bounds) ;

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcct Ctrl. : : DoPropBxchange - Persistence support
void CCalcctCtrl :: DoPropBxchange (CPropExchangek pPX)
ExchangeVersion (pPX, MAKELONG ( wVerMinor, wVerMajor));
CapMacroOCXBase : :DoPropBxchange (ppX) ;
// TODO: Call PX functions for each persistent custom property.

// / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / / /
// CCalcct Ctrl : ; OnResetState - Reset control to default state
void CCalcct Ctrl :: OnResetState ()
CapMacroOCXBase: ; OnResetState (); // Resets defaults found in
DoPropBxchange
f / TODO : Reset any other control state here.

// CCalcctCtrl message handlers


int CCalcctCtrl :: OnCreate (LPCREATESTRUCT lpCreateStruct)
if (CapMacrooCXBase: : Oncreate (lpCreateStruct) == -1)
return -1;
//m menu->LoadMenu (IDR CALCCT MENU) ;
//AfxMessageBox (T ("oncreate"));
return 0;

void CCalcctCtrl :: OnSize (UINT nType, int cx, int cy)


CapMacrooCXBase: : OnSize (nType, cx, cy) ;
//MEDSW ArT : Resize Dlg

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// please override this method
BSTR CCacct Ctrl. : : GetName (LPCTSTR token Id)
US 2002/O124054A1 Sep. 5, 2002
65

CString strResult ( T ("Calcct"));


return strResult. AllocSys String () ;

long CCalcict Ctrl : ; CapGetClientId (VARIANT FAR* signature)


// MEDSW ART: SPECIFY YOU CLTENT ID (IDS CALCCT CLIENTID) IN THE
STRING TABLE RESOURCE
signature->vt = VT BSTR;
CString clientlD(T("") ); clientID. LoadString (IDS CALCCT CLIENTID);
signature ->bstrVal = client ID. Alloc SysString () ;
return 0;

long CCalcctCtrl: : SetStatusBarDispPitr (long FAR* arg1)


/* END Method k /
CapMacroOCXBase: ; SetStatusBarDispPitr (arg1); // call the base class
method

//MEDSW ART: CapStatusBar:


LPDISPATCH aDisp = 0;
aDisp = (LPDISPATCH) arg1;
DCapStatus Bar pdisp;
pdisp. AttachDispatch (aDisp, TRUE) ;
pdisp. SetStatus Pos (2) ;
pdisp. Detach Dispatch () ;
return 0;

BOOL CCalcctCtrl :: Shutdown Request (BOOL RequestType)


{
return true; // shutdown granted
}
//- - - - - - - - - - - - - - - - - - - - relevant start - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

long CCalcctCtrl : ; Shutdown (long tif, const VARIANT FAR& f)


Add Exit () ;
return 0;

long CCalcct Ctrl : ; SetAdapterObject (long objPtr)


//MEDSW ART: ADD CODE TO HANDLE THE COMPONENTADAPTERPTR
CapMacroCCXBase: : SetAdapterObject (objPtri) ;
my Compadapter = objPtr;
?/MEDSW ART: EXAMPLE CODE FOLLOWS
bool ret= this->Addlnit () ;
return 0;

long CCalcctCtrl: : ModalityEvent (LPCTSTR eventString in)


US 2002/0124054 A1 Sep. 5, 2002
66

//MEDSW ART: ADD CODE TO HANDLE THE INCOMMING APPLICATION-EVENTS


Add Mod Events (eventString in);
return 0;

long CCalcct Ctrl : : ApplicationEvent (LPCTSTR eventString in)


{
//MEDSW ART: ADD CODE TO HANDLE THE INCOMMING APPLICATION-EVENTS
AddAppEvents (eventString in);
return O;

//- - - - - - - - - - - - - - upper half / Dialog Interface - - - - - - - - - - - - - - - - - - - - - - - -

//cmd mediator zwischen dialog und reply delivery


class Con1 : public CAbstrCons
{
public:
con1 (CCalcctctrl* c) my ctl = c ; );
void take (CapAtCmdReturnBase: );
private :
CCalcctCtrl *my ctl;
// hier evtl. das return object eines Interface OCX consumers
aufbewahren
// und verwenden zurn reply schicken, wenn die take methode hier
gerufen wird.

A/cmd -> reply trifft ein -> MFC MAin Thread


void con1: : take (CapAtCmdReturn Base r)
{
A / set mific module state
AFX MANAGE STATE (AfxGetStaticModulestate ( ));
// lock between main thread and workingbox thread
ACE Guard<ACE. Thread Mutex> aMon (my ctl->Lock);
r1* ret = (r1*) r,
Capat Cmdrd Type cmdid=ret- >getCmdId (); // Identisch mit der Cmdla,
die das
//
Proxy p1 hatte Welches diese
//
r1 Return Object Instance in Seinem
p1->execute (r1) angab. //
// restore from running object map
roe re;
CString sid;
bool erg=my ctl->mc->cmdid2Cstr (cmdid, sid);
BOOL found=ny ctl->rom. Lookup (sid, (CObject * &) re) ;
if (! found)
//AfxMessageBox (T ("error in rom lookup !"));
US 2002/O124054 A1 Sep. 5, 2002
67

return;
}
// client return ptr vor cmdid setzen
CString retid= T ("");
retid. Format ( T("%08x &s"), (long) re->ru->getData (), re->Cmdidu) ;
if ( (ret->getMoreFlag ()) ==false)
{ // last reply
int result = ret->getC () ;
CString str result (T (""));
str result. Format (T ("%d"), result);
//my ctl->mc->AddEnd Result (str result, re->ru, re->Cmdidu);
my ctl->mc->Add End Result (str result, re->ru, retid);
re->ru-> destroy () ; A / destroy the return checked out via
keep retval
BOOL rt=myctl->rom. RemoveKey (Sid); // remove key from map
delete re; // delete running object map entry
else
{ // more replies expected, adjust progressbar
CString str ( T (" "));
//my ctl->mc->Add MoreResult (str, ret->getC () , re->ru, re->Cmdidu) ;
my ctl->mc->AddMoreResult (str, ret->getC (), re->ru, retid);
ret -> autoDestroy () ;

//- - - - - - - - - - - - - - - - - - - - - - lower half - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -


bool CCalcct Ctrl. : : AddInit ()

// first create lower half objects (proxies to BE commands)


mpl=p1: : create () ; // create lower half proxy (once per
component).
mconl=new con1 (this); // create abstract consumer fro lower half
replies
// next create upper half objects (interfaceco)
Inc = new mycon (this) ;
exited = false;
return true;

bool CCalcct Ctrl. : : AddExit ()

// first delete upper half objects (interfaceCO)


mp1->destroy (); // delete lower half proxy (once per component).
delete mcon1; // delete abstract consumer fro lower half replies
// next delete lower half objects (proxies to BE commands)
delete mc ; // ifocx
exited = true;
return true;

A / Will be called by ifocx: : take method


BSTR CCalcict Ctrl : : AddExecCB (CString &s1, CString &S2, CKeyValueReturn * ret)
// set mfc module state
US 2002/O124054 A1 Sep. 5, 2002
68

AFX MANAGE STATE (AfxGetStaticModulestate ( ) };


// lock between main thread and workingbox thread
ACE Guard<ACE. Thread Mutex> aMon (Lock);
// translate String values from GUI into typed data values
int sum1 = wtoi (LPCTSTR (s1});
int sum2 = wtoi (LPCTSTR (s2));
// set attributes in proxy with typed values
mp1->setA (sum1); // lower half proxy business data
mp1 -> setB (sum2); // lower half proxy business data
A/ create a transfer specific return object & set the consumer
mediator object ptr into that return object
mr1=r1: : create (); // create return instance before the lower half
execute
mr1->my AbstractConsumer = mcon1; // set abstract consumer for reply
// transfer the proxy & return instances to the command object
server asynchron
// proxy cmdid wird intern nun an das return object uebertragen!
mp1 -> execute ( mr1); // execute lower half command in callback mode
// get cmd request id from proxy (same has the return later on as
well
Capat CmdIdType id= mp1->get Cmdid (); // get the unique request
sequence cmdid
CString s (T (""));
bool r=this->mc->cmdid2Cstr (id, s); // cmdid-obj to string conversion
// Store into running object map
roe *re = new roe () ;
re->cmdidu-s; // CString
re->idu-id; // CapAtCmdIdType
re->ru=ret; // CapAtCmdReturn Base
rom. SetAt (s , re); // store in running object map
// client return ptr vor cmdid setzen
CString retid= T ("");
retid. Format (T ("% 08X %s"), (long) ret->getData (), s) ;
// this->mc->Addiqueued Result (s , ret, s) ; reply
Remote Control ComponentOCX with request id
this->mc->AddQueued Result (retid, ret, retid); // reply
Remotecontrol ComponentOCX with request id
return s. AllocSysString () ;

?/ will be called implicitely by the preTake method


void CCalcctCtrl : : AddCancel (CString &s, CKeyValueReturn * ret)
CapAt CmdIdType id;
// string to object conversion
bool r=this->mc->Cstr2cmdid (s , id);
// the proxy is reused, but the sequence id changes per execute
mp1-> cancel (&id) ;

A/ will be called implicitely by the preTake method


void CCalcctCtrl. : : AddSuspend (CString &s, CKeyValueReturn ret)
US 2002/O124054A1 Sep. 5, 2002
69

CapatCmdIdType id;
f / string to object conversion
bool r=this->mc->Cstr2CIndid (s , id) ;
// the proxy is reused, but the sequence id changes per execute
mp1->pause (true, &id);

// will be called implicitely by the preTake method


void CCalcctCtrl : : AddResume (CString &s, CKeyValueReturn * ret)
CapAtCmdIdType id;
// String to object conversion
bool r=this->mc->Cstr2 cmdid s, id);
// the proxy is reused, but the sequence id changes per execute
mp1->pause (false, &id) ;

f / Will be called implicitely by the preTake method


void CCalcictCtrl : ; AddContinue (CString &S, CString &r, CKeyValueReturn ret)
{
CapAtCmdid Type id;
// String to object conversion
bool retwisthis->mc->Cstr2cmdid (s, id) ;
// the proxy is reused, but the sequence id changes per execute
f / feed in the result r which was given by client into this proxyl
A/
// the entire proxy will be sent, incl. all data structures
mpl.->setResult (r) ;
mp1-> resume (&id);

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void CCalcictCtrl: : Add AppEvents (LPCTSTR evt)
{
//AfxMessageBox (evt) ;
if (tcsicmp (evt, T ("xoff") ) == 0)
{
// disable add button
tac->AddSuspend () ;
}
if (tcsicmp (evt, T ("xon")) == 0)
{
// enable add button
mc->AddResume () ;
}
void CCalcictCtrl : : Add Mod Events (LPCTSTR evt)
{

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the KeyValueCOConsumer (Remotecontrol ComponentOCX-BE) header file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
#ifndef mycon H
US 2002/O124054A1 Sep. 5, 2002
70

#define mycon H
A/#include <at/Csa GenericComponent.h>

#include <wb/CsaWorking BoxDefines.h>


#include "Cac/KeyValueCO. h."
#include "Cac/KeyValueProxy.h"
#include "Cac/KeyValueReturn.h"
include "Cac/CMNotifier. h."
#include "Cac/KeyValueCOConsumer. h."
class CCalcctCtrl;
class CsaWorkingBox Factory; // wb
class mycon : public KeyValueCOConsumer
public :
mycon () ;
mycon (CCalcctCtrl k cp) ;
virtual -mycon () ;
bool start (); // init code
bool stop (); // exit code
void setCompType (const CString& msg);
CString getCompType () ;
virtual BOOL take (CKeyValueCO co, CKeyValueProxy proxy,
CKeyValueReturn's ret) ;
sendCOEvent (const CString & msg);
void cancel (CString & mid, CKeyValueReturn ret) ;
void suspend (CString & mid, CKeyValueReturn ret) ;
void resume (CString & mid, CKeyValueReturn ret) ;
void continueFEx (CString & mid CString & r, CKeyValueReturn ret) ;
void AddOueued Result (CString &res, CKeyValueReturn *ret, CString
idl) ;
void AddEnd Result (CString &res, CKeyValueReturn *r, CString idl) ;
void Add MoreResult (CString &res, int progress, CKeyValue Return *r,
CString idl) ;
void AddSuspend ();
void AddResume () ;
// helper routines for cmdid to string conversion,
// can be replaced via new API on CapAtCmdid Type if available from
Lutz in VA51
bool CIndid2Cstr (Cap.AtCmdIdType &id, CString & sid) ;
bool CStr2 cmdid (CString &Sid CapAtCmdid Type &id);
CCalcctCtrl *my ctrl;
private :
CKeyValueCO' my KeyValueCO; // cmd
CString compType;
CsaWorkingBoxFactory myWBF; // wb
CsaWorkingBoxIdType wbid1; // wb
US 2002/O124054 A1 Sep. 5, 2002
71

// the KeyValueCOConsumer (Remotecontrol ComponentOCX-BE) implementation


file ...
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
//#define ACE BUILD SVC DLL
# include <CsaCommon/CsaString Convert.h>
#include "mycon. h."
include "CalcctCti. h"
Hinclude <wb\CsaWorking BoxFactory.h> // wb
mycon : : mycon ()
{
}
mycon : : mycon (CCalcct Ctrl *cp)
my ctrl=Cp;
int r= start () ;

mycon : : -mycon ()
int r= Stop () ;
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
bool mycon : : start ()
{
myWBF = CsaWorkingBoxFactory : : instance (); // wb
myWBF-> create (wbid1); // wb
myKeyValueCO = CKeyValueCO: : create ( (const char
*) O, true, CapAtCmdNoWBoxId, (void k) 0, "\\ KeyValueProxy\\MEDCOM1 \\S") ;
// cmd.1 cmd
myKeyValueCO->setWBox TD (wbid1); // wb
myKeyValueCO->initialize (this, "MEDCOM MOD"); // med
this-> setKeyValueCO (my KeyValueCO); // med
// inform ACOX that I am working as a controller component not as a
business component
this->setCompType ( T ("SSSBEcontrollerBESSS"));
this->sendCOEvent (this->getCompType () ) ;
return true;

bool mycon : : stop ()


{
// 1) stop accepting new commands going into Command Processor
myKeyValueCO-> terminate () ;//cmd
// 2) stop and destroy the working box
myWBF->destroy (wbid1); // wb
// 3) wait until the working box thread has really shut down
myWBF->synch (&wbid1, 1); // wb
// 4) now it is safe to destroy the command object since none is
running anymore
myKeyValueCO->destroy () ; f/cmd
US 2002/O124054 A1 Sep. 5, 2002
72

return true;
}
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void mycon : : setCompType (const CString & msg)
compType=msg;

CString mycon : : getCompType ()


return compType;
}
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
//-> Command Processor Thread or Working Box Thread
BOOL mycon : : take (CKeyValueCO * co, CKeyValueProxy kproxy, CKeyValue Return
* ret)
{
AFX MANAGE STATE (AfrxGetStaticModulestate ( ));
// has to be called!
BOOL r=this->preTake (co, proxy, ret, this->getCompType () ); // check for
internal key/val
proxy->setKeyValueToFirst () ;
CString cmdkey;
CString cmdval;
proxy->getNextkeyValue (cmdkey, Cmdval);
if ( (cmdkey== T ("cmd")) && (cmdvall== T ("Add")))
{
CString sum1key;
CString sumival;
proxy->getNextkeyValue (sumilkey, sum1 vall) ;
CString sum2key;
CString sum2val;
proxy->getNextKeyValue (sum2key, sum2val) ;
// store client site return ptr
ret->setData (proxy->getData ());
CString cooky=my ctrl->AddExecCB (sum1val, sum2val, ret) ;
ret->setKeep Up () ;
return (TRUE) ;
}
return (TRUE) ;
}
f /- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
mycon : : sendCOEvent (const CString & msg)
Cout << "IntfoCX be: ; Laycon: : sendcoEvent" << endl;
this->my KeyValueCO->sendCMEvent (msg);
US 2002/O124054A1 Sep. 5, 2002
73

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void mycon : : cancel (CString & mid, CKeyValueReturnk ret)
my ctrl->AddCancel (mid, ret) ;

void mycon: ; suspend (CString & mid, CKeyValueReturnk ret)


my Ctrl->AddSuspend (mid, ret) ;

void mycon : : continueEx (CString & mid, CString& r, CKeyValueReturnik ret)


my Ctrl->AddContinue (mid, r, ret) ;

void mycon : : resume (CString & mid, CKeyValueReturne ret)


my ctrl->AddResume (mid, ret) ;

f /- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

void my con: : AddOueued Result (CString &res, CKeyValueReturn kret, CString


idl)

// give the first reply back to client and hand out a sequence id
idl
ret-> clearKeyValueList ();
ret->setKeyValueToFirst () ;
ret->add KeyValue ("reply", "Add") ;
ret->add KeyValue ("cooky", idl) ;
ret->reply (true);

Void myCon. : : AddMoreResult (CString &res, int progress, CKeyValueReturn


*ret, CString idl)
{
// give the second till n-th. reply back to client and hand out
// performed percentage and sequence id idl
ret-> clearKeyValueList () ;
ret->setKeyValueTo First () ;
ret ->addKeyValue ("reply", "Add") ;
chair txt 20) ;
switch (progress)
case -1; // suspended
sprintf(txt, ("%s"), "suspended") ;
CString percent (txt);
ret ->add KeyValue ("NewState", percent);
break;
US 2002/0124054 A1 Sep. 5, 2002
74

case -2 : // resumed
{
sprintif (txt, ("%s"), "resumed") ;
CString percent (txt);
ret->add KeyValue ("NewState", percent);
}
break;
case -3 : // delayed suspend ()
sprintf(txt, ("%s"), "delayed") ;
CString percent (txt) ;
ret->addKeyValue ("NewState", percent) ;
break;
case - 4: // continued = resume () on client called !
sprintf(txt, ("%s"), "continued");
CString percent (txt);
ret->add KeyValue ("NewState", percent);
break;
default: // running in percent of completion
sprintf(txt, ("%d"), progress);
CString percent (txt) ;
ret->add KeyValue ("percent", percent);
break;
ret->add KeyValue ("cooky", idl) ; // cmdid cooky of the lower level
Cmd!
ret->reply (true);

void mycon : : AddEnd Result (CString &res, CKeyValueReturn kret, CString idl)
ret-> clearKeyValueList () ;
ret->setKeyValueToFirst () ;
ret->addKeyValue ("reply", "Add") ;
ret->add KeyValue ("result", res);
ret->add KeyValue ("cooky", idl) ; // cmdid cooky of the lower level
cmd.
ret->reply (false) ;

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void mycon : : AddSuspend ()
{
this->sendCOEvent ("ADD xoff") ;
}
void mycon : : AddResume ()
{
this-> SendCOEvent ("ADD xon") ;
}
US 2002/O124054A1 Sep. 5, 2002
75

// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
bool mycon: ; cmdid2Cstir (CapAt CmdIdType &id, CString & sid)
{
// CapAtCmdIdType id= mp1->getCmdId ();
unsigned long inet=id.getInlet () ;
unsigned short liport=id. getLPort () ;
unsigned long uid=id. gettjid () ;
char buf 256 :
sprintf (buf, "% 08Xi8O4xià O8x", inet, liport, ulid);
sid=buf;
return true;

bool mycon: : Cstr2Cmdid (CString &Sid CapAtCmdIdType &id)


char buff (2OO) ;
CSA CSTRING TO ASCII (sid, &buff EO));
unsigned long inet;
unsigned short liport;
unsigned long ulid;
A/ SScanif (buff, "% 08Xiti: 04xi & O8x", &inet, &lport, &uid);
char *p; // adajust buffer because possible return ptr at beginning
if (buff (8) =='') p=&buff (9); else p=&buff (Ol;
ss canf (p, "% 08xit 04xii; O 8x", &inet, &lport, &uid) ;
id. set Inet (inet) ;
id. SetLPort (liport) ;
id. SetUid (uid) ;
//id (inet, liport, uid) ;
return true;

1.6.3 Model (service) Component with business logic implementation (where the real calculation
takes place)

The model (business logic) component is now the lowest layer of the application model. It is
implemented as a backend component derived from CsaGenericComponent Standard (see
more in the software IC standard about this) as shown below:
f /- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
A / the calcbe GenericComponent header file ...
A/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
#ifndef calcbe H
#define calcbe H
# include & at WCsaGenericComponent.h>

it include <wb/Csa WorkingBoxDefines.h>


US 2002/O124054A1 Sep. 5, 2002
76

ACE SVC FACTORY DECLARE (calcbe)


class C1; //cmds
Class Csa WorkingBoxFactory; // wb
class ACESVc Export calcbe : public CsaGeneric Component
public:
calcbe () ;
- Cachoe () ;

int info (char**, size t = 0) const;


int suspend (void) ;
int resume (void) ;
int swic (void) ;
int open (void thePtr) ;
int close (unsigned long);
protected:
int do service (ACE Message Block *) ;
bool process Args (int key, char * arg) ;
int get Concurrency Level (void) ;
void handleApplicationEvent (char *); // incoming application
event
void handleModality Event (char *) ; // incoming modality event
bool handleShutdown Request (bool p, A / incoming shutdown request
LPTSTR kaddText) ;
CsaWorkingBoxFactory k myWBF; // wb
CsaWorkingboxIdType wbid1; // wb

private :
//MEDSW ArT: Add private Member hear
c1 cmycmd.1; //cmds
};
iendlif
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the calcbe GenericComponent implementation file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
#define ACE BUILDSVC DLL
it include cacbe. h "

#include "Testcmd. cmd.h" //cmd


#include <wb\CsaWorkingBoxFactory.h> // wb

calcbe : : calcbe ()
: CsaGeneric Component (this)
{
US 2002/O124054A1 Sep. 5, 2002
77

//MEDSW ArT : Init private Member here


mycmd1 =0; ?/cmd
wbidla0; // wb

Calcbe : : - calcbe ()
{
?/MEDSW ArT : Add source code here
}

int calcbe : : info (char * , size t ) const


{
Cout << " (" << ACE OS: : thr self () << ") calcbe: : info ()" << endl;
return 0;

int calcbe: ; suspend (void)


{
cout << " (" << ACE OS: : thr self () << ") calcbe : : suspend ()" << endl;
CsaGenericComponent: : suspend () ;
return 0;
}
int calcbe : : resume (void)
{
cout << " (" << ACE OS: ; thir self () << ") calcbe: ; resume () " << endl;
CsaGenericComponent: : resume () ;
return 0;
}
int calcbe : : open (void * the Ptr)
{
//MEDSW ArT : Add code here
cout << " (" << ACE OS: ; thir self () << ") calcbe; : open()" << endl;
myWBF = CsaWorkingBoxFactory: : instance (); // wb
myWBF-> create (wbid1) ; f / wb
mycmd1 = c 1: ; create (); //cmd
mycmd1 -> setUserData ( (void *) this); // cmd. + events
mycmd1->setWBoxID (wbid1); // wb
return 0;
}
int calcbe : : svc ()
{
while (1)
{
cout << " (" << ACE OS: : thr self () << ") calcbe: ; svc () " << endl;
this->do service (O);
if (isTermination RequestPending () )
Cout << "calcbe: ; SVC () detected cancellation: ';
US 2002/O124054A1 Sep. 5, 2002
78

Cout << "aborting !" << endl;


return 0;
}
}
return 0;

int calcbe: : close (unsigned long val)


A/MEDSW ArT : Add source code here
cout << " (" << ACE OS: : thr self () << ") calcbe: ; close ()" << endl;
f / 1) stop accepting new commands going into Command Processor
mycmd1->terminate () ; A f cmd
// 2) stop and destroy the working box
myWBF->destroy (wbidi) ; // wo
// 3) wait until the working box thread has really shut down
myWBF->synch (&wbidl, 1); // wb
f / 4) now it is safe to destroy the command object since none is
running anymore
mycmd1->destroy () ; A/cmd
return 0;

bool calcbe: ; process Args (int key, char * val)


Cout << " (" << ACE OS: ; thr self () << ") calcbe: ; process Args () " << endl;
Switch (key)
//MEDSW ArT: Define your cases here
default:
cout << "calcbe : No match found for : " << (char) key << endl;
return false;

int calcbe : : getConcurrency Level ()


//MEDSW ArT : Please return you concurrency level here
cout << " (" << ACE OS: : thr self () << ")
calcbe: : getConcurrency Level () " << endl;
return 1 ;

int calcbe: : do service (ACE Message Block *mb)


W/MEDSW ArT : Add source code here
cout << "calcbe: ; do service () " << endl;
if ( notifyApplication ("calcbe : : MEDSW ArT Application. Event ! : " ))
Cout << "Calcbe : : Error sending Application. Event " << endi;
if (! notify Modality ("calcbe: : MEDSW ArT Modality Event ") )
cout << "calche : : Error sending Modality Event " << endl;
ACE OS: : sleep (5) ;
US 2002/O124054A1 Sep. 5, 2002
79

return O;

void calcbe: ; handleApplicationEvent (char * theEvent)


//MEDSW ArT : Add source code here
Cout << "calcbe: ; handleApplicationEvent: <" << theEvent << ">" <<
end;

void calcbe: ; handleModalityEvent (char * the Event)


A/MEDSW ArT : Add source code here
cout << "calcbe: ; handleModalityEvent: <" << the Event << ">" << endl;

bool calcbe: ; handleshutdown Request (bool p, LPTSTR addText)


//MEDSW ArT : Add source code here
cout << "calcbe: ;handle Shutdown Request: "<< endl;
return TRUE;

ACE SVC FACTORY DEFINE (calcbe)

1.64 Appendix: ATOMIC based Command Proxy/Return connecting Controller to Model (service)
The controller component is using a command proxy/return interface (based on ATOMIC
standard) to a model command object implementation. Tis proxy/return dll is linked to both,
the controller component (as the client) and the model component (business logic) command
object dll (the server).
A/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the business proxy/return object header file ...
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// Testcmd prox. h.
#ifndef CAP ATCMD PROX Testcmd H
idefine CAP AT CMD PROX Testcmd H
#include <At / CapatCmdProxRetBase.h>
#include <CsaCommon/Csalefs.h>
#ifdef BUILD CapAtProxTestcmd.
#define EXP IMP CapAtProxTestcmd CSA EXPORT
fielse
#define EXP IMP CapAtProxTest cmd CSA IMPORT
iendlif

//pl BEGLN
class EXP IMP CapAtProxTestcmd p1 : public CapAtCmdProxyBase
US 2002/O124054A1 Sep. 5, 2002
80

{
DECLARE PROXY (p1)
public:
void setResult (CString & foo);
void setA (int foo= 0) ;
void setB (int foo=O);
CString getResult (void) ;
int getA (void) ;
int getB (void);
?/MEDSW ArT:
protected;
//MEDSW ArT: For all members you have corresponding Get / Set
methodes
void copyHook (const pi& class in ) ;
private :
int pvall;
int pval2;
CString res;
//MEDSW ArT: Define your data here
};
//p1 END

// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the business proxy/return object implementation file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
//Testcmd prox. Cpp
# include <iostream.h>
#include <At/CapAtMacDef.h>
#include "Testcmd prox. h"

f/p1 BEGIN
IMPLEMENT PROXY ( p1, G ( p val1 ) G pval2 ) C ( res) PROXY EXT )
void p1: : copyHook (const p1& C in)
CSA TRACE IN ( (CAP AT, "p1: ; copyHook"));
// the cpy hook members
pval1 = c in pval1;
pVal2 = c in .pval2;
res= c in res;
?/MEDSW ArT : Add your code here

CString pl; : getResult (void)


return res;

void pl; : setResult (CString & foo)


res=foo;
US 2002/O124054 A1 Sep. 5, 2002
81

void p1 : : setA (int foo)


{
pval1 = foo;
}
void p1: ; setB (int foo)
{
pval2=foo;
}
int p1 : : getA (void)
return pval1;
}
int p1: : getB (void)
{
return pval2;
}
//p1 END

1.6.5 Appendix: ATOMIC based Command Object implementation Model (service)

The business logic component is finally using a command object which implements the
requested Add command which was initiated by the RemoteControl ComponentOCX running
within the corresponding UI component.

A/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
W/ the business command object header file ...
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
A/Testcmd cmd.h
#ifndef CAP ATCMD CMD Testcmd H
#define CAP ATCMD CMD Testcmd H
#include <At/CapAtCmdObjBase.h>
#include <CsaCommon/CsaDefs.h>
#ifdef BUILD CapAtCmdCmdTestcmd
#define EXP IMP CapAtCmdCmdTestcmd. CSA EXPORT
else
#define EXPIMP CapAtCmdCmdTestcmd. CSA IMPORT
end if
class p1; // ProxyClass
class r1; //ReturnClass
US 2002/O124054 A1 Sep. 5, 2002
82

// C1 BEGIN
class EXP IMP CapAtCmdCmdTestcmd c1: public CapAtCmdObjBase
DECLARE CMD (c1)
// CMD EXECUTESYNC ( p1, r1 )
public:
bool execute ( p1* , r1* ) ;
bool executeSync (pl. , ril );
};
// c1 END
fiendlif

//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// the business command object implementation file ...
A/- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
//Testcmd. Cmd. Cpp
#include <CsaCommon/CsaStringConvert.h>
#include "Testcmd. Cmd.h"
#include ". . /ProxRet/Testcmd prox.h"
#include ". . /ProxRet/Testcmd ret. h"
#include <At/CapAtMacDef.h>
// events
#include <At/CsaGenericComponent.h>
// c1 BEGIN
//MEDSW ArT: Hooks for starting and destroying CmdObjects from a
Genericcomponent
extern "C" int startupc1 (void*)
?/MEDSW ArT: Initialize your Command Objects here
return 0;

extern "C" int shutdownc1 (void*)


//MEDSW ArT : Destroy your Command Objects here
return 0;
// c1 END
//cll BEGIN
class CsaGeneric Component;
IMPLEMENT CMD (c1, p1, r1)
bool cl: : execute (p1* acmdProxyPtr, r1* acmd RetPtr)
CSA TRACE IN ( (CAP AT, "c1: : execute"));
?/MEDSW ArT : Define your code here
// business logic is here
US 2002/O124054A1 Sep. 5, 2002
83

p1 * anotherPxy;
p1 *aPxy = NULL;
Static bool suspended=false;
int i ;
bool canceled= false;
bool delayed= false;
// évents
CsaGenericComponent * compptr= (CsaGenericComponent *) this
>getUserData ();
unsigned int timeout;
timeout = 10000;
int sum1;
int Sum2;
sum1 =acmdProxyPtr->getA () ;
sum2=aCmdProxyPtr->getB();
// simulate that BE has to ask the client user something and
// wait for answer!
if ( (Sum1 == 0) )
{
cout << "cmd delayed! !" << endl;
delayed=true;
//Add MoreResult (str result, -3, ret, s); // inform client:
delayed
aCmdRetPtr->setC (-3);
aCmdRetPtr-> reply (true);
bool r;
while (1)
{ r= this
> suspend (timeout, (CapAtCmdProxyBase **) &anotherPxy) ; // blocks here !
if (r)
{
// get the proxy data here and delete the proxy
later on
cout << "cmd continued !" << endl;
CString result;
result=anotherPxy->getResult () ;
char wbuff (20 O} :
CSA CSTRING TO ASCII (result, &vbuff (Ol);
Cout << " vall=" << vbuff C & endl;
sum1 = wtoi (LPCTSTR (result));
anotherPxy->destroy () ;
delayed=false;
//AddMoreResult (str result, - 4, ret, s) ; // inform
client: suspended
aCmdRetPtr->setC (-4);
aCmdRetPtr-> reply (true);
break; // resume normal operation
// timed out, so keep in loop
US 2002/O124054A1 Sep. 5, 2002
84

for (i =l; i <10; i++)


{
// check if we should suspend
if (this->is Pause (true, (CapAtCmdProxyBase**) &aPxy))
{
cout << "cmd suspended : " << endl;
suspended //Add MoreResult (str result, -1, ret, s) ; // inform client:
aCmdRetPtr-> set C (-1);
aCmdRetPtr-> reply (true);
bool r;
while (1)
{
r= this -
>is Pause (false, (CapatCmdProxyBase**) &aPxy, timeout); // blocks here !
if (r)
cout << "cmd resumed ! !" << endl;
//Add MoreResult (str result, -2, ret, s); //
inform client : suspended
a CmdRetPtr->setC (-1);
aCmdRetPtr-> reply (true);
break; // resume normal operation
// timed out, so keep in loop
}
// check if we should cancel
if (this->is Terminated () )
cout << "cmd cancelled! !" << endl;
cancelled=true;
break;
; : Sleep (1000) ;
aCmd RetPtr->set C (ik 10) ;
aCmdRetPtr->reply (true);

int Sum;
if (! canceled)
{
Slum = Sum1 + Slum2; A / the wole business logic ; -)
}
else sum= 0;
aCmdRetPtr->setC (sum);
if ( (this->getNumOf PendingRequest () > 5) && ! suspended)
{ compptr->notifyApplication ("xoff"); // évents
Suspended=true;
else

if ( (this->getNumOf Pending Request () <= 5) && suspended)


US 2002/0124054 A1 Sep. 5, 2002
85

compptr->notifyApplication ("xon"); // évents


suspended=false;

aCmdRetPtr-> reply (false);


cout << "c1 : : execute" << " reuslt = " << sum Cz endl;
return true;

bool cl: : executeSync (p1* acmdProxyPtr, r1* acmdReturnPtr )


CSA TRACE IN ( (CAP AT, "c1: : executeSync"));
return true;
//c1 END
US 2002/O124054A1 Sep. 5, 2002
86

We claim: 7. A medical System architecture according to claim 5,


1. A medical System architecture, comprising: wherein the remote control component is a connectable/
a modality for acquiring images, remote interface component.
8. A medical System architecture according to claim 6,
a means for processing the images, Said means for pro wherein the remote control component is a connectable/
cessing includes a digital image System with a com remote interface component.
puter that works according to a Standard for object
linking and embedding method for data eXchange 9. A medical System architecture according to claim 1,
between various application programs with graphical wherein Said means for transmitting uses for data eXchange
control elements and a Standard for object linking and the Standard for object linking and embedding.
embedding custom controls, wherein a Standard for 10. A medical System architecture according to claim 1,
object linking and embedding custom controls Software wherein a Standard for Said Standard for object linking and
component is allocated to every individual proceSS embedding Custom Controls is the component Standard
limited by address Space boundaries, Microsoft OCX.
means for expanding the Standard for object linking and 11. A medical System architecture according to claim 1,
embedding custom controls Software components with further comprising:
a remote control component for asynchronous commu
nication So that devices and processes can be remote means for use of Software component technology for
controlled without any limitations caused by address producing components for graphic user interfaces con
Space or computer boundaries, and tained within a process.
a means for the transmission of the images, 12. A medical System architecture according to claim 1,
2. A medical System architecture according to claim 1, further comprising:
wherein Said remote control component is an OLE Automa means for combining Software component technology
tion interface.
3. A medical System architecture according to claim 2, with Standard for object linking and embedding Auto
wherein the remote control ensues according to an OLE mation for distributed propagation of an event within a
Automation Standard. control level and between the control levels.
4. A medical System architecture according to claim 1, 13. A medical System architecture according to claim 1,
wherein the remote control component is an Automation further comprising:
Interface component. means for combining Software component technology
5. A medical System architecture according to claim 1,
wherein the remote control ensues with Software-IC con with software-IC connections for the distributed propa
nections. gation of an event within a control level and between
6. A medical System architecture according to claim 1, the control levels.
wherein the remote control ensues according to the
ATOMIC standard.

You might also like