# Class and Interface Registration

## Comprehensive registration system for classes and interfaces with methods, properties, and events.

VlppReflection provides extensive macros for registering classes and interfaces, enabling complete runtime reflection support including methods, properties, events, constructors, and inheritance relationships. The system supports both classes and interfaces with shared registration patterns.

## Basic Registration Patterns

### Class Registration
- Use `BEGIN_CLASS_MEMBER` and `END_CLASS_MEMBER` for class registration
- Provides foundation for making class types accessible through reflection
- Supports all class features including inheritance, methods, and properties

### Interface Registration
- Use `BEGIN_INTERFACE_MEMBER` and `END_INTERFACE_MEMBER` for inheritable interfaces
- Use `BEGIN_INTERFACE_MEMBER_NOPROXY` and `END_INTERFACE_MEMBER` for non-inheritable interfaces
- Interfaces can be inherited in Workflow scripts when using the regular `BEGIN_INTERFACE_MEMBER`

## Registration Components

### Base Class Declaration
- Use `CLASS_MEMBER_BASE` for reflectable base class declaration
- Enables proper inheritance hierarchy in reflection
- Supports multiple inheritance scenarios

### Field Registration
- Use `CLASS_MEMBER_FIELD` for member field registration
- Exposes public fields through the reflection system
- Enables dynamic field access and manipulation

### Constructor Registration
- Use `CLASS_MEMBER_CONSTRUCTOR` for constructor registration with `Ptr<Class>(types...)` or `Class*(types...)`
- Use `CLASS_MEMBER_EXTERNALCTOR` for external function constructors
- Use `CLASS_MEMBER_EXTERNALCTOR_TEMPLATE` when an external constructor needs custom generated C++ code templates
- Constructor type determines whether instances are boxed in `Ptr<T>` or not

### Method Registration
- Use `CLASS_MEMBER_METHOD` for method registration with parameter names
- Use `CLASS_MEMBER_METHOD_RENAME` to register a non-overloaded member function under a different reflected name
- Use `CLASS_MEMBER_METHOD_OVERLOAD` for overloaded method registration
- Use `CLASS_MEMBER_METHOD_OVERLOAD_RENAME` to register a specific overload under a different reflected name
- Use `CLASS_MEMBER_EXTERNALMETHOD` for external function methods
- Use `CLASS_MEMBER_EXTERNALMETHOD_TEMPLATE` when an external method needs custom generated C++ code templates
- Use `CLASS_MEMBER_STATIC_METHOD` for static method registration
- Use `CLASS_MEMBER_STATIC_METHOD_OVERLOAD` for overloaded static method registration
- Use `CLASS_MEMBER_STATIC_EXTERNALMETHOD` for global functions registered as static methods
- Use `CLASS_MEMBER_STATIC_EXTERNALMETHOD_TEMPLATE` when a static external method needs custom generated C++ code templates

### Event Registration
- Use `CLASS_MEMBER_EVENT` for event registration
- Events are typically `Event<T>` type fields
- Enables dynamic event subscription and notification

### Property Registration
- Use `CLASS_MEMBER_PROPERTY_READONLY`, `CLASS_MEMBER_PROPERTY` for property registration
- Use `CLASS_MEMBER_PROPERTY_EVENT_READONLY`, `CLASS_MEMBER_PROPERTY_EVENT` for properties with explicit getter/setter/event methods
- Use `CLASS_MEMBER_PROPERTY_REFERENCETEMPLATE` when generated C++ needs custom reference code for the property
- Use `CLASS_MEMBER_PROPERTY_READONLY_FAST`, `CLASS_MEMBER_PROPERTY_FAST` for standard getter/setter patterns
- Use `CLASS_MEMBER_PROPERTY_EVENT_READONLY_FAST`, `CLASS_MEMBER_PROPERTY_EVENT_FAST` for properties with change events

## Parameter Name Specifications

### Function Arguments
For constructors and methods, argument names are required in the declaration:
- Use `NO_PARAMETER` for parameterless functions
- Use `{ L"arg1" _ L"arg2" ... }` for parameter name lists
- The `_` macro must be defined as `,` in the implementation file

## Registration Examples

### Basic Class Registration
```cpp
BEGIN_CLASS_MEMBER(MyClass)
    CLASS_MEMBER_FIELD(FirstField)
    CLASS_MEMBER_FIELD(SecondField)
END_CLASS_MEMBER(MyClass)
```

### Interface Registration
```cpp
BEGIN_INTERFACE_MEMBER(IMyInterface)
    CLASS_MEMBER_FIELD(FirstField)
    CLASS_MEMBER_FIELD(SecondField)
END_INTERFACE_MEMBER(IMyInterface)
```

### Complete Class with All Features
```cpp
#define _ ,

BEGIN_CLASS_MEMBER(MyClass)
    CLASS_MEMBER_BASE(BaseClass)
    CLASS_MEMBER_FIELD(fieldName)
    CLASS_MEMBER_CONSTRUCTOR(Ptr<MyClass>(vint), { L"value" })
    CLASS_MEMBER_METHOD(MethodName, { L"arg1" _ L"arg2" })
    CLASS_MEMBER_STATIC_METHOD(StaticMethod, NO_PARAMETER)
    CLASS_MEMBER_EVENT(SomeEvent)
    CLASS_MEMBER_PROPERTY_FAST(PropertyName)
END_CLASS_MEMBER(MyClass)

#undef _
```

## Attribute Registration

### Attaching Attributes to Types, Members, and Parameters
- Use `ATTRIBUTE_TYPE(TYPE, ...)` to attach an attribute to the type descriptor itself
- Use `ATTRIBUTE_MEMBER(TYPE, ...)` after any member registration to attach an attribute to that member
- Use `ATTRIBUTE_PARAMETER(PARAMETER_NAME, TYPE, ...)` after a method or constructor registration to attach an attribute to a named parameter
- The attribute type must be a reflected struct
- Each ordinary argument must be serializable; `ITypeDescriptor*` is supported as a raw-pointer descriptor reference
- Multiple attributes can be attached to the same target
- See [Attribute Registration](./KB_VlppReflection_AttributeRegistration.md) for full details

### Class with Attributes Example
```cpp
#define _ ,

BEGIN_CLASS_MEMBER(MyClass)
    ATTRIBUTE_TYPE(MyAttribute, L"type", 1)

    CLASS_MEMBER_CONSTRUCTOR(Ptr<MyClass>(vint), {L"seed"})
    ATTRIBUTE_MEMBER(MyAttribute, L"ctor", 2)
    ATTRIBUTE_PARAMETER(L"seed", MyAttribute, L"param", 3)

    CLASS_MEMBER_METHOD(DoWork, {L"x" _ L"y"})
    ATTRIBUTE_MEMBER(MyAttribute, L"method", 4)
    ATTRIBUTE_PARAMETER(L"x", MyAttribute, L"param-x", 5)
END_CLASS_MEMBER(MyClass)

#undef _
```

## Interface Requirements

### Proxy Requirements
Using `BEGIN_INTERFACE_MEMBER` requires a proxy to EXIST in the header file, which means the interface can be inherited in Workflow script.

Using `BEGIN_INTERFACE_MEMBER_NOPROXY` requires a proxy to NOT EXIST in the header file, which means the interface cannot be inherited in Workflow script.

### Constructor Limitations
There is no constructor in an interface registration - only classes support constructor registration.

## Extra Content

### Advanced Registration Features

#### Method Overloading
For overloaded methods, use specific macros:
- `CLASS_MEMBER_METHOD_OVERLOAD(name, parameter, function-type)`
- `CLASS_MEMBER_METHOD_OVERLOAD_RENAME(new-name, name, parameter, function-type)`
- `CLASS_MEMBER_METHOD_RENAME(new-name, name, parameters)` for non-overloaded methods that need a different reflected name
- Function type must be a pointer to member function

#### External Methods
For methods implemented as external functions:
- `CLASS_MEMBER_EXTERNALMETHOD(name, parameters, function-type, source)`
- `CLASS_MEMBER_EXTERNALMETHOD_TEMPLATE(name, parameters, function-type, source, invoke-template, closure-template)`
- First parameter acts as `this` pointer
- Should not appear in parameters or function-type

#### Static Methods
For static methods and global functions registered as static methods:
- `CLASS_MEMBER_STATIC_METHOD(name, parameters)` for non-overloaded static member functions
- `CLASS_MEMBER_STATIC_METHOD_OVERLOAD(name, parameters, function-type)` for overloaded static member functions
- `CLASS_MEMBER_STATIC_EXTERNALMETHOD(name, parameters, function-type, source)` for global functions
- `CLASS_MEMBER_STATIC_EXTERNALMETHOD_TEMPLATE(name, parameters, function-type, source, invoke-template, closure-template)` when generated C++ needs custom templates

#### Property Shortcuts
Fast property registration shortcuts:
- `CLASS_MEMBER_PROPERTY_READONLY_FAST(X)` for `GetX()` getter and property `X`
- `CLASS_MEMBER_PROPERTY_FAST(X)` for `GetX()` getter, `SetX()` setter, and property `X`
- `CLASS_MEMBER_PROPERTY_EVENT_READONLY_FAST(X, XChanged)` for `GetX()` and an existing `XChanged` event
- `CLASS_MEMBER_PROPERTY_EVENT_FAST(X, XChanged)` for `GetX()`, `SetX()`, and an existing `XChanged` event
- `CLASS_MEMBER_PROPERTY_REFERENCETEMPLATE(X, GetX, SetX, template)` when generated C++ needs a custom property reference expression

### Best Practices

1. **Complete Registration**: Register all public members that should be accessible
2. **Consistent Naming**: Follow established naming conventions
3. **Parameter Documentation**: Provide meaningful parameter names
4. **Event Integration**: Use events to notify property changes
5. **Type Safety**: Ensure all referenced types are properly registered

### Performance Considerations

- Registration occurs at startup time with minimal runtime overhead
- Dynamic method calls have slight performance cost compared to direct calls
- Property access through reflection is slower than direct field access
- Consider caching reflection results for frequently used operations
