Announcement

Collapse
No announcement yet.

Extrem langsame Labels

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

  • Extrem langsame Labels

    Hallo,

    ich versuche gerade, ein VB6 Projekt in .NET(C#) umzusetzten.
    Dabei bin ich auf ein großes Problem gestossen, guckst du da:

    Code:
    namespace WindowsFormsApplication1
    {
      public partial class Form1 : Form
      {
        public Form1()
        {
          Label[] l = new Label[32*25];
          InitializeComponent();
          this.Width = 820;
          this.Height = 484;
          this.WindowState = FormWindowState.Maximized;
          this.BackgroundImage = new Bitmap(1680, 1050);
          for (int i = 0; i < 32; i++)
          {
            for (int j = 0; j < 25; j++)
            {
              int idx = i * 25 + j;
              l[idx] = new Label();
              l[idx].BackColor = Color.Transparent;
              l[idx].AutoSize = true;
              l[idx].Text = idx.ToString(" 0000");
              l[idx].Top = i * 14;
              l[idx].Left = j * 32;
            }
          }
          this.Controls.AddRange(l);
        }
      }
    }
    Die Ausführung(rendern) des Programmes dauert so ca 20-30 sec
    Zum Vergleich in VB6 ca 1 Mausklick. Faktor 10 000 - 100 000!!!

    Benötigt wird das Bitmap in Bildschirmgröße. In diesem Bitmap werden
    Punkte markiert (angeklickt) und mit den numerierten Labels gekennzeichnet.
    Diese müssen deshalb transparent sein, damit die Markierungsstelle und das
    Bitmap erkennbar bleiben. z.Z kann ich 10 Mauslicks setzen, und die Zahlen
    auf Papier schreiben, und bin damit schneller fertig als der 2GHz Pc unter .NET

    Weiß von Euch jemand. Rat
    Zuletzt editiert von jay-be; 28.04.2009, 20:14.

  • #2
    Warum zeichnest Du das nicht einfach alles im OnPaint Event handler eines Panels z.B.?

    Mit C# hat das garantiert nichts zu tun, weil am Ende derselbe Quelltext rauskommt wie auch bei VB.

    Du kannst auch mal Suspend/Resumelayout der Form aufrufen, damit wird verhindert, dass das ganze ständig neu gezeichnet wird.

    Comment


    • #3
      Hi, ich redete nicht von VB.Net sondern von VB6
      Klar, in VB.Net/C++.Net ist die Sache genauso langsam.
      Was ich nicht verstehe, in VB6 brauchen die 800 Labels grad mal 0.1 sec.
      Mit 1 sec wär ich schon glücklich, aber 100 000 mal langsamer als die
      Visual-Basic Vorgängerversion das kann man Kunden wohl kaum als
      Upgrade verkaufen!

      Mit Suspend/Resumelayout kommt man auch nicht weiter.

      Mit der Stopwatch gestoppt, ist der Code in ca 0.1 sec abgearbeitet,
      nur bis das Ergebnis auf dem Monitor ist hängt alles 20 sec. lang.

      Wenn das Form aus und in den Monitorbereich gezogen wird, ist der Code
      ja auch schon längst abgearbeitet, nur bis das Bild dann wieder gerendert
      ist vergeht wieder die gleiche Zeit.

      Comment


      • #4
        Rehi fanderlf,

        der Tip mit OnPaint ist gar nicht so schlecht, hab das jetzt mal ausprobiert,
        auch wenn ich mit der Thematik noch nicht so ganz firm bin, aber der Anfang
        lässt sich schon sehen.

        Die Nummer hab ich mit DrawString gezeichnet, das wird von vornherein transparent.
        Und das ganze geht auch recht schnell.

        Ein Problem bleibt aber noch. Oft trifft man die neuen Positionen mit der Maus nicht so
        genau, und ich musste die Labels per DragDrop verschieben, oder anklicken und löschen.
        Das werd ich nun wohl auch selber machen müssen :-(

        Wenn man nicht alles selber macht !!! :-)

        Trotzdem mal vielen Dank für den Tip, sieht echt vielversprechend aus.

        Einen hab ich noch:
        Das obige Beispielprogramm hab ich in VB, C# und C++ (.NET)umgesetzt, mit Labels und mit
        Buttons, alle mit dem gleichen Ergebnis. Labels und Buttons sind wohl die wichtigsten
        Grundelemente, da frage ich mich, was soll ich damit, wenn ich es letztendlich doch selber
        und anders machen muss? Selbst beim Splash-screen sieht es einfach sch.... aus, wenn erst
        für eine zehntel Sekunde 5 Löcher zu sehen sind, wo hinterher 5 Labels erscheinen (mit
        Betonung auf 5)
        Im IE krieg ich 50 Werbebanner mit animierter Grafik im Millisekundenbereich angezeigt,
        ohne Löcher?!?!

        Comment


        • #5
          Winforms ist langsam.
          Aber so schlecht ist Winforms dann doch nicht man muß nur wissen was man tut.

          a.) Hunderte von Controls (auch wenns nur Label sind) sind einfach zuviel. Jedes Control braucht einen eigenen Handle und die sind endlich und das Systemweit. Heißt wenn du damit rumhunst legst du letztlich nicht nur deinen Prozess lahm sondern den ganzen Rechner.

          b.) Winforms kann keine Transparenz. Die ist nur simuliert. Solange du also auf Transparenz verzichtest ist die Geschwindigkeit im Normalfall zumindest erträglich.

          c.) Der DOTNET Debugger ist eine Bremse probier die Geschwindigkeit insbesondere von Winforms auch mal ohne Debugger aus.

          d.) Winforms ist für klassische Businessanwendungen ausgelegt. Beschriftung von Grafiken (und damit die notwendige langsame Pseudotransparenz) ist da glaub ich eher unüblich. Du solltest dich fragen ob du nicht einfach das falsche Tool für dein Problem gewählt hast. Wie wärs mit WPF anstatt Winforms?

          Comment


          • #6
            Hallo Ralf,

            wie bereits weiter oben gesagt, ich hab angefangen, das Ganze im Paint Ereignis mit
            Drawstring unterzubringen. Das passt sich recht gut in die Anwendung ein und ist schnell.

            Dennoch muss ich mal dagegenhalten, das Projekt hat eine gewisse Tradition, angefangen
            als Clipperprogramm (ein Datenbanktool!), wurde dann in Visual Basic 6.0 umgesetzt. Damals
            auf 386er Rechnern mit Vesa Grafikkarte. Ich kann dir gern mal ein Programm mit 8000 statt
            NUR 800 Label zur verfügung stellen, interessant wird es da vielleicht bei 100 000 Labels.
            Ich weiß ja nicht, ob Du Dir mal das Beispielprogramm in der Ausführung angesehen hast?
            (als Exe noch langsamer als unter dem Debugger, da kommt noch 1-2 min Ladezeit dazu!)

            Dass man dann heutzutage mit 2,5GHz dual Core Rechnern und Hochleistungsgrafikkarten
            bei dem Wort "Hundert" in Angst und Schrecken verfällt ist doch wirklich mit nichts zu begründen.

            Ich hab das ganze hier im .NET forum gepostet, weil es nix mit VB, C# oder Cpp und auch nix
            mit dem Debugger zu tun hat, das ganze liegt irgendwie an .NET. Selbst das GDI scheidet
            aus, da wie gesagt mit Paint und DrwawString das ganze akzeptabel dargestellt werden
            kann.

            Rein rechnerisch sieht es so aus, als würde bei jedem Label das komplette Bitmap jeweils
            neu "geladen", obwohl nur einige Pixel geändert werden.

            Bei 800 Labels und 20 Frames/s kommen in etwa die 40 sec raus.

            => selbst bei NUR 20 Labels/Buttons/Controls 1 Sec! Das ist doch selbst für
            Bussinessanwendungen inakzeptabel.

            Deshalb ja meine Frage, ich hab immer das Gefühl etwas falsch gemacht zu haben,
            die Diskrepanz zu Win32 ist einfach zu krass.

            Comment


            • #7
              Nur mal nebenbei:

              In diesem PlugIn für die IDE Netbeans http://plugins.netbeans.org/PluginPo...pluginid=16235

              werden 999 Images geladen, auf 80 x 80 gebracht (ggf. transparent), und als Label dargestellt. Dauer 2 Sek.

              Da nun darunter auch WIN 32 liegt, wird es am Betriebssytem wohl nicht liegen........
              Christian

              Comment


              • #8
                Dass man dann heutzutage mit 2,5GHz dual Core Rechnern und Hochleistungsgrafikkarten bei dem Wort "Hundert" in Angst und Schrecken verfällt ist doch wirklich mit nichts zu begründen.
                Nicht ich zittere vor Angst, sondern Windows . Und die Aussage bezog sich nicht auf dein Performanceproblem sondern auf eventuellen Resourcenmangel durch die Art deiner Lösung. Je nach Betriebssystemversion und Einstellung hast du systemweit zwischen 10000 und 14000 GUI Handles zur Verfügung und danach bekommst du nur noch weiße Löcher wo Fenster sein sollten. Das wird also schnell eng wenn man mit Handles um sich schmeißt. Und übrigens du brauchst einen Handle per Devicecontext . Heißt in einem Dualmonitorsystem(nicht so selten) hast du deine verfügbaren Handles quasi nochmal halbiert.


                Ich hab das ganze hier im .NET forum gepostet, weil es nix mit VB, C# oder Cpp und auch nix mit dem Debugger zu tun hat, das ganze liegt irgendwie an .NET. Selbst das GDI scheidet aus, da wie gesagt mit Paint und DrwawString das ganze akzeptabel dargestellt werden kann.
                Wie von mir erwähnt es liegt an der Implementierung von Winforms. Der Managed Code um die systemeigenen CommonControls herum die Interop zwischen Managed Code und den unmanaged Common Controls machen ist langsam. Die CommonControls selbst sind ja im klassischen VB die selben wie in Winforms. Wenn dann noch Transparenz ins Spiel kommt ist man schnell beim Daumenkino.
                Für eine Businessanwendung reicht das meißt. Da geht es ja mehr um die Produktivität während der Entwicklung und nicht um das letzte % bei der Ausführung. Für das was du vor hast ist eine reine Winformslösung mit den entsprechenden Controls ungeeignet. Wenn du eine Lösung in .NET möchtest heißt das entweder selbstzeichnen oder WPF nehmen.

                Comment

                Working...
                X