home *** CD-ROM | disk | FTP | other *** search
- {*******************************************************}
- { }
- { Delphi Visual Component Library }
- { }
- { Copyright (c) 1995 Borland International }
- { }
- {*******************************************************}
-
- unit DsgnIntf;
-
- interface
-
- {$N+,S-,W-}
-
- uses SysUtils, Classes, Graphics, Controls, Forms, TypInfo;
-
- type
-
- { TComponentList }
-
- TComponentList = class(TObject)
- public
- constructor Create;
- destructor Destroy; override;
- function Add(Item: TComponent): Integer;
- function Equals(List: TComponentList): Boolean;
- property Count: Integer;
- property Items[Index: Integer]: TComponent; default;
- end;
-
- { TPropertyEditor
- Edits a property of a component, or list of components, selected into the
- Object Inspector. The property editor is created based on the type of the
- property being edited as determined by the types registered by
- RegisterPropertyEditor. The Object Inspector uses the a TPropertyEditor
- for all modification to a property. GetName and GetValue are called to display
- the name and value of the property. SetValue is called whenever the user
- requests to change the value. Edit is called when the user double-clicks the
- property in the Object Inspector. GetValues is called when the drop-down
- list of a property is displayed. GetProperties is called when the property
- is expanded to show sub-properties. AllEqual is called to decide whether or
- not to display the value of the property when more than one component is
- selected.
-
- The following are methods that can be overriden to change the behavior of
- the property editor:
-
- Activate
- Called whenever the property becomes selected in the object inspector.
- This is potientially useful to allow certian property attributes to
- to only be determined whenever the property is selected in the object
- inspector. Only paSubProperties and paMultiSelect, returned from
- GetAttributes, need to be accurate before this method is called.
- AllEqual
- Called whenever there are more than one components selected. If this
- method returns true, GetValue is called, otherwise blank is displayed
- in the Object Inspector. This is called only when GetAttributes
- returns paMultiSelect.
- Edit
- Called when the '...' button is pressed or the property is double-clicked.
- This can, for example, bring up a dialog to allow the editing the
- component in some more meaningful fashion than by text (e.g. the Font
- property).
- GetAttributes
- Returns the information for use in the Object Inspector to be able to
- show the approprate tools. GetAttributes return a set of type
- TPropertyAttributes:
- paValueList: The property editor can return an enumerated list of
- values for the property. If GetValues calls Proc
- with values then this attribute should be set. This
- will cause the drop-down button to appear to the right
- of the property in the Object Inspector.
- paSortList: Object Inspector to sort the list returned by
- GetValues.
- paSubProperties: The property editor has sub-properties that will be
- displayed indented and below the current property in
- standard outline format. If GetProperties will
- generate property objects then this attribute should
- be set.
- paDialog: Indicates that the Edit method will bring up a
- dialog. This will cause the '...' button to be
- displayed to the right of the property in the Object
- Inspector.
- paMultiSelect: Allows the property to be displayed when more than
- one component is selected. Some properties are not
- approprate for multi-selection (e.g. the Name
- property).
- paAutoUpdate: Causes the SetValue method to be called on each
- change made to the editor instead of after the change
- has been approved (e.g. the Caption property).
- paReadOnly: Value is not allowed to change.
- GetComponent
- Returns the Index'th component being edited by this property editor. This
- is used to retieve the components. A property editor can only refer to
- multiple components when paMultiSelect is returned from GetAttributes.
- GetEditLimit
- Returns the number of character the user is allowed to enter for the
- value. The inplace editor of the object inspector will be have its
- text limited set to the return value. By default this limit is 255.
- GetName
- Returns a the name of the property. By default the value is retrieved
- from the type information with all underbars replaced by spaces. This
- should only be overriden if the name of the property is not the name
- that should appear in the Object Inspector.
- GetProperties
- Should be overriden to call PropertyProc for every sub-property (or nested
- property) of the property begin edited and passing a new TPropertyEdtior
- for each sub-property. By default, PropertyProc is not called and no
- sub-properties are assumed. TClassProperty will pass a new property
- editor for each published property in a class. TSetProperty passes a
- new editor for each element in the set.
- GetPropType
- Returns the type information pointer for the propertie(s) being edited.
- GetValue
- Returns the string value of the property. By default this returns
- '(unknown)'. This should be overriden to return the appropriate value.
- GetValues
- Called when paValueList is returned in GetAttributes. Should call Proc
- for every value that is acceptable for this property. TEnumProperty
- will pass every element in the enumeration.
- Initialize
- Called after the property editor has been created but before it is used.
- Many times property editors are created and because they are not a common
- property across the entire selection they are thrown away. Initialize is
- called after it is determined the property editor is going to be used by
- the object inspector and not just thrown away.
- SetValue(Value)
- Called to set the value of the property. The property editor should be
- able to translate the string and call one of the SetXxxValue methods. If
- the string is not in the correct format or not an allowed value, the
- property editor should generate an exception describing the problem. Set
- value can ignore all changes and allow all editing of the property be
- accomplished through the Edit method (e.g. the Picture property).
-
- Properties and methods useful in creating a new TPropertyEditor classes:
-
- Name property
- Returns the name of the property returned by GetName
- PrivateDirectory property
- It is either the .EXE or the "working directory" as specified in
- DELPHI.INI. If the property editor needs auxilury or state files
- (templates, examples, etc) they should be stored in this directory.
- Properties indexed property
- The TProperty objects representing all the components being edited
- by the property editor. If more than one component is selected, one
- TProperty object is created for each component. Typically, it is not
- necessary to use this array since the Get/SetXxxValue methods will
- propagate the values appropriatly.
- Value property
- The current value, as a string, of the property as returned by GetValue.
- Modified
- Called to indicate the value of the property has been modified. Called
- automatically by the SetXxxValue methods. If you call a TProperty
- SetXxxValue method directly, you *must* call Modified as well.
- GetXxxValue
- Gets the value of the first property in the Properties property. Calls
- the appropriate TProperty GetXxxValue method to retrieve the value.
- SetXxxValue
- Sets the value of all the properties in the Properties property. Calls
- the approprate TProperty SetXxxxValue methods to set the value. }
-
- TFormDesigner = class(TDesigner)
- public
- function CreateMethod(const Name: string; TypeData: PTypeData): TMethod; virtual; abstract;
- function GetMethodName(const Method: TMethod): string; virtual; abstract;
- procedure GetMethods(TypeData: PTypeData; Proc: TGetStrProc); virtual; abstract;
- function GetPrivateDirectory: string; virtual; abstract;
- function MethodExists(const Name: string): Boolean; virtual; abstract;
- procedure RenameMethod(const CurName, NewName: string); virtual; abstract;
- procedure ShowMethod(const Name: string); virtual; abstract;
- end;
-
- TPropertyAttribute = (paValueList, paSubProperties, paDialog,
- paMultiSelect, paAutoUpdate, paSortList, paReadOnly);
- TPropertyAttributes = set of TPropertyAttribute;
-
- TPropertyEditor = class;
-
- TInstProp = record
- Instance: TComponent;
- PropInfo: PPropInfo;
- end;
-
- PInstPropList = ^TInstPropList;
- TInstPropList = array[0..1023] of TInstProp;
-
- TGetPropEditProc = procedure(Prop: TPropertyEditor) of object;
-
- TPropertyEditor = class
- protected
- function GetPropInfo: PPropInfo;
- function GetFloatValue: Extended;
- function GetFloatValueAt(Index: Integer): Extended;
- function GetMethodValue: TMethod;
- function GetMethodValueAt(Index: Integer): TMethod;
- function GetOrdValue: Longint;
- function GetOrdValueAt(Index: Integer): Longint;
- function GetStrValue: string;
- function GetStrValueAt(Index: Integer): string;
- procedure Modified;
- procedure SetFloatValue(Value: Extended);
- procedure SetMethodValue(const Value: TMethod);
- procedure SetOrdValue(Value: Longint);
- procedure SetStrValue(const Value: string);
- public
- destructor Destroy; override;
- procedure Activate; virtual;
- function AllEqual: Boolean; virtual;
- procedure Edit; virtual;
- function GetAttributes: TPropertyAttributes; virtual;
- function GetComponent(Index: Integer): TComponent;
- function GetEditLimit: Integer; virtual;
- function GetName: string; virtual;
- procedure GetProperties(Proc: TGetPropEditProc); virtual;
- function GetPropType: PTypeInfo;
- function GetValue: string; virtual;
- procedure GetValues(Proc: TGetStrProc); virtual;
- procedure Initialize; virtual;
- procedure SetValue(const Value: string); virtual;
- property Designer: TFormDesigner;
- property PrivateDirectory: string;
- property PropCount: Integer;
- property Value: string;
- end;
-
- TPropertyEditorClass = class of TPropertyEditor;
-
- { TOrdinalProperty
- The base class of all ordinal property editors. It established that ordinal
- properties are all equal if the GetOrdValue all return the same value. }
-
- TOrdinalProperty = class(TPropertyEditor)
- function AllEqual: Boolean; override;
- function GetEditLimit: Integer; override;
- end;
-
- { TIntegerProperty
- Default editor for all Longint properties and all subtypes of the Longint
- type (i.e. Integer, Word, 1..10, etc.). Retricts the value entrered into
- the property to the range of the sub-type. }
-
- TIntegerProperty = class(TOrdinalProperty)
- public
- function GetValue: string; override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TCharProperty
- Default editor for all Char properties and sub-types of Char (i.e. Char,
- 'A'..'Z', etc.). }
-
- TCharProperty = class(TOrdinalProperty)
- public
- function GetValue: string; override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TEnumProperty
- The default property editor for all enumerated properties (e.g. TShape =
- (sCircle, sTriangle, sSquare), etc.). }
-
- TEnumProperty = class(TOrdinalProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TFloatProperty
- The default property editor for all floating point types (e.g. Float,
- Single, Double, etc.) }
-
- TFloatProperty = class(TPropertyEditor)
- public
- function AllEqual: Boolean; override;
- function GetValue: string; override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TStringProperty
- The default property editor for all strings and sub types (e.g. string,
- string[20], etc.). }
-
- TStringProperty = class(TPropertyEditor)
- public
- function AllEqual: Boolean; override;
- function GetEditLimit: Integer; override;
- function GetValue: string; override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TSetElementProperty
- A property editor that edits an individual set element. GetName is
- changed to display the set element name instead of the property name and
- Get/SetValue is changed to reflect the individual element state. This
- editor is created by the TSetProperty editor. }
-
- TSetElementProperty = class(TPropertyEditor)
- public
- destructor Destroy; override;
- function AllEqual: Boolean; override;
- function GetAttributes: TPropertyAttributes; override;
- function GetName: string; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TSetProperty
- Default property editor for all set properties. This editor does not edit
- the set directly but will display sub-properties for each element of the
- set. GetValue displays the value of the set in standard set syntax. }
-
- TSetProperty = class(TOrdinalProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- procedure GetProperties(Proc: TGetPropEditProc); override;
- function GetValue: string; override;
- end;
-
- { TClassProperty
- Default proeperty editor for all objects. Does not allow modifing the
- property but does display the class name of the object and will allow the
- editing of the object's properties as sub-properties of the property. }
-
- TClassProperty = class(TPropertyEditor)
- public
- function GetAttributes: TPropertyAttributes; override;
- procedure GetProperties(Proc: TGetPropEditProc); override;
- function GetValue: string; override;
- end;
-
- { TMethodProperty
- Property editor for all method properties. }
-
- TMethodProperty = class(TPropertyEditor)
- public
- function AllEqual: Boolean; override;
- procedure Edit; override;
- function GetAttributes: TPropertyAttributes; override;
- function GetEditLimit: Integer; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const AValue: string); override;
- end;
-
- { TComponentProperty
- The default editor for TComponents. It does not allow editing of the
- properties of the component. It allow the user to set the value of this
- property to point to a component in the same form that is type compatible
- with the property being edited (e.g. the ActiveControl property). }
-
- TComponentProperty = class(TPropertyEditor)
- public
- function GetAttributes: TPropertyAttributes; override;
- function GetEditLimit: Integer; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TComponentNameProperty
- Property editor for the Name property. It restricts the name property
- from being displayed when more than one component is selected. }
-
- TComponentNameProperty = class(TStringProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- end;
-
- { TFontNameProperty
- Editor for the TFont.FontName property. Displays a drop-down list of all
- the fonts known by Windows.}
-
- TFontNameProperty = class(TStringProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- procedure GetValues(Proc: TGetStrProc); override;
- end;
-
- { TColorProperty
- Property editor for the TColor type. Displays the color as a clXXX value
- if one exists, otherwise displays the value as hex. Also allows the
- clXXX value to be picked from a list. }
-
- TColorProperty = class(TIntegerProperty)
- public
- procedure Edit; override;
- function GetAttributes: TPropertyAttributes; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TCursorProperty
- Property editor for the TCursor type. Displays the color as a crXXX value
- if one exists, otherwise displays the value as hex. Also allows the
- clXXX value to be picked from a list. }
-
- TCursorProperty = class(TIntegerProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TFontProperty
- Property editor the Font property. Brings up the font dialog as well as
- allowing the properties of the object to be edited. }
-
- TFontProperty = class(TClassProperty)
- public
- procedure Edit; override;
- function GetAttributes: TPropertyAttributes; override;
- end;
-
- { TModalResultProperty }
-
- TModalResultProperty = class(TIntegerProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TShortCutProperty
- Property editor the the ShortCut property. Allows both typing in a short
- cut value or picking a short-cut value from a list. }
-
- TShortCutProperty = class(TOrdinalProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- function GetValue: string; override;
- procedure GetValues(Proc: TGetStrProc); override;
- procedure SetValue(const Value: string); override;
- end;
-
- { TMPFilenameProperty
- Property editor for the TMediaPlayer. Displays an File Open Dialog
- for the name of the media file.}
-
- TMPFilenameProperty = class(TStringProperty)
- public
- procedure Edit; override;
- function GetAttributes: TPropertyAttributes; override;
- end;
-
- { TTabOrderProperty
- Property editor for the TabOrder property. Prevents the property from being
- displayed when more than one component is selected. }
-
- TTabOrderProperty = class(TIntegerProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- end;
-
- { TCaptionProperty
- Property editor for the Caption and Text properties. Updates the value of
- the property for each change instead on when the property is approved. }
-
- TCaptionProperty = class(TStringProperty)
- public
- function GetAttributes: TPropertyAttributes; override;
- end;
-
- EPropertyError = class(Exception);
-
- { TComponentEditor
- A component editor is created for each component that is selected in the
- form designer based on the component's type (see GetComponentEditor and
- RegisterComponentEditor). When the component is double-clicked the Edit
- method is called. When the context menu for the component is invoked the
- GetVerbCount and GetVerb methods are called to build the menu. If one
- of the verbs are selected ExecuteVerb is called. Paste is called whenever
- the component is pasted to the clipboard. You only need to create a
- component editor if you wish to add verbs to the context menu, change
- the default double-click behavior, or paste an additional clipboard format.
- The default component editor (TDefaultEditor) implements Edit to searchs the
- properties of the component and generates (or navigates to) the OnCreate,
- OnChanged, or OnClick event (whichever it finds first). Whenever the
- component modifies the component is *must* call Designer.Modified to inform
- the designer that the form has been modified.
-
- Create(AComponent, ADesigner)
- Called to create the component editor. AComponent is the component to
- be edited by the editor. ADesigner is an interface to the designer to
- find controls and create methods (this is not use often).
- Edit
- Called when the user double-clicks the component. The component editor can
- bring up a dialog in responce to this method, for example, or some kind
- of design expert. If GetVerbCount is greater than zero, edit will execute
- the first verb in the list (ExecuteVerb(0)).
- ExecuteVerb(Index)
- The Index'ed verb was selected by the use off the context menu. The
- meaning of this is determined by component editor.
- GetVerb
- The component editor should return a string that will be displayed in the
- context menu. It is the responcibility of the component editor to place
- the & character and the '...' characters as appropriate.
- GetVerbCount
- The number of valid indexs to GetVerb and Execute verb. The index assumed
- to be zero based (i.e. 0..GetVerbCount - 1).
- Copy
- Called when the component is being copyied to the clipboard. The
- component's filed image is already on the clipboard. This gives the
- component editor a chance to paste a different type of format which is
- ignored by the designer but might be recoginized by another application. }
-
- TComponentEditor = class
- public
- constructor Create(AComponent: TComponent; ADesigner: TFormDesigner); virtual;
- procedure Edit; virtual;
- procedure ExecuteVerb(Index: Integer); virtual;
- function GetVerb(Index: Integer): string; virtual;
- function GetVerbCount: Integer; virtual;
- procedure Copy; virtual;
- property Component: TComponent;
- property Designer: TFormDesigner;
- end;
-
- TComponentEditorClass = class of TComponentEditor;
-
- TDefaultEditor = class(TComponentEditor)
- protected
- procedure EditProperty(PropertyEditor: TPropertyEditor;
- var Continue, FreeEditor: Boolean); virtual;
- public
- procedure Edit; override;
- end;
-
- { RegisterPropertyEditor
- Registers a new property editor for the given type. When a component is
- selected the Object Inspector will create a property editor for each
- of the component's properties. The property editor is created based on
- the type of the property. If, for example, the property type is an
- Integer, the property editor for Integer will be created (by default
- that would be TIntegerProperty). Most properties do not need specialized
- property editors. For example, if the property is an ordinal type the
- default property editor will restrict the range to the ordinal subtype
- range (e.g. a property of type TMyRange = 1..10 will only allow values
- between 1 and 10 to be entered into the property). Enumerated types will
- display a drop-down list of all the enumerated values (e.g. TShapes =
- (sCircle, sSquare, sTriangle) will be edited by a drop-down list containing
- only sCircle, sSquare and sTriangle). A property editor need only be
- created if default property editor or none of the existing property editors
- are sufficient to edit the property. This is typically because the
- property is an object. The properties are looked up newest to oldest.
- This allows and existing property editor replaced by a custom property
- editor.
-
- PropertyType
- The type information pointer returned by the TypeInfo built-in function
- (e.g. TypeInfo(TMyRange) or TypeInfo(TShapes)).
-
- ComponentClass
- Type type of the component to which to restrict this type editor. This
- parameter can be left nil which will mean this type editor applies to all
- properties of PropertyType.
-
- PropertyName
- The name of the property to which to restrict this type editor. This
- parameter is ignored if ComponentClass is nil. This paramter can be
- an empty string ('') which will mean that this editor applies to all
- properties of PropertyType in ComponentClass.
-
- EditorClass
- The class of the editor to be created whenever a property of the type
- passed in PropertyTypeInfo is displayed in the Object Inspector. The
- class will be created by calling EditorClass.Create. }
-
- procedure RegisterPropertyEditor(PropertyType: PTypeInfo; ComponentClass: TClass;
- const PropertyName: string; EditorClass: TPropertyEditorClass);
-
- procedure GetComponentProperties(Components: TComponentList;
- Filter: TTypeKinds; Designer: TFormDesigner; Proc: TGetPropEditProc);
-
- procedure RegisterComponentEditor(ComponentClass: TComponentClass;
- ComponentEditor: TComponentEditorClass);
-
- function GetComponentEditor(Component: TComponent;
- Designer: TFormDesigner): TComponentEditor;
-
- implementation
-