Meu componente está com access violation (código no post)

Delphi

16/07/2009

Pessoal,

Estou estudando criação de componente. Quero criar um componente herdado da TDBEdit que terá 3 propriedades novas: Ligado, CorFonte e CorFundo. Quando ele estiver com Ligado = True o componente checará se a propriedade Required do Field do DataSet está True (ou seja, se é componente requerido). Se for requerido então ele automaticamente mudará as cores do componente das cores padrão para a cor das novas propriedades. Mas após escrever algum código e estudar bastante eu não consigo mais avançar... o componente é colocado no form mas quando rolo as propriedades (a lista mesmo) ele dá um monte de access violation. O que está errado? Segue abaixo código completo do que eu fiz:

unit DBEditRequerido;

interface

uses
  SysUtils, Classes, Controls, StdCtrls, Mask, DBCtrls, Graphics, Messages, DB;

type
  TDBEditRequerido = class(TDBEdit)
  private
    { Private declarations }
     FCorFundo : TColor;
     FCorFonte : TColor;
     FLigado: Boolean;
     FDataLink: TFieldDataLink;
     procedure AjustaCorFundo(Value: TColor);
     procedure AjustaCorFonte(Value: TColor);
     procedure AjustaLigado(Value: Boolean);
     procedure SetDataField(const Value: WideString);
     function GetDataField: WideString;
     procedure ResetMaxLength;
     procedure PerdeFoco(var Message: TCMExit); message CM_EXIT;
  protected
    { Protected declarations }
  public
    { Public declarations }
    constructor Create(AOwner: TComponent); override;
  published
    { Published declarations }
    property CorFundo : TColor  read FCorFundo  write AjustaCorFundo;
    property CorFonte : TColor  read FCorFonte  write AjustaCorFonte;
    property Ligado   : Boolean read FLigado write AjustaLigado;
    property DataField: WideString read GetDataField write SetDataField;
  end;

procedure Register;

implementation

procedure Register;
begin
   RegisterComponents(´Meus Componentes´, [TDBEditRequerido]);
end;

{ TDBEditRequerido }

procedure TDBEditRequerido.AjustaCorFundo(Value: TColor);
begin
   if (Value <> FCorFundo) then
   begin
      FCorFundo := Value;
      Self.Color := Value;
   end;
end;

function TDBEditRequerido.GetDataField: WideString;
begin
  Result := FDataLink.FieldName;
end;

procedure TDBEditRequerido.SetDataField(const Value: WideString);
begin
  if not (csDesigning in ComponentState) then
     ResetMaxLength;
  FDataLink.FieldName := Value;

  if Self.Field.Required Then
   begin
      FCorFundo := $00CACAFF;
      FCorFonte := clBlack;

      Self.Color := $00CACAFF;
      Self.Font.Color := clBlack;
   end;
end;

procedure TDBEditRequerido.ResetMaxLength;
var
  F: TField;
begin
  if (MaxLength > 0) and Assigned(DataSource) and Assigned(DataSource.DataSet) then
  begin
    F := DataSource.DataSet.FindField(DataField);
    if Assigned(F) and (F.DataType in [ftString, ftWideString]) and (F.Size = MaxLength) then
      MaxLength := 0;
  end;
end;

procedure TDBEditRequerido.AjustaLigado(Value: Boolean);
begin
   if (Value <> FLigado) then
   begin
      FLigado := Value;

      if Not FLigado then
      begin
         AjustaCorFundo(clWhite);
         AjustaCorFonte(clBlack);
      end else
      begin
         AjustaCorFundo(FCorFundo);
         AjustaCorFonte(FCorFonte);
      end;
   end;
end;

procedure TDBEditRequerido.AjustaCorFonte(Value: TColor);
begin
   if (Value <> FCorFonte) then
   begin
      FCorFonte := Value;
      Self.Font.Color := Value;
   end;
end;

procedure TDBEditRequerido.PerdeFoco(var Message: TCMExit);
begin

   If FLigado And Self.Field.Required Then
   begin
      if Trim(Self.Text) <> ´´ then
      begin
         FCorFundo := clWhite;
         FCorFonte := clBlack;

         Self.Color := clWhite;
         Self.Font.Color := clBlack;
      end else
      begin
         FCorFundo := $00CACAFF;
         FCorFonte := clBlack;

         Self.Color := $00CACAFF;
         Self.Font.Color := clBlack;
      end;
   end;
end;

constructor TDBEditRequerido.Create(AOwner: TComponent);
begin
   inherited Create(AOwner);

   FLigado := True;
   FCorFundo := $00CACAFF;
   FCorFonte := clBlack;
end;

end.


Pessoal, alguma sugestão/orientação? Sou novato ao extremo no assunto! Valeu!


Willian

Willian

Curtidas 0

Respostas

Osocram

Osocram

16/07/2009

olha...
eu acho que um dos problemas pode ser
property DataField: WideString read GetDataField write SetDataField;
pois o DBEdit ja tem essa property.


GOSTEI 0
Willian

Willian

16/07/2009

Boa observação. Vou pôr um [b:d7554f5578]override [/b:d7554f5578]na frente e ver o que acontece.

Valeu!


GOSTEI 0
Willian

Willian

16/07/2009

[i:2a9e7d92a0][b:2a9e7d92a0]Override [/b:2a9e7d92a0]não funciona pra propriedade... [/i:2a9e7d92a0]pelo menos aqui não foi....

Eu criei essa propriedade novamente para que assim que ela for configurada com o nome do Field o componente veja se ele é requerido ou não e aí ele decide se vai mudar as cores ou não.

Se tiver algum meio de não sobrepor essa propriedade mas receber algum evento dela assim que ela for ´setada´ também resolve meu problema. Alguma sugestão?


GOSTEI 0
Osocram

Osocram

16/07/2009

Faça o seguinte

pegue o metodo SetDataField e faça override dele...
pronto;

Espero que seja apenas esse o prob.
XD

[i:1ca6a4aebf][b:1ca6a4aebf]Override [/b:1ca6a4aebf]não funciona pra propriedade... [/i:1ca6a4aebf]pelo menos aqui não foi.... Eu criei essa propriedade novamente para que assim que ela for configurada com o nome do Field o componente veja se ele é requerido ou não e aí ele decide se vai mudar as cores ou não. Se tiver algum meio de não sobrepor essa propriedade mas receber algum evento dela assim que ela for ´setada´ também resolve meu problema. Alguma sugestão?



GOSTEI 0
Willian

Willian

16/07/2009

Esse método está no private do componente então ele fala durante a compilação que o método não foi encontrado na classe base.

Mais alguma idéia?


GOSTEI 0
Woinch

Woinch

16/07/2009

Não testei, mas experimente assim:

  published 
    { Published declarations } 
    property CorFundo : TColor  read FCorFundo  write AjustaCorFundo; 
    property CorFonte : TColor  read FCorFonte  write AjustaCorFonte; 
    property Ligado   : Boolean read FLigado write AjustaLigado; 
    property DataField; 



GOSTEI 0
Danielrsanches

Danielrsanches

16/07/2009

eu fiz algo parecido e está funcionando perfeitamente ...

quando o foco está no dbedit, mostra uma cor e quando sai, volta a cor padrão ...

unit dsDBEdit;

interface

uses
  SysUtils, Classes, Controls, StdCtrls, Mask, DBCtrls, Graphics, Dialogs;

type
  TdsDBEdit = class(TDBEdit)
  private
    { Private declarations }
    fAtivaFoco: Boolean;
    fCorFocado: TColor;
    fCorNaoFocado: TColor;
    fFontFocado: TFont;
    fFontNaoFocado: TFont;
//    procedure setFocoEnter(Sender: TObject);
    procedure setFocoEnter(var Message: TCMEnter);   message CM_ENTER;
    procedure setFontFocado(Valor: TFont);
    procedure setFocoExit(var Message: TCMExit);   message CM_EXIT;
  protected
    { Protected declarations }
  public
    { Public declarations }
    constructor create(AOwner: tcomponent); override;
    destructor destroy; override;
  published
    { Published declarations }
    property dsAtivaFoco: Boolean read fAtivaFoco write fAtivaFoco default True;
    property dsCorFocado: TColor read fCorFocado write fCorFocado;
    property dsFontFocado: TFont read fFontFocado write setFontFocado;
  end;

procedure Register;

implementation

constructor TdsDBEdit.Create(AOwner : TComponent);
begin
        inherited Create(AOwner);
        fAtivaFoco:= True;
        fCorFocado:= $00FF8080;
        fCorNaoFocado:= Self.Color;
        fFontFocado:= TFont.Create;
        fFontFocado.Assign(Font);
        fFontNaoFocado:= TFont.Create;
        fFontNaoFocado.Assign(Font);
end;

destructor TdsDBEdit.Destroy;
begin
        fFontFocado.Free;
        fFontNaoFocado.Free;
        inherited destroy;
end;

procedure TdsDBEdit.setFocoEnter(var Message: TCMEnter);
begin
        inherited;
        if fAtivaFoco = true then
        begin
                fCorNaoFocado:= Color;
                Color:= fCorFocado;
                fFontNaoFocado.Assign(Font);
                Font.Assign(fFontFocado);
        end;
end;

procedure TdsDBEdit.setFocoExit(var Message: TCMExit);
begin
        inherited;
        Color:= fCorNaoFocado;
        Font.Assign(fFontNaoFocado);
end;

procedure TdsDBEdit.setFontFocado(Valor: TFont);
begin
        fFontFocado.Assign(Valor);
end;

procedure Register;
begin
  RegisterComponents(´Daniel´, [TdsDBEdit]);
end;

end.



dá uma olhadinha pra ver se te ajuda em algo ...

abraços !!!


GOSTEI 0
POSTAR