StringGrid und Grafik



  • Moin,
    ich möchte ein 1000x1000 Feld große StringGrid verwenden. Zeile/Spalte 0 hab ich beschriftet und von einer Imagelist lass ich ein Elemnt zeichnen.

    ImageList1->Draw(sgMap->Canvas,10,10,0,true);
    

    Das klappt alles wunderbar und so könnte ich auch eine 2D-Map darstellen, allerdings wenn man ein Grid anwählt, verschwindet die Grafik, genauso, wenn ich scrolle. Gibt es eine Möglichkeit, die Grafiken permanent mit dem Grid zu verankern, dass die nicht (durch Usergeklicke) verschwinden?

    Florian



  • Benutze das OnDrawCell-Ereignis, dann brauchst du dich auch nicht mehr extra um die Koordinaten zu kümmern.



  • hmm... also ich hab jetzt das OnDrawCell-Ereignis verwendet und auch ein DrawGris, statt eines Stringgrids, aber das Problem besteht weiter hin. Nur das mit dem Klicken und Verschwinden ist gelöst. Klickt man allerdings auf die Bildlaufleiste, so stimmt die Zeichnung wieder nicht.
    Feld [1,1] soll ein Hügel-bmp bekommen.
    Feld [1,2] soll ein Feld-bmp bekommen.
    Feld [2,1] soll ein Berg-bmp bekommen.
    Feld [2,2] soll ein Wasser-bmp bekommen.

    Solange alles auf einem Ausschnitt liegt, klappt es. nur wenn auf 10,10 wieder ein Hügel liegt, ich aber nur 1-5 seh und zu 10,10 scrolle, taucht der net auf... wieso net? Er wurde doch vorher definiert, dass er an 10,10 erscheinen soll...

    Noch was: Wie kann ich auch nem DrawGrid nen Text ausgeben?

    EDIT: Net, dass wir an einander vorbei reden. Also das Grid soll eine 2D-Map darstellen, bestehend aus glaub 8 verschiedenen Grafiken, die so eine ganze Map ergeben. Sie muss scrollbar sein, und die Felder müssen Informationen anzeigen. (also wenn ich entweder auf 10,10 klick oder mit der Maus drüber fahr, sollen Infos am Rand oder so erscheinen) Die Datenbank, die da hinter is, is schon fertig. Es geht eigentlich nur noch darum, dass man die db graphisch darstellen kann.



  • Zeig doch mal deinen OnDrawCell-Code.



  • ok, ich muss zugeben, des is jetzt ein bissl chaotisch, aber ich teste überall grad rum, wie ich des denn machen könnt...

    void __fastcall TmfMain::DrawGrid1DrawCell(TObject *Sender, int ACol,
          int ARow, TRect &Rect, TGridDrawState State)
    {
      long index = ARow * DrawGrid1->ColCount + ACol;
      DrawGrid1->Canvas->Brush->Color = clBackground;
      DrawGrid1->Canvas->FillRect(Rect);
    int x = 14;
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+10*x,DrawGrid1->TopRow+10*x,2,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+11*x,DrawGrid1->TopRow+10*x,1,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+12*x,DrawGrid1->TopRow+10*x,0,true);
    
    /*
    ImageList1->Draw(DrawGrid1->Canvas,187*x,260*x,0,true);
    ImageList1->Draw(DrawGrid1->Canvas,187*x,261*x,2,true);
    ImageList1->Draw(DrawGrid1->Canvas,187*x,262*x,2,true);
    ImageList1->Draw(DrawGrid1->Canvas,186*x,260*x,2,true);
    ImageList1->Draw(DrawGrid1->Canvas,185*x,260*x,2,true);
    ImageList1->Draw(DrawGrid1->Canvas,184*x,260*x,2,true);
    ImageList1->Draw(DrawGrid1->Canvas,186*x,259*x,2,true);
    */
      if (State.Contains(gdFocused))
        DrawGrid1->Canvas->DrawFocusRect(Rect);
    DrawGrid1->Canvas->Refresh();
    }
    //---------------------------------------------------------------------------
    void __fastcall TmfMain::DrawGrid1MouseMove(TObject *Sender,
          TShiftState Shift, int X, int Y)
    {
    int x = 14;
      Label2->Caption = "X: "+IntToStr(X/x)+"Y: "+IntToStr(Y/x);
    }
    //---------------------------------------------------------------------------
    
    void __fastcall TmfMain::DrawGrid1Click(TObject *Sender)
    {
    int x = DrawGrid1->Col;
    Label3->Caption = IntToStr(x);
    int y = DrawGrid1->Row;
    Label4->Caption = DrawGrid1->TopRow;// >LeftCol;//IntToStr(y);
    x=21;
    ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->Col*x,DrawGrid1->Row*x,2,true);
    }
    //---------------------------------------------------------------------------
    
    void __fastcall TmfMain::FormCreate(TObject *Sender)
    {
    int x;
    x = 21;
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+10*x,DrawGrid1->TopRow+10*x,2,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+11*x,DrawGrid1->TopRow+10*x,1,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+12*x,DrawGrid1->TopRow+10*x,0,true);
    DrawGrid1->Canvas->Refresh();
    
    }
    //---------------------------------------------------------------------------
    
    void __fastcall TmfMain::DrawGrid1TopLeftChanged(TObject *Sender)
    {
    int x = 21;
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+10*x,DrawGrid1->TopRow+10*x,2,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+11*x,DrawGrid1->TopRow+10*x,1,true);
      ImageList1->Draw(DrawGrid1->Canvas,DrawGrid1->LeftCol+12*x,DrawGrid1->TopRow+10*x,0,true);
    DrawGrid1->Canvas->Refresh();
    
    }
    //---------------------------------------------------------------------------
    

    Edit: Code-Tags korrigiert.
    -jansen



  • D betreibst viel zu viel Aufwand.
    Das Schöne an OnDrawCell ist, dass es selbst dafür sorgt, dass immer dann gezeichnet wird, wenn es notwendig ist. Du brauchst dir also keine Gedanken zu machen, welcher Ausschnitt des Grids gerade zu sehen ist.

    //---------------------------------------------------------------------------
    void __fastcall TForm1::DrawGrid1DrawCell(TObject *Sender, int ACol,
          int ARow, TRect &Rect, TGridDrawState State)
    {
      // Bild in Zelle zeichnen
      if (ARow >= DrawGrid1->FixedRows && ACol >= DrawGrid1->FixedCols)
        ImageList1->Draw(DrawGrid1->Canvas, Rect.left, Rect.top, ACol, true);
    
      // ggf. Rahmen zeichnen
      if (State.Contains(gdFocused))
      {
        Rect.top++;  // Rahmen verkleinern, dadurch besser bzw. überhaupt sichtbar
        Rect.left++;
        Rect.bottom--;
        Rect.right--;
        DrawGrid1->Canvas->DrawFocusRect(Rect);
      }
    
      // Text ausgeben
      String cell = String(ACol) + "/" + String(ARow);
      DrawText(DrawGrid1->Canvas->Handle, cell.c_str(), -1, &Rect, DT_SINGLELINE);
    }
    //---------------------------------------------------------------------------
    void __fastcall TForm1::DrawGrid1MouseMove(TObject *Sender,
          TShiftState Shift, int X, int Y)
    {
      int x, y;
      DrawGrid1->MouseToCell(X, Y, x, y);
      Caption = String(x) + "/" + String(y);
    }
    //---------------------------------------------------------------------------
    

    OnDrawCell ist die einzige Stelle, an der gezeichnet wird. Alles, was da noch feht ist die Logik, welches Bild aus der Liste jeweils in die aktuelle Zelle gezeichnet werden soll.



  • leider konnt ich net früher online gehn (Netzausfall), aber thx für den Code... ich hab an der ein und andren Stelle noch kleine Anpassungen vorgenommen... ich bin fasziniert... eine Lösung, die das Problem, schnell, sauber und vorallem läuffähig löst! ;)) Und ich hab schon so viel probiert.... Ich sollte echt weniger auf meine Informatiklehrer hören und mir net immer so viele Gedanken machen 😉


Log in to reply