Announcement

Collapse
No announcement yet.

eigene FindControl

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • eigene FindControl

    Hallo
    ich habe ein Function FindControl

    //************
    //Control finden
    function TfrmMain.FindControl(root_c : Control; name_s : String): Control;
    var
    ctrl : Control;
    begin
    for ctrl In root_c.Controls do
    begin
    FindControl(ctrl, name_s);
    if ctrl.name = name_s then
    begin
    Result := ctrl;
    end;
    end;
    end;
    //************

    wenn ich jetzt die function so aufrufe
    FindControl(Self, 'A_TextBox1').Text := '12';
    bekomme ich die Fehlermeldung
    "der Objektverweis wurde nicht auf eine Objektinstanz festgelegt"

    das Funktioniert
    FindControl(Self.TabControl1, 'A_TextBox1').Text := '12';

    auch das in der Function
    Result .text := '12';

    kann mir bitte jemand sagen wo der fehler liegt?

  • #2
    Hallo,
    das Problem liegt darin, dass unter NET die <u>Controls nicht direkt ins Formular</u> eingebunden sind, sondern in den verschiedenen Containern (z.B. TabControl1). Dies kannst Du untersuchen, indem Du die Methode <u>InitializeComponents()</u> - speziell die Add-Befehle - analysierst.

    Eine Methode wie Dein FindControl() muss <b>immer rekursiv</b> alle vorhandenen Container durchlaufen.

    Nebenbei: Bei Dir fehlen die Sicherungsmaßnahmen:
    * Result := nil;
    * if (FindControl) <> nil...

    Ich hoffe, es hilft Dir. Gruß Jürge

    Comment


    • #3
      Hallo
      Ich durchlaufe doch rekursiv

      //************
      //Control finden
      function TfrmMain.FindControl(root_c : Control; name_s : String): Control;
      var
      ctrl : Control;
      begin
      for ctrl In root_c.Controls do
      begin
      FindControl(ctrl, name_s); <<<<<<<<<<<<<<<<<<<<<<
      if ctrl.name = name_s then
      begin
      Result := ctrl;
      end;
      end;
      end;
      //************

      die control wird ja auch gefunde

      Comment


      • #4
        Au ja, Du hast recht. (Hier im Entwickler-Forum gibt es leider keine einfache Möglichkeit, Quellcode zu formatieren, anders als z.B. in http://www.delphipraxis.net; deshalb habe ich das übersehen.)

        Aber an dieser Stelle machst Du Deinen Fehler: Du willst ein Control als Rückgabewert nutzen und diesen prüfen; wenn Du in einem Container Dein Control nicht findest, musst Du nil nutzen. Also:

        function TfrmMain.FindControl(root_c : Control; name_s : String): Control;
        var temp, ctrl : Control;
        begin
        Result := nil;
        for temp In root_c.Controls do
        begin
        ctrl := FindControl(temp, name_s); // Zuweisung!!!
        if ctrl <> nil then
        begin
        if ctrl.name = name_s then
        begin
        Result := ctrl;
        break;
        end; // Ende if(ctrl.name = name_s)
        end; // Ende if(ctrl <> nil)
        end; // Ende for
        end; // Ende Functio

        Comment


        • #5
          <code>
          <b>function</b> TfrmMain.FindControl(root_c : Control; name_s : <b>String</b>): Control;
          <b>var</b>
          temp, ctrl : Control;
          <b>begin</b>
          Result := <b>nil</b>;
          <b>for</b> temp <b>In</b> root_c.Controls <b>do</b>
          <b>begin</b>
          ctrl := FindControl(temp, name_s); <font color="#003399"><i>// Zuweisung!!! </i></font>
          <b>if</b> ctrl &lt;&gt; <b>nil</b> <b>then</b>
          <b>begin</b>
          i f ctrl.name = name_s <b>then</b>
          <b>begin</b>
          Result := ctrl;
          break;
          <b>end</b>; <font color="#003399"><i>// Ende if(ctrl.name = name_s) </i></font>
          <b>end</b>; <font color="#003399"><i>// Ende if(ctrl &lt;&gt; nil) </i></font>
          <b>end</b>; <font color="#003399"><i>// Ende for </i></font>
          <b>end</b>; <font color="#003399"><i>// Ende Function </i></font>
          </code&gt

          Comment


          • #6
            Hallo,
            damit die Einrücktiefen erhalten bleiben, muss der Quelltext über das <b>&lt;pre&gt;</b>-Tag eingeklammert werden:

            <pre>
            <b>function</b> TfrmMain.FindControl(root_c : Control; name_s : <b>String</b>): Control;
            <b>var</b>
            temp, ctrl : Control;
            <b>begin</b>
            Result := <b>nil</b>;
            <b>for</b> temp <b>In</b> root_c.Controls <b>do</b>
            <b>begin</b>
            ctrl := FindControl(temp, name_s); <font color="#003399"><i>// Zuweisung!!! </i></font>
            <b>if</b> ctrl &lt;&gt; <b>nil</b> <b>then</b>
            <b>begin</b>
            i f ctrl.name = name_s <b>then</b>
            <b>begin</b>
            Result := ctrl;
            break;
            <b>end</b>; <font color="#003399"><i>// Ende if(ctrl.name = name_s) </i></font>
            <b>end</b>; <font color="#003399"><i>// Ende if(ctrl &lt;&gt; nil) </i></font>
            <b>end</b>; <font color="#003399"><i>// Ende for </i></font>
            <b>end</b>; <font color="#003399"><i>// Ende Function </i></font>
            </pre&gt

            Comment


            • #7
              Hallo Jürgen
              wenn ich deine Function so aufrufe
              FindControl(self, 'A_Textbox1').Text := '12';
              kommt der gleiche Fehler

              ausserdem kann ich kein unterschied zwischen
              for ctrl In root_c.Controls do
              begin
              FindControl(ctrl, name_s); <<<<<<<<<<<<<<<<<<<<<<

              und deiner
              for temp In root_c.Controls do
              begin
              ctrl := FindControl(temp, name_s); // Zuweisung!!!

              &#10

              Comment


              • #8
                Hallo Raimund,
                der entscheidende Unterschied ist folgender: Du übergibst das aktuelle ctrl Deiner for-Schleife an die <b>Funktion</b> und lässt mit dieser Funktion etwas machen, aber <u>das Ergebnis interessiert Dich überhaupt nicht!!!</u> (Dass es ein rekursiver Aufruf derselben Funktion ist, ist insofern unerheblich.)

                Tatsächlich interessiert Dich doch in der obersten Ebene der Funktionsaufrufe, <u>welches Control dem gegebenen Namen entspricht;</u> also musst Du dieses Control <b>nach der erfolgreichen Suche zuweisen</b> und von unten nach oben durchreichen.

                Das wollte ich mit dem Hinweis // Zuweisung!!! statt Deines Vermerks <<<< deutlich machen.

                Eine andere Art der Erklärung wäre: Delphi unterscheidet zwischen Funktion und Prozedur.

                War ich jetzt deutlich genug? Jürge

                Comment


                • #9
                  Hallo
                  jep, die Zuweisung war nicht richtig

                  <pre>
                  //Control finden
                  function FindControl(root_c : Control; name_s : String): Control;
                  var
                  parent : Control;
                  ctrl : Control;
                  begin
                  Result := NIL;
                  for parent In root_c.Controls do
                  begin
                  if parent.Name = name_s then
                  begin
                  Result := parent;
                  end
                  else
                  begin
                  ctrl := FindControl(parent, name_s);
                  if(ctrl <> NIL) then
                  begin
                  if ctrl.Name = name_s then
                  begin
                  Result := ctrl;
                  break;
                  end;
                  end;
                  end;
                  end;
                  end;
                  <pre>

                  und der Aufruf dann
                  (FindControl(self, mycontrol1) as TextBox).Width:= 120;

                  Danke für die Hilfe
                  Raimund

                  &#10

                  Comment

                  Working...
                  X