Pregunta

¿Cómo puedo configurar el protegido? DoubleBuffered ¿Propiedad de los controles en un formulario que sufre parpadeo?

¿Fue útil?

Solución

Aquí hay una versión más genérica de La solución del muñeco.

Podemos usar la reflexión para llegar a lo protegido. Doble buffer propiedad, y luego se puede establecer en verdadero.

Nota:Debería paga tus impuestos de desarrollador y no use doble almacenamiento en búfer si el usuario se está ejecutando en una sesión de servicios de terminal (p.ej.Escritorio remoto) Este método auxiliar no activará el doble almacenamiento en búfer si la persona está ejecutando en un 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); 
}

Otros consejos

Controlar este hilo

Repitiendo el núcleo de esa respuesta, puede activar el indicador de estilo WS_EX_COMPOSITED en la ventana para que tanto el formulario como todos sus controles tengan doble búfer.La bandera de estilo está disponible desde XP.No hace que pintar sea más rápido, pero toda la ventana se dibuja en un búfer fuera de la pantalla y se muestra en la pantalla de un solo golpe.Haciendo que parezca instantáneo a los ojos del usuario sin artefactos de pintura visibles.No está completamente libre de problemas, algunos renderizadores de estilos visuales pueden fallar, particularmente TabControl cuando tiene demasiadas pestañas.YMMV.

Pegue este código en su 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 el soporte de doble buffer de Winform es que la versión de Winform sólo funciona en un control a la vez.Aún verás que cada control individual se pinta.Lo que también puede parecer un efecto de parpadeo, especialmente si el rectángulo de control sin pintar contrasta mal con el fondo de la ventana.

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 más información sobre el uso de esto en un servidor terminal.

public void EnableDoubleBuffering()
{
   this.SetStyle(ControlStyles.DoubleBuffer | 
      ControlStyles.UserPaint | 
      ControlStyles.AllPaintingInWmPaint,
      true);
   this.UpdateStyles();
}

Una forma es extender el control específico que desea duplicar el búfer y establecer la propiedad DoubleBuffered dentro del ctor del control.

Por ejemplo:

class Foo : Panel
{
    public Foo() { DoubleBuffered = true; }
}

nobugz obtiene el crédito por el método en su enlace, solo estoy volviendo a publicar.Agregue esta anulación al formulario:

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

Esto funcionó mejor para mí, en Windows 7 aparecían grandes bloques negros cuando cambiaba el tamaño de un formulario de control pesado.¡El control ahora rebota!Pero es mejor.

Método de extensión para activar o desactivar el doble buffer para los controles

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);
    }
}

Uso (por ejemplo, cómo hacer que DataGridView sea DoubleBuffered):

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

Antes de intentar el doble buffer, vea si SuspendLayout()/ResumeLayout() resuelve su problema.

Esto me causó un lote de duelo durante dos días con el control de un tercero hasta que lo localicé.

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

Recientemente tuve muchos agujeros (excrementos) al cambiar el tamaño/redibujar un control que contiene varios otros controles.

Probé WS_EX_COMPOSITED y WM_SETREDRAW pero nada funcionó hasta que usé esto:

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

Sólo quería transmitirlo.

Versión vb.net 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

También puede heredar los controles en sus propias clases y establecer la propiedad allí.Este método también es bueno si tiendes a realizar muchas configuraciones que son iguales en todos los controles.

Descubrí que simplemente configurar la configuración DoubleBuffered en el formulario establece automáticamente todas las propiedades enumeradas aquí.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top