Co powoduje zawieszenie systemu Windows w tej aplikacji WPF Ribbon

Mieliśmy kilka problemów z dość dużą i złożoną aplikacją komputerową, w której użycie Microsoft Ribbon dla WPF (lub kombinacji z tym związanych) powoduje zawieszenie komputera.

Poniższy sprowadzony kod wydaje się powodować sytuację zawieszania się systemu Windows na wielu komputerach. Niektóre komputery doświadczają tego zawieszenia za każdym razem, niektóre nigdy go nie doświadczą. Zawieszenie będzie na pewnym komputerze zablokować całą sesję (w tym num lock i caps lock), ale na innych mysz nadal się porusza (num lock nadal nie działa). Gdy komputer przestaje odpowiadać, wydaje się, że nadal działają funkcje zdalnego logowania i udostępniania sieci, ale nie można zakończyć sesji konsoli.

Krótko mówiąc, główną przyczyną zachowania jest połączenie kilku rzeczy:

Microsoft Ribbon dla WPFAplikacja Windows Forms obsługująca kontrolę WPF w ElementHostKorzystanie z podwójnie buforowanych formularzy systemu Windows (za pomocą CreateParams)Wykorzystanie renderowania oprogramowania na wstążce WPF

Później rozwiązaliśmy ten problem za pomocąWS_EX_COMPOSITED tylko w kilku wybranych formularzach, ale bardzo chciałbym odkryć główną przyczynę tego problemu.

Do tej pory nie odkryłem prostego sposobu na odtworzenie zawieszenia, ale ta minimalna aplikacja wydaje się sprawiać, że firma wykonuje, przynajmniej na niektórych komputerach, trochę maksymalizacji / przywracania i najechania myszką nad przycisk wstążki.

Poniższy kod jest kompilowany jako x86 .NET 4.0 przeciwkoWstążka Microsoft WPF Biblioteka .NET 4.0.

using System;
using System.Windows.Forms;
using Microsoft.Windows.Controls.Ribbon;
using System.Windows.Interop;
using System.Windows.Forms.Integration;

namespace WindowsRibbonHang
{
    public class Form1 : Form
    {
        protected override CreateParams CreateParams
        {
            get
            {
                CreateParams cp = base.CreateParams;
                cp.ExStyle |= 0x02000000;  // Turn on WS_EX_COMPOSITED
                return cp;
            }
        }

        public Form1()
        {
            Ribbon ribbon = new Ribbon();

            RibbonTab tab = new RibbonTab { Header = "FooTab" };
            ribbon.Items.Add(tab);

            RibbonSplitButton button = new RibbonSplitButton { Label = "FooButton" };
            tab.Items.Add(button);

            ElementHost elementHost = new ElementHost
            {
                Dock = DockStyle.Fill,
                Child = ribbon,
            };

            Controls.Add(elementHost);
            Dock = DockStyle.Fill;

            ribbon.Loaded += (sender, args) => {
                HwndSource hwndSource = System.Windows.PresentationSource.FromVisual(ribbon) as HwndSource;
                HwndTarget hwndTarget = hwndSource.CompositionTarget;
                hwndTarget.RenderMode = RenderMode.SoftwareOnly;
            };
        }
    }

    static class Program
    {
        /// <summary>
        /// The main entry point for the application.
        /// </summary>
        [STAThread]
        static void Main()
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Application.Run(new Form1());
        }
    }
}

questionAnswers(2)

yourAnswerToTheQuestion