Autor |
Beitrag |
Peter18
      
Beiträge: 489
Erhaltene Danke: 2
Delphi4
|
Verfasst: Di 14.08.12 10:33
Ein freundliches Hallo an alle,
leider habe ich im Forum keine Lösung gefunden, daher folgendes Problem:
Ich verwende Delphi 4 und erzeuge neue Komponenten. Bisher lief es gut.
Die Basis meiner Komponente ist TPanel. Darauf werden verschiedene andere Komponenten wie Label Combobox, Panel u.s.w arangiert. Als ich nun TRadioGroup erzeugen wollte erhielt ich bei
Delphi-Quelltext 1:
| "oNewTerm.Items.Add( 'Dauer' );" |
die Fehlermeldung. Parent wird jedoch zugewiesen.
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13:
| constructor T_TagesListe.Create( Owner: TComponent ); var R, C : Integer;
begin inherited Create( Owner ); inherited Parent := TWinControl( Owner ); . . . oNewTerm := TRadioGroup.Create( Self ); oNewTerm.Parent := Self; oNewTerm.Items.Add( 'Dauer' ); |
Es scheint ein besonderer Type Parent notwendig zu sein. Doch welcher und warum? Wenn ich TWinControl( Owner ); zuweise erhalte ich die gleiche Meldung.
Ich hoffe jemand hat einen heißen Tip auf Lager.
Grüße von der sonnigen Nordsee
Peter
|
|
rd3
Ehemaliges Mitglied
Erhaltene Danke: 1
|
Verfasst: Di 14.08.12 15:38
ExtCtrls in der uses List? (für TRadioGroup)
//Edit: blöd, dann würde es ja sowieso nicht gehen...
|
|
jaenicke
      
Beiträge: 19312
Erhaltene Danke: 1747
W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
|
Verfasst: Di 14.08.12 16:41
Zu dem Zeitpunkt ist das Fensterhandle schlicht noch nicht erzeugt, deshalb geht das so nicht.
Wie wäre es mit einem Frame statt dem Panel? Dann kannst du das visuell designen und dann aufs Formular legen wie eine Komponente.
|
|
Martok
      
Beiträge: 3661
Erhaltene Danke: 604
Win 8.1, Win 10 x64
Pascal: Lazarus Snapshot, Delphi 7,2007; PHP, JS: WebStorm
|
Verfasst: Mi 15.08.12 20:51
jaenicke hat folgendes geschrieben : | Zu dem Zeitpunkt ist das Fensterhandle schlicht noch nicht erzeugt, deshalb geht das so nicht.  |
Dann würde aber das vorher auch nicht gehen. AFAIR wird wenn man Parent zuweist das solange zurückgehalten bis mal jemand HandleNeeded aufruft.
jaenicke hat folgendes geschrieben : | Wie wäre es mit einem Frame statt dem Panel? Dann kannst du das visuell designen und dann aufs Formular legen wie eine Komponente. |
Delphi 4, vor 14 Jahren gabs sowas noch nicht.
2 Sachen: welcher Fehler tritt denn auf? Fehler!!! ist eine Null-Aussage. /€: oh, steht ja im Thementitel. Da hab ich nicht gesucht
Außerdem: teste das mal so, in D7 funktioniert das.
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31:
| TFoo = class(TPanel) private FRG: TRadioGroup; public constructor Create(AOwner: TComponent); override; end;
constructor TFoo.Create(AOwner: TComponent); begin inherited; Parent:= TWinControl(AOwner); Width:= 300; Height:= 300;
FRG:= TRadioGroup.Create(Self); FRG.Parent:= Self; FRG.Align:= alClient; FRG.Caption:= 'testgroup'; FRG.Items.Add('Check 1'); FRG.Items.Add('Check 2'); FRG.Items.Add('Check 3'); end;
procedure TForm1.Button1Click(Sender: TObject); begin TFoo.Create(Self); end; |
_________________ "The phoenix's price isn't inevitable. It's not part of some deep balance built into the universe. It's just the parts of the game where you haven't figured out yet how to cheat."
|
|
jaenicke
      
Beiträge: 19312
Erhaltene Danke: 1747
W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
|
Verfasst: Mi 15.08.12 21:42
|
|
Peter18 
      
Beiträge: 489
Erhaltene Danke: 2
Delphi4
|
Verfasst: So 26.08.12 11:24
Ein freundliches Hallo von der verregneten Nordsee,
Dank euch für die Antworten, und entschuldigt meine späte Reaktion, war außer Haus.
Zwischendurch hatte ich einen workaround mit den Radiobutton erstellt. Da die Radiogroup sowieso zunächst unsichtbar sein soll, kann ich in diesem Fall beim sichtbar Schalten der Radiogroup die Länge der Item-Liste prüfen und sie dann hinzufügen. Damit wäre das Problem gelöst.
Ich habe aber ein weiteres Problem, das eventuell die gleiche Ursache hat:
Die Basis ist auch hier ein Panel. Im constructor wird eine Routine aufgerufen, die einen Rahmen um ein Label zeichnet, um es hervorzuheben. Wärend der Laufzeit wird die Markierung gelöscht und ein anderes Element markiert. Wenn das Formular aufgebaut wurde fehlt die Markierung, wechselt die Markierung jedoch auf ein anderes Element, so ist sie sichtbar. Die Markierung wird durch properties gesteuert, die im constructor des Panels gesetzt werden. Sie später durch einen Button zu aktivieren ist nicht sinnvoll, das muß automatisch gehen!
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23:
| procedure T_Monat_Kalender.PaintRect; var R, C : Integer;
begin if oTag > 0 then begin GetTagIndex( R, C, oTag ); Self.Canvas.Pen.Width := 2; Self.Canvas.Pen.Color := clBlack; Self.Canvas.MoveTo( C * CellWidth + 9, R * CellHeight + PTo - 1 ); Self.Canvas.LineTo( C * CellWidth + CellWidth + 9, R * CellHeight + PTo-1); Self.Canvas.LineTo( C * CellWidth + CellWidth + 9, R * CellHeight + CellHeight + PTo-1); Self.Canvas.LineTo( C * CellWidth + 9, R * CellHeight + CellHeight + PTo-1); Self.Canvas.LineTo( C * CellWidth + 9, R * CellHeight + PTo - 1 ); oRectR := R; oRectC := C; end; end;
|
Der Versuch das Problem durch ein Objekt zu beheben, führte dazu, dass beim Beenden der Anwendung die Fehlermeldung "Element hat kein übergeordnetes Fenster" erscheint. Kommentiere ich dieses Objekt heraus, so erscheint die Meldung nicht. Das Objekt erscheint auch nicht auf dem Panel.
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58:
| T_Rect = class(TGraphicControl)
private oTop : Integer; oLeft : Integer; oHeight : Integer; oWidth : Integer; oColor : TColor; oBackgr : TColor; oLine : Integer; oParent : TWinControl;
procedure WriteTop ( I : Integer ); procedure WriteLeft ( I : Integer ); procedure WriteHeight ( I : Integer ); procedure WriteWidth ( I : Integer ); procedure WriteColor ( C : TColor ); procedure WriteBackgr ( C : TColor ); procedure WriteLine ( I : Integer ); procedure WriteParent ( P : TWinControl );
public constructor Create( Owner: TComponent ); override; destructor Destroy; override; procedure Paint; override;
published property Top : Integer Read oTop Write WriteTop; property Left : Integer Read oLeft Write WriteLeft; property Height : Integer Read oHeight Write WriteHeight; property Width : Integer Read oWidth Write WriteWidth; property Color : TColor Read oColor Write WriteColor; property Backgr : TColor Read oBackgr Write WriteBackgr; property Line : Integer Read oLine Write WriteLine; property Parent : TWinControl Read oParent Write WriteParent;
procedure Clr;
end;
constructor T_Rect.Create( Owner: TComponent ); begin inherited Create( Owner ); Owner.InsertComponent( Self ); oTop := 0; oLeft := 0; oHeight := 10; oWidth := 10; oColor := clBlack; oBackgr := clBtnFace; oLine := 1; end;
|
Zur Laufzeit wird keine Fehlermeldung ausgegeben, auch beim Wechsel der Markierungen nicht, nur beim Beenden der Anwendung.
Wäre schön, wenn jemand eine Erklärung hätte, eine Lösung wär phantastisch!
Freundliche Grüße an alle
Peter
|
|
mandras
      
Beiträge: 431
Erhaltene Danke: 107
Win 10
Delphi 6 Prof, Delphi 10.4 Prof
|
Verfasst: So 26.08.12 15:36
Versuch doch mal beim Create das Formular anzugeben, nicht die übergeordnete Komponente.
Ich habe Dein Programm nicht getestet, normalerweise sollte der Owner immer die jeweilige Form sein und Parent die übergeordnete Komponente.
|
|
jaenicke
      
Beiträge: 19312
Erhaltene Danke: 1747
W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
|
Verfasst: So 26.08.12 16:06
Ich frage mich gerade, warum du versuchst die Komponente doppelt dem Owner hinzuzufügen (einmal im geerbten Konstruktor und einmal mit InsertComponent)?
Ich nehme zwar an, dass InsertComponent prüft, ob die Komponente schon drin ist, aber wenn nicht, knallt das beim Freigeben logischerweise...
Ein Beispielprogramm wäre hier sehr hilfreich, denn so lässt sich das nicht so einfach nachvollziehen.
|
|
Peter18 
      
Beiträge: 489
Erhaltene Danke: 2
Delphi4
|
Verfasst: So 26.08.12 17:51
Hallo mandras, hallo jaenicke,
Danke für Eure Antworten.
Mit dem Formular klappt das leiter nicht. Das Panel, das T_Rect erzeugt ist wiederum ein Objekt eines Panels, das mehrere andere trägt. Dieses Panel Basis-Panel wird vom Formular erzeugt.
InsertComponent war nur ein Versuch, da das Rechteck nicht sichtbar wurde und beim Schließen der Anwendung die bekannte Fehlermeldung erschien.
Hier ist das Objekt:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69: 70: 71: 72: 73: 74: 75: 76: 77: 78: 79: 80: 81: 82: 83: 84: 85: 86: 87: 88: 89: 90: 91: 92: 93: 94: 95: 96: 97: 98: 99: 100: 101: 102: 103: 104: 105: 106: 107: 108: 109: 110: 111: 112: 113: 114: 115: 116: 117: 118: 119: 120: 121: 122: 123: 124: 125: 126: 127: 128: 129: 130: 131:
|
procedure T_Rect.Draw; begin Self.Canvas.MoveTo( oTop, oLeft ); Self.Canvas.LineTo( oTop, oLeft + oWidth ); Self.Canvas.LineTo( oTop + oHeight, oLeft + oWidth ); Self.Canvas.LineTo( oTop + oHeight, oLeft ); Self.Canvas.LineTo( oTop, oLeft ); end;
procedure T_Rect.WriteTop( I : Integer ); begin oTop := I; end;
procedure T_Rect.WriteLeft( I : Integer ); begin oLeft := I; end;
procedure T_Rect.WriteHeight( I : Integer ); begin oHeight := I; end;
procedure T_Rect.WriteWidth( I : Integer ); begin oWidth := I; end;
procedure T_Rect.WriteColor( C : TColor ); begin oColor := C; end;
procedure T_Rect.WriteBackgr( C : TColor ); begin oBackgr := C; end;
procedure T_Rect.WriteLine( I : Integer ); begin oLine := I; end;
procedure T_Rect.WriteParent( P : TWinControl ); begin oParent := P; inherited Parent := P; end;
procedure T_Rect.Paint; begin Self.Canvas.Pen.Width := oLine; Self.Canvas.Pen.Color := oColor; Draw; end;
procedure T_Rect.Clr; begin Self.Canvas.Pen.Width := oLine; Self.Canvas.Pen.Color := oBackgr; Draw; end;
constructor T_Rect.Create( Owner: TComponent ); begin inherited Create( Owner ); oTop := 0; oLeft := 0; oHeight := 10; oWidth := 10; oColor := clBlack; oBackgr := clBtnFace; oLine := 1; end;
destructor T_Rect.Destroy; begin Clr; inherited Destroy; end; |
Das ist der Code im constructor des übergeordneten Panels:
Delphi-Quelltext 1: 2: 3: 4: 5:
| oMark := T_Rect.Create( Owner ); oMark.Parent := Self; oMark.Height := CellHeightMin; oMark.Width := CellWidthMin; oMark.Line := 2; |
Und das ist der Teil, wenn das Rechteck gezeichnet werden soll:
Delphi-Quelltext 1: 2: 3:
| oMark.Top := R * CellWidth + 9; oMark.Left := C * CellHeight + PTo - 1; oMark.Paint; |
Grüße von der Nordsee
Peter
|
|
Peter18 
      
Beiträge: 489
Erhaltene Danke: 2
Delphi4
|
Verfasst: Do 06.09.12 18:00
Ein freudliches Hallo an alle,
schade, dass mir niemand sagen kann, warum die Fehlermeldung kommt. Irgend etwas muß da doch noch fehlen.
Habe das Problem erst ein mal kaschiert, und im Formular OnPaint die Property neu gesetzt. Damit erscheint der Rahmen. Unschön aber geht.
Grüße von der Nordsee
Peter
Zuletzt bearbeitet von Peter18 am Fr 12.02.16 15:54, insgesamt 1-mal bearbeitet
|
|
mandras
      
Beiträge: 431
Erhaltene Danke: 107
Win 10
Delphi 6 Prof, Delphi 10.4 Prof
|
Verfasst: Do 06.09.12 19:13
Setz doch bitte einmal einen Quelltext hier ein den man ohne überarbeiten übersetzen kann
|
|
|