Types are the fundamental building blocks of the Oxygene language.
There are three broad categories of types:
Predefined Simple Types are small and atomic types that are built into the language to represent the simplest of data: numbers, booleans, strings, and the like.
Custom Types are types not defined by the language, but by yourself or provided by base libraries or frameworks. Where standard types are universal in application, custom types usually serve a specific purpose.
- Blocks (a.k.a. Delegates)
Modified Types are defined by the language itself, and extend or modify the behavior of a regular type, or form complex combinations, such as arrays, sequences, tuples or pointers of a given other type.
Anonymous Types are custom types (Classes or Records) that are instantiated on the fly without being explicitly declared or given a name.
Oxygene also has support for declaring types in special ways:
Generic Types are classes (or records and interfaces) where one or more of the other types that the class interacts with (for example to receive or return as a parameter from methods) is not well-defined, but kept generic. This allows for the class to be implemented in a fashion that it can work with or contain different type parameters. Only when a generic type is used, a concrete type is specified.
Partial Types are regular types that are declared and implemented across multiple source files – commonly to keep a large class easier to maintain, or because one part of the class is generated by a tool.
Mapped Types allow you to provide the definition of a type that will not exist at runtime, but merely map to a different, already existing type.
Type Extensions can expand an existing type with new methods or properties (but not new data), even if that type was originally declared in an external library.
Type Aliases can give a new name to an existing type.
Custom Types and Aliases to existing types can be declared in the
implementation section of any source file, after a
Each type declaration starts with the type's name, followed by an equal sign (
=) and followed by optional Type Modifiers, which can also include a Visibility Lebel, followed by the details of the type declaration as specified in the individual custom type topics referenced above.
type MyClass = sealed class end; MyInteger = public type Integer;
In the above example,
MyInteger are the type names. They are followed by the equal sign, and the
public type modifiers, respectively. Finally
class ... end and
Integer are the type declaration itself (a Class declaration and an Alias, in this case).
While Type Declarations, covered above, introduce a new type name, the most common interaction with types is to reference existing ones.
Most types, including Simple Types and Custom Types, are referenced using simply their name – either their short name, or their fully qualified name including the Namespace.
var x: SomeClass; // Variable x is declared referencing the SomeClass type by name.
By contrast, Modified Types are referenced using a particular syntax specific to the type, such as the
sequence of or
nullable keywords, often combined with a type name.
var x: array of SomeRecord; // Variable x is as an *array* of the type referred to by name. var y: nullable Integer; // Variable x is as a *nullable* version of the name's simple type.
On the Cocoa platform, type references can be prefixed with Storage Modifiers to determine how they interact with ARC.
On the Island-based platform, type references can be prefixed with a Life-Time Strategy Modifier to determine how their lifetime is managed (although doing so explicitly is rarely needed). Storage Modifiers, as discussed above, are also supported when working with Cocoa or Swift objects Cocoa project.
More on Type Names
Every named type (Simple Types and Custom Types) in Oxygene can be referred to either by its short name (e.g.
MyClass), or what is called a fully qualified name that includes a full namespace (e.g.
When declaring types with a simple name, the type will automatically be placed within the namespace that is declared at the top of the file alongside the
namespace keyword. Alternatively, a fully qualified name can be provided in the declaration to override the namespace.
namespace MyCompany.MyProject interface type MyClass = class // full name will be MyCompany.MyProject.MyClass end; MyCompany.OtherProject.OtherClass = class // full name will be MyCompany.OtherProject.OtherClass end;
You can read more about this in the Namespaces topic.