Cómo doble búfer .RED de controles en un formulario?

¿Cómo puedo ajustar el protegido DoubleBuffered propiedad de los controles en un formulario que están sufriendo de parpadeo?

InformationsquelleAutor Ian Boyd | 2008-09-16

12 Kommentare

  1. 85

    He aquí una más genérica versión de Maniquí de la solución.

    Podemos utilizar la reflexión para llegar a la protegida DoubleBuffered de la propiedad y, a continuación, se puede establecer a verdadero.

    Nota: Usted debe pagar su desarrollador impuestos y no el uso de doble búfer si el usuario se ejecuta en una sesión de servicios de terminal (por ejemplo, de Escritorio Remoto) Este método helper no activarla si la persona se ejecuta en el escritorio remoto.

    public static void SetDoubleBuffered(System.Windows.Forms.Control c)
    {
       //Taxes: Remote Desktop Connection and painting
       //http://blogs.msdn.com/oldnewthing/archive/2006/01/03/508694.aspx
       if (System.Windows.Forms.SystemInformation.TerminalServerSession)
          return;
    
       System.Reflection.PropertyInfo aProp = 
             typeof(System.Windows.Forms.Control).GetProperty(
                   "DoubleBuffered", 
                   System.Reflection.BindingFlags.NonPublic | 
                   System.Reflection.BindingFlags.Instance);
    
       aProp.SetValue(c, true, null); 
    }
    • Divertido, me gustaría pensar que es aún más importante para doble búfer cuando la comunicación remota, de modo que se evite innecesariamente el envío de un montón de repaints sobre el alambre?
    • Es exactamente lo que no quieres. En una sesión de terminal en el sistema GDI puede enviar comandos (dibuja una línea aquí, dibujar círculo aquí, rellene aquí, etc). El doble búfer se logra mediante el dibujo todo en un mapa de bits y, a continuación, utilizando GDI para pintar tu formulario en su totalidad como un mapa de bits. El envío de un sin compresión de mapa de bits a través del cable es por TANTO más lento que el envío de la origianl comandos GDI.
    • No ayuda a prevenir el auto de un tamaño de cuadro de texto de un parpadeo en cambiar el tamaño de… De hecho nada de lo que he probado hasta ahora.
    • De no hacer nada. Mi cuadro de texto todavía parpadea como el infierno. Demasiado malo…
    • Eso es porque el Windows TEXTBOX de control de no obedece a ningún las leyes de la pintura.
    • Si usted necesita un búfer doble TextBox, el uso de un RichTextBox con DetectUrls establece en False. Si usted quiere que sea editable, tira el formato mediante el EM_SETCHARFORMAT y EM_SETPARAFORMAT los mensajes (código de ejemplo es aquí).

  2. 65

    De verificación este hilo

    Repetir el núcleo de la respuesta, puede activar la WS_EX_COMPOSITED estilo de la bandera en la ventana para obtener el formulario y todos sus controles de doble buffer. El estilo de la bandera está disponible desde XP. No hacer la pintura más rápido, pero toda la ventana se dibuja en un búfer de pantalla y blitted a la pantalla en un solo golpe. Hacer que se vea instante a los ojos del usuario, sin visibles pintura artefactos. No está del todo libre de problemas, algunos de los estilos visuales de los representadores, puede glitch en él, particularmente TabControl cuando tiene muchas pestañas. YMMV.

    Pegar este código en la clase de formulario:

    protected override CreateParams CreateParams {
        get {
            var cp = base.CreateParams;
            cp.ExStyle |= 0x02000000;    //Turn on WS_EX_COMPOSITED
            return cp;
        } 
    }

    La gran diferencia entre esta técnica y Winform del doble búfer de apoyo es que Winform la versión sólo funciona en un control en tiempo. Usted todavía podrá ver cada control individual de pintura en sí. Que puede parecer como un efecto de parpadeo y, en particular, si la no pintada de control rectángulo contrasta gravemente con la ventana del fondo.

  3. 18
    System.Reflection.PropertyInfo aProp = typeof(System.Windows.Forms.Control)
        .GetProperty("DoubleBuffered", System.Reflection.BindingFlags.NonPublic |
        System.Reflection.BindingFlags.Instance);
    aProp.SetValue(ListView1, true, null);

    Ian tiene algo más de información sobre el uso de este en un servidor de terminal server.

    • Realmente no es para en un servidor de terminal server, ya que ninguno de mis clientes ejecutar el software desde una sesión de escritorio remoto. Pero usted debe pagar su desarrollador impuestos, y yo no quiero poner el código que no ya incluyen los impuestos.
  4. 12
    public void EnableDoubleBuffering()
    {
       this.SetStyle(ControlStyles.DoubleBuffer | 
          ControlStyles.UserPaint | 
          ControlStyles.AllPaintingInWmPaint,
          true);
       this.UpdateStyles();
    }
  5. 8

    Es una manera de extender el control específico que desee a doble búfer y establecer el DoubleBuffered propiedad dentro del control del cto r.

    Por ejemplo:

    class Foo : Panel
    {
        public Foo() { DoubleBuffered = true; }
    }
    • Estoy trabajando con una dibujado por el propietario ListView en una clase derivada. Ya esta resuelto el problema a la perfección!
    • Estoy que no sé es si hay inconvenientes, pero esto funcionó a la perfección. Mi costumbre de control previamente heredado de «Control», y acabo de cambiar a heredar de «Panel», y establecer DoubleBuffered a la verdad. Una de dos cambio de línea. El movimiento es suave… y la velocidad para dibujar una sola actualización parece mucho más rápido.
  6. 5

    nobugz obtiene el crédito por el método en su enlace, estoy sólo reenvío. Agregar este reemplazo a la Forma:

    protected override CreateParams CreateParams
    {
        get
        {
            CreateParams cp = base.CreateParams;
            cp.ExStyle |= 0x02000000;
            return cp;
        }
    }

    Esta funcionado mejor para mí, en Windows 7 me estaba poniendo grandes bloques negros que aparecen cuando se cambia el tamaño de un control de forma pesada. El control ahora de rebote en su lugar! Pero es mejor.

    • Este es el mismo que @Hans Pasante de la respuesta, pero +1 para poner el código aquí.
    • Estoy nobugz, el nick que he usado de nuevo en los foros de MSDN.
  7. 5

    Método de extensión a su vez el doble búfer en o fuera de los controles de

    public static class ControlExtentions
    {
        ///<summary>
        ///Turn on or off control double buffering (Dirty hack!)
        ///</summary>
        ///<param name="control">Control to operate</param>
        ///<param name="setting">true to turn on double buffering</param>
        public static void MakeDoubleBuffered(this Control control, bool setting)
        {
            Type controlType = control.GetType();
            PropertyInfo pi = controlType.GetProperty("DoubleBuffered", BindingFlags.Instance | BindingFlags.NonPublic);
            pi.SetValue(control, setting, null);
        }
    }

    Utilización (por ejemplo, cómo hacer DataGridView DoubleBuffered):

    DataGridView _grid = new DataGridView();
    // ...
    _grid.MakeDoubleBuffered(true);
  8. 4

    Antes de intentar el doble búfer, a ver si SuspendLayout()/ResumeLayout() a resolver su problema.

    • Suspender/ResumeLayout no resuelve el problema de parpadeo cuando la pintura.
  9. 4

    Esto me causó una mucho de pena por dos días con un tercero de control hasta que relacionarlo.

    protected override CreateParams CreateParams
    {
        get
        {
            CreateParams cp = base.CreateParams;
            cp.ExStyle |= 0x02000000;
            return cp;
        }
    }

    Recientemente he tenido un montón de agujeros (excrementos) cuando el cambio de tamaño /redibujando un control que contiene varios otros controles.

    Traté de WS_EX_COMPOSITED y WM_SETREDRAW pero nada funcionó hasta que he usado esta:

    private void myPanel_SizeChanged(object sender, EventArgs e)
    {
         Application.DoEvents();
    }

    Sólo quería pasar.

  10. 2

    vb.net la versión de esta excelente solución….:

    Protected Overrides ReadOnly Property CreateParams() As CreateParams
        Get
            Dim cp As CreateParams = MyBase.CreateParams
            cp.ExStyle = cp.ExStyle Or &H2000000
            Return cp
        End Get
    End Property
  11. 1

    También puede heredar los controles en sus propias clases, y se establece la propiedad allí. Este método también es bueno si usted tiende a estar haciendo un montón de configurar que es el mismo en todos los controles.

  12. 0

    He encontrado que simplemente establecer el DoubleBuffered ajuste en el formulario establece automáticamente todas las propiedades enumeradas aquí.

    • sí, lo sé… he perdido ese código y no he sido capaz de encontrar en ningún otro lugar en t’internet… lo siento!

Kommentieren Sie den Artikel

Bitte geben Sie Ihren Kommentar ein!
Bitte geben Sie hier Ihren Namen ein

Pruebas en línea