Rius |
Отправлено: 14.05.2005, 09:54 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
Этого явно недостаточно:
CODE |
//---------------------------------------------------------------------------
void __fastcall TButtonImage::SetImageIndex(const TImageIndex Value)
{
if( FImageIndex != Value)
{
FImageIndex = Value;
if(this) Invalidate();
}
}
//---------------------------------------------------------------------------
void __fastcall TButtonImage::SetImages(TImageList* Value)
{
if( FImages != Value)
{
FImages = Value;
if(this)
{
// FEditControl.Perform(CM_EDITIMAGECHANGEDEH, ObjectToIntPtr(Self), 0);
// if Value <> nil then Value.FreeNotification(FEditControl);
}
}
}
//---------------------------------------------------------------------------
class PACKAGE TButtonImage : public TButton
{
typedef TButton Inherited;
private:
TImageIndex FImageIndex;
TImageList* FImages;
void __fastcall SetImageIndex(const TImageIndex Value);
void __fastcall SetImages(TImageList* Value);
__published:
__property TImageIndex ImageIndex = {read=FImageIndex, write=SetImageIndex, default=-1};
__property TImageList* Images = {read=FImages, write=SetImages};
};
|
не выпадает список. может есть какие примеры?
|
|
GIZMO |
Отправлено: 14.05.2005, 10:29 |
|
Машинист паровоза
Группа: Участник
Сообщений: 174
|
QUOTE (Rius @ 14/05/2005, 09:54) | Этого явно недостаточно:
...
не выпадает список. может есть какие примеры? |
Как он тебе выпадет, редактор св-ва надо писать.
|
|
Rius |
Отправлено: 14.05.2005, 12:42 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
У многих компонент VCL есть свойство ImageIndex, определенное также. Редактор должен предоставляться средой, как делается для других свойств...
Свой писать — может придется, пока разбираюсь.
|
|
Gedeon |
Отправлено: 14.05.2005, 12:49 |
|
Ветеран
Группа: Модератор
Сообщений: 1742
|
TImageIndex есть не что иное как int, а конкретно номер рисунка в TImageList, соответственно причем тут редактор? Посмотрите как это реализовано в других компонентах.
И из Первоначального вопроса Rius того, что Вы привели явно достаточно для добавления свойства, а теперь Вам надо позаботиться как достать рисунок и правильно его нарисовать в Вашем компоненте.
Отредактировано Gedeon — 14/05/2005, 12:51
|
|
Rius |
Отправлено: 14.05.2005, 13:11 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
Gedeon ImageIndex на самом деле типа Imglist::TImageIndex, что есть переименованный int.
Свойство добавлено, рисунок достать тоже могу, но в инспекторе объектов при выборе ImageIndex должен выпадать список. Вот его-то и нет! Для этого делают редакторы свойств, но этот тип TImageIndex уже должен иметь редактор... Что-то не так делаю.
Перерыл много чего в сети, а нашел один пример в Toolbar2k, там сделан свой редактор свойства, и тот на паскале.
Или у меня синтаксическая ошибка/отличие или очередная "фича" борланда.
здесь удалось добавить выпадающий ImageIndex:
*.pas
CODE | unit ColorButton;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls, Buttons, ExtCtrls, ImgList;
type
TDrawButtonEvent = procedure(Control: TWinControl;
Rect: TRect; State: TOwnerDrawState) of object;
TColorButton = class(TButton)
private
FImages: TImageList;
FImageIndex: TImageIndex;
procedure SetImageIndex(const Value: TImageIndex);
procedure SetImages(const Value: TImageList);
protected
public
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
published
property Images: TImageList read FImages write SetImages;
property ImageIndex: TImageIndex read FImageIndex write SetImageIndex default 0;
end;
procedure Register;
implementation
procedure Register;
begin
RegisterComponents('RComp', [TColorButton]);
end;
constructor TColorButton.Create(AOwner: TComponent);
begin
inherited Create(AOwner);
end;
destructor TColorButton.Destroy;
begin
inherited Destroy;
end;
procedure TColorButton.SetImageIndex(const Value: TImageIndex);
begin
if Value <> FImageIndex then
begin
FImageIndex := Value;
Changed();
end;
end;
procedure TColorButton.SetImages(const Value: TImageList);
begin
if Value <> FImages then
begin
FImages := Value;
Changed();
end;
end;
end. |
а здесь — ни в какую!
*.cpp
CODE | //---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
#include "ButtonImage.h"
#pragma package(smart_init)
//---------------------------------------------------------------------------
// ValidCtrCheck is used to assure that the components created do not have
// any pure virtual functions.
//
static inline void ValidCtrCheck(TButtonImage *)
{
new TButtonImage(NULL);
}
//---------------------------------------------------------------------------
__fastcall TButtonImage::TButtonImage(TComponent* Owner)
: TButton(Owner)
{
}
//---------------------------------------------------------------------------
namespace Buttonimage
{
void __fastcall PACKAGE Register()
{
TComponentClass classes[1] = {__classid(TButtonImage)};
RegisterComponents("RComp", classes, 0);
}
}
//---------------------------------------------------------------------------
void __fastcall TButtonImage::SetImageIndex(const TImageIndex Value)
{
if( FImageIndex != Value)
{
FImageIndex = Value;
if(this) Invalidate();
Changed();
}
}
//---------------------------------------------------------------------------
void __fastcall TButtonImage::SetImages(const TImageList* Value)
{
if( FImages != Value)
{
FImages = (TImageList *)Value;
Changed();
}
}
//--------------------------------------------------------------------------- |
*.h
CODE | //---------------------------------------------------------------------------
#ifndef ButtonImageH
#define ButtonImageH
//---------------------------------------------------------------------------
#include <SysUtils.hpp>
#include <Classes.hpp>
#include <Controls.hpp>
#include <StdCtrls.hpp>
#include <Windows.hpp>
#include <Messages.hpp>
#include <Graphics.hpp>
#include <Forms.hpp>
#include <Dialogs.hpp>
#include <StdCtrls.hpp>
#include <Buttons.hpp>
#include <ExtCtrls.hpp>
#include "uxtheme.h"
#include "tmschema.h"
#include "imglist.hpp"
//---------------------------------------------------------------------------
typedef void __fastcall (__closure *TDrawButtonEvent)
(System::TObject *Sender, const Types::TRect &Rect, TOwnerDrawState State);
class PACKAGE TButtonImage : public TButton
{
typedef TButton Inherited;
private:
TImageList* FImages;
TImageIndex FImageIndex;
void __fastcall SetImageIndex(const TImageIndex Value);
void __fastcall SetImages(const TImageList* Value);
protected:
public:
__fastcall TButtonImage(TComponent* Owner);
__fastcall ~TButtonImage();
__published:
__property TImageIndex ImageIndex = {read=FImageIndex, write=SetImageIndex, default=0};
__property TImageList* Images = {read=FImages, write=SetImages};
};
//---------------------------------------------------------------------------
#endif |
Отредактировано Rius — 14/05/2005, 18:00
|
|
Rius |
Отправлено: 15.05.2005, 06:59 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
Написал свой редактор, как правильно переопределить методы ListDrawValue, ListMeasureWidth, ListMeasureHeight? А то ничего не рисуется.
CODE | //---------------------------------------------------------------------------
#pragma hdrstop
#include "MyComponentsRegister.h"
#include "buttonimage.h"
//---------------------------------------------------------------------------
namespace Mycomponentsregister
{
void __fastcall PACKAGE Register()
{
TComponentClass classes[1];
classes[0] = __classid(TButtonImage);
RegisterComponents("RComp", classes, 0);
PTypeInfo ti = *GetPropInfo(__typeinfo(TButtonImage),"ImageIndex")->PropType;
RegisterPropertyEditor(ti, __classid(TButtonImage),
"ImageIndex",__classid(TMyImageIndexPropertyEditor));
}
}
//---------------------------------------------------------------------------
TPropertyAttributes __fastcall TMyImageIndexPropertyEditor::GetAttributes()
{
return TPropertyAttributes() << paMultiSelect << paValueList << paRevertable;
}
//---------------------------------------------------------------------------
void __fastcall TMyImageIndexPropertyEditor::GetValues(TGetStrProc Proc)
{
TCustomImageList *ImgList = NULL;
int i;
ImgList = GetImageListAt(0);
if(ImgList != NULL)
{
for (i = 0; i < ImgList->Count; i++)
{
Proc (IntToStr(i));
}
}
}
//---------------------------------------------------------------------------
//TCustomImageList * __fastcall TMyImageIndexPropertyEditor::GetImageListAt (int Index)
//{
// return NULL;
//}
//---------------------------------------------------------------------------
void __fastcall TMyImageIndexPropertyEditor::ListMeasureHeight(const AnsiString Value, TCanvas *ACanvas,
int &AHeight)
{
TCustomImageList *ImgList = NULL;
ShowMessage(Value);
ImgList = GetImageListAt(0);
AHeight = ACanvas->TextHeight(Value) + 2;
if((ImgList != NULL) && (ImgList->Height + 4 > AHeight))
AHeight = ImgList->Height + 4;
}
//---------------------------------------------------------------------------
void __fastcall TMyImageIndexPropertyEditor::ListMeasureWidth(const AnsiString Value, TCanvas *ACanvas,
int &AWidth)
{
TCustomImageList *ImgList = NULL;
ShowMessage(Value);
ImgList = GetImageListAt(0);
AWidth = ACanvas->TextWidth(Value) + 4;
if(ImgList != NULL)
AWidth += ImgList->Width;
}
//---------------------------------------------------------------------------
void __fastcall TMyImageIndexPropertyEditor::ListDrawValue(const AnsiString Value, TCanvas *ACanvas,
const Types::TRect &ARect, bool ASelected)
{
TCustomImageList *ImgList = NULL;
int x;
// ShowMessage(Result != NULL ? "1" : "0");
ShowMessage(Value);
ImgList = GetImageListAt(0);
ACanvas->FillRect (ARect);
x = ARect.Left + 2;
if(ImgList != NULL)
{
ImgList->Draw (ACanvas, x, ARect.Top + 2, StrToInt(Value));
x += ImgList->Width;
}
ACanvas->TextOut (x + 3, ARect.Top + 1, Value);
}
//---------------------------------------------------------------------------
TCustomImageList * __fastcall TMyImageIndexPropertyEditor::GetImageListAt (int Index)
{
TPersistent *C;
TButtonImage *Item;
TCustomImageList *Result = NULL;
//I'm guessing that the Index parameter is a component index (one that
// would be passed to the GetComponent function).
C = GetComponent(Index);
AnsiString classname = C->ClassName();
// ShowMessage(classname);
if( (C != NULL) && (classname == AnsiString("TButtonImage")))
{
Item = (TButtonImage *)C;
// do
// {
Result = Item->Images;
// ShowMessage(Result != NULL ? "1" : "0");
// if(Result != NULL)
// break;
// Item = Item->Parent;
// if Item = nil then
// Break;
// Result := Item.SubMenuImages;
// while (Result != NULL);
}
return Result;
}
//---------------------------------------------------------------------------
#pragma package(smart_init) |
*.h
CODE | //---------------------------------------------------------------------------
#ifndef MyComponentsRegisterH
#define MyComponentsRegisterH
#include "designeditors.hpp"
#include "designintf.hpp"
#include <vcleditors.hpp>
//---------------------------------------------------------------------------
//class DELPHICLASS TMyImageIndexPropertyEditor;
//class PASCALIMPLEMENTATION TMyImageIndexPropertyEditor : public Designeditors::TIntegerProperty
//class TMyImageIndexPropertyEditor : public TIntegerProperty// : public ICustomPropertyListDrawing
class TMyImageIndexPropertyEditor : public TCursorProperty// : public ICustomPropertyListDrawing
{
// typedef Designeditors::TIntegerProperty Inherited;
typedef TCursorProperty Inherited;
private:
// void *__ICustomPropertyListDrawing; /* Vcleditors::ICustomPropertyListDrawing */
protected:
public:
// operator ICustomPropertyListDrawing*(void) { return (ICustomPropertyListDrawing*)&__ICustomPropertyListDrawing; }
void __fastcall GetValues(TGetStrProc Proc);
TPropertyAttributes __fastcall GetAttributes();
virtual TCustomImageList * __fastcall GetImageListAt (int Index);
// ICustomPropertyListDrawing
void __fastcall ListMeasureHeight(const AnsiString Value, Graphics::TCanvas* ACanvas, int &AHeight);
void __fastcall ListMeasureWidth(const AnsiString Value, Graphics::TCanvas* ACanvas, int &AWidth);
void __fastcall ListDrawValue(const AnsiString Value, Graphics::TCanvas* ACanvas, const Types::TRect &ARect, bool ASelected);
// void __fastcall ListMeasureHeight(const AnsiString Value, Graphics::TCanvas* ACanvas, int &AHeight);
// void __fastcall ListMeasureWidth(const AnsiString Value, Graphics::TCanvas* ACanvas, int &AWidth);
// HIDESBASE void __fastcall ListDrawValue(const AnsiString Value, Graphics::TCanvas* ACanvas, const Types::TRect &ARect, bool ASelected);
// #pragma option push -w-inl
// /* TPropertyEditor.Create */ inline __fastcall virtual TMyImageIndexPropertyEditor(const Designintf::_di_IDesigner ADesigner, int APropCount) : Designeditors::TIntegerProperty(ADesigner, APropCount) { }
// #pragma option pop
// #pragma option push -w-inl
// /* TPropertyEditor.Destroy */ inline __fastcall virtual ~TMyImageIndexPropertyEditor(void) { }
// #pragma option pop
__published:
protected:
#pragma option push -w-inl
// inline __fastcall virtual TMyImageIndexPropertyEditor(const Designintf::_di_IDesigner ADesigner, int APropCount) : Designeditors::TIntegerProperty(ADesigner, APropCount) { }
#pragma option pop
public:
#pragma option push -w-inl
// inline __fastcall virtual ~TMyImageIndexPropertyEditor(void) { }
#pragma option pop
};
//---------------------------------------------------------------------------
#endif |
|
|
GIZMO |
Отправлено: 15.05.2005, 07:45 |
|
Машинист паровоза
Группа: Участник
Сообщений: 174
|
QUOTE (Rius @ 15/05/2005, 06:59) | Написал свой редактор, как правильно переопределить методы ListDrawValue, ListMeasureWidth, ListMeasureHeight? А то ничего не рисуется.
CODE |
...
TPropertyAttributes __fastcall TMyImageIndexPropertyEditor::GetAttributes()
{
return TPropertyAttributes() << paMultiSelect << paValueList << paRevertable;
}
...
|
|
А где paOwnerDrawList?
|
|
Rius |
Отправлено: 15.05.2005, 08:41 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
http://epsilon.narod.ru/rus/progr/delphi_comp1.html
QUOTE | ListDrawValue (const Value: string; Canvas: TCanvas; Rect: TRect; Selected: Boolean) — Рисует пункт в выпадающем списке — OwnerDraw чистой воды, но не верьте Help'у: никакого атрибута paOwnerDrawList в природе не бывает! |
и нигде нет определения такой константы.
|
|
GIZMO |
Отправлено: 15.05.2005, 12:49 |
|
Машинист паровоза
Группа: Участник
Сообщений: 174
|
QUOTE (Rius @ 15/05/2005, 08:41) | http://epsilon.narod.ru/rus/progr/delphi_comp1.html
QUOTE | ListDrawValue (const Value: string; Canvas: TCanvas; Rect: TRect; Selected: Boolean) — Рисует пункт в выпадающем списке — OwnerDraw чистой воды, но не верьте Help'у: никакого атрибута paOwnerDrawList в природе не бывает! |
и нигде нет определения такой константы. |
Да-а-а, вот это тема. Щас еще покопаюсь...
|
|
GIZMO |
Отправлено: 15.05.2005, 13:13 |
|
Машинист паровоза
Группа: Участник
Сообщений: 174
|
QUOTE (GIZMO @ 15/05/2005, 12:49) | Да-а-а, вот это тема. Щас еще покопаюсь... |
Че-то Я начинаю тупить(воскресенье на работе...), но попробуй объявить так:
CODE |
DYNAMIC void __fastcall ListMeasureWidth(const AnsiString Value, Graphics::TCanvas* ACanvas, int &AWidth
);
DYNAMIC void __fastcall ListDrawValue(const AnsiString Value, Graphics::TCanvas* ACanvas, const Windows::TRect
&ARect, bool ASelected);
DYNAMIC void __fastcall PropDrawValue(Graphics::TCanvas* ACanvas, const Windows::TRect &ARect, bool
ASelected);
|
|
|
Rius |
Отправлено: 15.05.2005, 14:06 |
|
Мастер участка
Группа: Участник
Сообщений: 321
|
И так пробовал и сяк пробовал, ничего не помогает. Т.к. у меня редактор сейчас основан на TCursorProperty, он мне курсоры и рисует в списке. Кстати, TRect у меня нашелся в namespace Types, а не в Windows.
В дельфях это работает типа через множественное наследование, а здесь как его объявить?
Сапоги для сапожника
|
|
|