Проблема производительности WPF при изменении размера окна с большим количеством элементов управления - PullRequest
5 голосов
/ 10 января 2011

У меня есть окно WPF, содержащее необычное изображение с примерно 200 элементами управления (полученными из кнопок), каждый из которых использует один из 5 моих шаблонов (контуры, эффекты тени и т. Д.). Согласитесь, это тяжелое окно для рисования. Я могу жить с этим.

Моя проблема связана с изменением размера окна. Максимизация / восстановление занимает около 1-2 секунд, но ручное перетаскивание нижнего левого угла приводит к зависанию системы в течение 5-10 секунд. В этой задержке окно является черным и содержит частичные остатки, пока не будет показан окончательный результат. Это выглядит любительским и , с которым я не могу жить.

Удаленное подключение: используя удаленную учетную запись, я обнаружил, что изменение размера окна всегда занимает 1-2 секунды, но не рисует «промежуточные» этапы, пока я перетаскиваю границы окна. Результат такой же быстрый, как я и ожидал.

Мой вывод такой: перерисовки во время изменения размера являются узкими местами.

Неизбежный вопрос заключается в следующем: как я могу предотвратить перерисовку окна, пока изменение размера не будет завершено?

Заранее спасибо за любые идеи ...

Ответы [ 3 ]

4 голосов
/ 10 января 2011

@ Себ: Я начинаю думать, что WPF не предназначен для интерфейсов, которые идут за 2-3 контроля одновременно

Visual Studio 2010 и Expression Blend должны быть хорошими контрпримерами. Хотя Visual Studio иногда замирает, узкое место определенно отсутствует в рендеринге WPF.

@ Себ: неизбежный вопрос: как могу ли я предотвратить перерисовку окна пока не закончится изменение размера?

Просто установите видимость содержимого окна на Visibility.Collapsed перед изменением размера / максимизации и сделайте его видимым впоследствии. Хотя я думаю, что вы задали не тот вопрос. Вот правильный

Как заставить мои элементы управления измерять / упорядочивать очень быстро?

И чтобы ответить на него, вы должны взглянуть на свой код. Может быть, вы интенсивно используете свойства зависимостей в алгоритме измерения / упорядочения? Или, может быть, вы выбрали неправильные панели (например, Grid медленнее, чем Canvas)? Или, может быть ... я перестаю догадываться здесь :).

Кстати, всегда лучше запускать приложение под профилировщиком и доказывать узкое место, а не предполагать, где оно может быть. Проверьте, Eqatec Profiler , он бесплатный, но достаточно мощный. VS 2010 также предлагает хорошие функции профилирования, хотя это далеко не бесплатно. И вы можете проверить WPF Performance Suite .

Надеюсь, это поможет.

1 голос
/ 10 января 2011

Дайте мне знать, как это работает ... Я предполагаю, что ваш корневой визуальный элемент растягивается по горизонтали и вертикали, чтобы заполнить ваше окно автоматической высотой / шириной.Избавьтесь от Авто высота / ширина.При запуске приложения установите размеры корневого элемента.Существует FrameworkElements с измененным размером событие .Зарегистрируйтесь для этого на Application.Current.MainWindow (возможно, это опечатка, которая была из памяти).Всякий раз, когда происходит это событие, запускайте таймер с небольшим интервалом.Если вы получите другое изменение размера во время работы таймера, проигнорируйте его и сбросьте таймер.Когда таймер срабатывает, вы теперь знаете новый размер, который желает пользователь, и что он (по крайней мере, на короткий период) прекратил изменение размера окна.

Надеюсь, это поможет!

0 голосов
/ 14 апреля 2011

Из Ответ Ragepotato и ваш комментарий о необходимости примерно увидеть, как будет выглядеть интерфейс при изменении размера , если у вас нет динамически перемещаемых объектов.(например, Wrap Panel) - вы можете сделать скриншот содержимого окна и заполнить его рамкой.Установите растяжение как по высоте, так и по ширине, и вы получите (слегка размытое) представление о том, каким будет конкретный размер.Он не будет жить при изменении размера, но в течение тех нескольких секунд, которые, вероятно, не будут иметь значения ..

...