OpenDoc Development Framework
The OpenDoc Development Framework, or ODF, is an object-oriented framework developed in C++ which is targeted for building cross-platform OpenDoc component editors. Like MacApp, Apple's framework for building standalone Macintosh applications, ODF makes the process of building an OpenDoc component editor easier by implementing much of a component editor's default behavior.
OpenDoc will be delivered on a variety of platforms and provides a good
foundation for building cross-platform component editors. On top of OpenDoc,
ODF provides a set of cross-platform services to ease the development of
OpenDoc component editors. One of the services needed to write a truly
cross-platform component editor is a cross-platform graphics engine. Other
services include menu support and cross platform resources. The OpenDoc
Development Framework builds on the technology provided by OpenDoc and
cross-platform technology developed at Apple to provide a complete
cross-platform solution. ODF will allow a developer to develop component
editors once and have them work on multiple platforms.
- Support for object standards: ODF is designed to fully support
OpenDoc, and thanks to the OLE inter-operability capabilities offered by
OpenDoc, developers get OLE support with minimum effort.
- Cross-platform development: ODF will allow the development of component
editors for both Macintosh and Windows. Apple is working to ensure that the
most prominent development environments and compilers for both platforms
- Modular: ODF reduces the inter-dependencies between modules in the
framework by introducing a subsystems and layers architecture. This design
approach makes it possible for developers to use only the parts of the
framework that are needed, which will result in component editors with greater
performance and reduced code-size.
- Full source code availability: developers will have access to the full source code.
ODF uses the underlying API to implement the look and
feel of each platform. Anything that is built with ODF looks native on the
target platform. At the same time, if ODF does not provide support for a
specific service available in the platform, developers can bypass it and write
directly to the platform-specific API.
By using ODF, developers will be able to do faster, multiplatform software development leveraging their development resources; they will lower development, maintenance, and revision costs by providing product updates and integrating new OS functionality more easily; in addition, they will be able to develop custom business solutions. Today, commercial developers, system integrators, VARs, consultants, and in-house corporate developers face the challenge of creating software solutions across incompatible computers, software versions, and networks. ODF will be an important piece to help deliver those solutions.
Since ODF provides implementation for most of the component editor's default behavior, developing OpenDoc components with ODF will ensure that different components interoperate, and that each component gets the correct behavior expected in an OpenDoc environment.
One of the traditional problems
developers have experienced with frameworks is the large number of
inter-dependencies between the framework modules. It has been very difficult
for a developer to use a particular piece of the framework without requiring
the rest of it. ODF eliminates the inter-dependencies between modules in the
framework by introducing a subsystems and layers architecture.
Figure 1 Layers and subsystems
Figure 1 is a representation of how different subsystems and layers in ODF
are organized. A subsystem in ODF is collection of classes, utility functions,
and definitions that work together to provide a service in the framework.
Examples of subsystems in ODF are the collections subsystem, strings subsystem,
cross-platform graphics subsystem, and an embedding part subsystem. Subsystems are
then grouped together in distinct layers which are ordered according to the
complexity of the services provided by its subsystems.
To break the inter-dependencies in the framework, a subsystem is allowed to
have one-way dependencies to other subsystems. For example the strings
subsystem in the Foundation layer has a dependency on the streams and
exceptions subsystems, but not vice versa.
Figure 2 Layers and Subsystems - String Dependencies
Subsystems may also have dependencies on subsystems in layers below their layer, but no subsystem can have a dependency on a subsystem in a layer above it. In ODF, the graphics subsystem uses the facilities of the exceptions and streams subsystems creating a dependency between the OS layer and Foundation layer, but no subsystem in the Foundation layer can rely on services of the OS layer. (Figure 2)
Eliminating the inter-dependencies between subsystems allows the services of
ODF to be used for additional types of programs besides OpenDoc component
Figure 3 Layers and Subsystems - Graphics Dependencies
Services Provided By ODF
The services provided by ODF
are described by the subsystems and layers in which they reside.
The Foundation layers subsystems are largely platform-independent
and provide a useful set of services to a wide variety of programs. There are
twelve subsystems in the Foundation layer.
- Common Subsystem - A collection of generic type definitions and functions, that is, definitions and functions that are needed by many of the other ODF subsystems.
- Task Globals Subsystem - Provides an interface to per-task global data for
shared-code libraries (under operating systems that do not provide any
mechanism for per-task global data). ODF uses this interface for all global
data, including those operating systems that provide per-task global data, in
order to simplify writing code that uses global data.
- Debug Subsystem - Contains tools that are useful during the testing and
debugging of ODF component editors.
- Runtime Type Identification Subsystem - Provides mechanisms for runtime
type identification and runtime-checked type casts. RTTI is an accepted ANSI
C++ language extension. However, at the time of this writing few compilers
support this extension. The RTTI subsystem provides a set of macros that
simulate RTTI mechanisms.
- Utilities Subsystem - A collection of miscellaneous utilities which
don't logically belong in the other ODF subsystems.
- Exceptions Subsystem - Defines the protocol ODF uses to throw, catch,
and define exceptions. It provides a set of classes and macros that emulate
native C++ style exception handling.
- Collections Subsystem - A simple collection class implemented as a linked
list, plus an iterator class to go with it. Borrowed from OpenDoc.
- Streams Subsystem - Provides input/output services. These facilities are
provided by the ODF streams, sinks, and stream formatters classes. The ODF
Streams subsystem provides services which are separate and distinct from those
provided by an implementation of the IOStreams class library but is compatible
with the C++ IOStreams library.
- Archivers Subsystem - Saves and restores dynamic and static objects in
their current states. ODF subsystems use the Archivers subsystem to archive
objects of classes they define. For example, the Strings subsystem provides
archiving for the concrete string classes defined by ODF.
- Strings Subsystem - Classes in the strings subsystem create and delete
strings objects, and write, read, modify, translate, and delete strings and
text within those objects. Strings may be composed of ASCII or user-defined
character sets. It is designed to provide a simplified interface to strings
operations, to provide a consistent programming interface to all ODF
- Memory subsystem - Provides platform-independent interfaces for pointer-
and handle-based allocation/deallocation requests, as well as interfaces for
manipulating blocks of allocated memory. It also provides global C++ new and
delete operators and a strategy for handling failed memory requests.
- Notification subsystem - Provides classes for doing notification.
The OS layer's subsystems provide a
platform-independent interface to common system services such as memory management and graphics. These subsystems are dependent on the underlying operating system as well as the existence of OpenDoc. The implication of this dependency is that unlike the subsystems in the Foundation layer, which are largely platform-independent and can be used in many different types of environments, subsystems in the OS layer cannot be used in a non-OpenDoc environment.
- Files subsystem - Creates, opens, closes, renames and deletes files;
sets file permissions; and reads and writes to files. Virtual methods within
some classes allow you to extend the files concept to files that do not reside
on disk media.
- Resources subsystem - Provides classes for resources and resource files.
Use the resources subsystem classes to open and close resource files, and to read
resources from resource files.
- Window subsystem - Provides wrapper objects for OpenDoc ODWindow
objects. This is needed because OpenDoc doesn't really provide a full
cross-platform API to manipulate windows, and also because ODWindow cannot be
- Menu subsystem - Provides classes to allow you to create cross-platform
menus and attach them to OpenDoc's menu bar. Menus may be changed dynamically,
and hierarchical menus are supported. The menu subsystem is composed of three
classes which encapsulate the top-level menu bar, pull-down menus, and
individual menu items.
- Events subsystem - Provides classes for platform-independent access
to operating system events, distribution of events to event handlers, and
target management. Event handlers in ODF support the ability to dynamically
attach additional event handlers to intercept events providing a superset of
the behavior mechanism in MacApp.
- Graphic subsystem - Uses a QuickDraw GX model to provide
platform-independent graphics. Like QuickDraw GX you create and draw objects.
Fundamental graphic shapes like rectangles and lines are objects. Other pieces
of information such as the color of a shape or the font used to draw a letter,
are also kept in an object.
- OS Utilities subsystem - Provides a collection of miscellaneous classes
which don't logically belong with other OS layer subsystems. There are four
classes defined in the utilities subsystem to manage different types of cross
platform resources. FW_CAlert allows you to display cross-platform alerts or
message boxes. FW_CCursor is used to load, show, and hide cursors. FW_CTime
and FW_CTimeSpan provide a way to work with time in a platform-independent
- International subsystem - Provides routines for dealing with OpenDoc's
ODIText type, which represents international strings used in menus.
- OD Utilities - Provides classes that support streaming data to and from
OpenDoc storage units. There are also classes that make it easier to deal with
OpenDoc exceptions and ODByteArrays.
The Framework layer ties together all of the services provided by the Foundation and OS layer to produce cross-platform OpenDoc component editors.
- Gadget Subsystem - Gadgets are intended to provide a light-weight
view-like object for dealing specifically with user interface objects, such as
buttons and scroll bars, provided on Macintosh and Windows platforms. They
provide a platform-independent abstraction for creating and interacting with
- Part Subsystem - Classes in the part subsystem allow you to create component editors that have content, support drag and drop, undo, linking, selection, and scrolling. The part subsystem allows you to create component editors that can be embedded in other containers as well as component editors capable of embedding other components into their own content.
Hardware and Software Compatibility Requirements
ODF relies on the existence of OpenDoc on the target machine. Its hardware and software requirements will be the same as those required by OpenDoc for both the 68K and PowerPC Macintosh platforms and Intel-based Windows platforms.
Apple is working to ensure that the most prominent development environments and compilers for both platforms support ODF, so that developers will be able to use their preferred environment and set of tools. We will evaluate other compilers and development environments as they add support for the shared library mechanisms used by OpenDoc.