LINUX.ORG.RU
ФорумTalks

Тулкиты, двойная буферизация, backing store


0

3

Если взять окно Firefox и повозюкать по нему другим окном, то вы не увидите никаких артефактов перерисовки окна.
Если взять окно Dolphin, то, аналогично, не будет никаких артефактов.
Если взять любое приложение на Gtk, то будет виден этот тихий ужас, когда обновляемая область окна сначала заливается цветом фона, а уже потом с ощутимой задержкой на ней появляется актуальное содержимое.
Почему?

Потому что Firefox и Qt буферизуют результат рендеринга окна и при последующих Expose не отрисовывают его заново, а просто копируют пиксели из буфера. Gtk так не делает.

Очевидно, что хранение пререндеренного пиксмапа и последующий рендеринг из него — более дешевая операция, чем постоянная перерисовка 100500 виджетов. Когда-то у xorg была поддержка backing store, решающая именно эту проблему: графический сервер мог сохранять содержимое окон и использовать его для отрисовки при изменении расположения окон. Сейчас эта фича объявлена устаревшей и выпилена. Лол, ок. Задача-то никуда не делась. Значит, этим должны заниматься тулкиты.

Теперь самое интересное: Gtk имеет поддержку двойной буферизации при выводе. Её предназначение в исключении «моргания» отрисовки интерфейса. Когда тулкит получает Expose, он создаёт пиксмап, равный по размеру обновляемой области. Весь рендеринг производится в этот пиксмап. После окончания рендеринга, содержимое пиксмапа копируется в окно одной командой (чем и обеспечивается отсутствие моргания), после чего пиксмап уничтожается.

Очевидно, что на самом деле вместо этой недоделанной двойной буферизации нам нужна полноценная буферизации всего содержимого окна в постоянно существующем пиксмапе. Реальный код перерисовки должен выполняться только при явном запросе со стороны виджетов, Expose же со стороны сервера должен всегда обрабатываться единственной операцией «скопировать пиксели».

Это я всё к чему. Очень чешутся руки взяться за допилку Gtk, и чем дольше я имею с ним дело, тем сильнее. Пока гномеры ваяют очередную ненужную DE, их тулкит продолжает оставаться изрядным говном. Лучше бы на тулкит силы направили.

Отговорите меня, кто-нибудь.

Если взять любое приложение на Gtk, то будет виден этот тихий ужас, когда обновляемая область окна сначала заливается цветом фона, а уже потом с ощутимой задержкой на ней появляется актуальное содержимое.

о_О Не видел такого.

GotF ★★★★★
()
Ответ на: комментарий от snizovtsev

Я не использую композитный WM.

Тулкит должен себя адекватно вести и при отсутствии композитного WM.

geekless ★★
() автор топика

Написать поддержку backing store заново?

leonidko ★★★★
()
Ответ на: комментарий от geekless

Тулкит должен себя адекватно вести и при отсутствии композитного WM.

Это объясняет, почему я никогда не видел ничего подобного описанному...

Axon ★★★★★
()
Ответ на: комментарий от buddhist

От Gtk он только движок стилей использует.

geekless ★★
() автор топика

нефиг использовать вм-ы, которые отображают содержимое окна при перетаскивании

ananas ★★★★★
()
Ответ на: комментарий от ananas

Так дело не только в этом. С любым (нетайловым и некомпозитным) WM будет наблюдаться то же самое при изменении z order.

geekless ★★
() автор топика

повозюкать по нему другим окном

обновляемая область окна сначала заливается цветом фона

Ух ты. Как у вас там здорово.

krakatau
()

Еще к вопросу об эффективности тулкитов:

Gtk имеет разные стили для виджета, на которого наведена мышь и для которого нет. Соответственно, при наведении мыши виджет перерисовывается. Веселье начинается когда эти стили совпадают: тулкит об этом ровным счетом ничего не знает, и виджет всё равно перерисовывается.

Например, возьмем тунар и несколько секунд поводим мышью по боковой панели, где названия точек монтирования. В окне программы при этом не меняется ни единого пикселя. А вот что при этом происходит под капотом:

$ x11trace -n thunar  2>/dev/null | grep Request | cut -d: -f6 | cut -d' ' -f2 | sort | uniq -c | sort -n
      1 ConvertSelection
      1 Enable
      1 GetCrtcInfo
      1 GetOutputPrimary
      1 GetScreenResourcesCurrent
      1 GrabKeyboard
      1 GrabPointer
      1 Initialize
      1 ListInputDevices
      1 OpenFont
      1 PerClientFlags
      1 QueryPictFormats
      1 QueryTree
      1 SelectInput
      1 UngrabKeyboard
      1 UngrabPointer
      1 UseExtension
      2 Attach
      2 CreateCounter
      2 CreateGlyphSet
      2 DestroyCounter
      2 DestroyWindow
      2 GetExtensionVersion
      2 GetGeometry
      2 GetWindowAttributes
      2 OpenDevice
      2 PolySegment
      2 SelectEvents
      2 SelectSelectionInput
      2 SendEvent
      2 SetInputFocus
      2 UnmapWindow
      3 CreateGlyphCursor
      3 GetOutputInfo
      3 GetSelectionOwner
      3 GrabServer
      3 UngrabServer
      4 ConfigureWindow
      5 MapWindow
      6 DeleteProperty
      7 CreateWindow
      7 TranslateCoordinates
      8 GetAtomName
      8 GetProperty
      8 QueryVersion
     10 QueryPointer
     15 QueryExtension
     16 Trapezoids
     30 ChangeWindowAttributes
     33 FreeGC
     42 GetInputFocus
     51 InternAtom
     68 CreateGC
     77 ChangeProperty
    104 AddGlyphs
    116 ChangePicture
    432 CompositeGlyphs16
    529 CopyArea
    618 FillRectangles
    995 CompositeGlyphs8
   1322 SetPictureClipRectangles
   1617 PolyFillRectangle
   2144 SetClipRectangles
   2162 Composite
   2171 PutImage
   2702 FreePixmap
   2715 CreatePixmap
   4460 FreePicture
   4484 CreatePicture
   5021 ChangeGC

А потом мы удивляемся, на что гигагерцы тратятся, и куда энергия из аккумулятора пропадает...

geekless ★★
() автор топика
Ответ на: комментарий от thelonelyisland

А у Qt я сходу не нашел такого виджета, который должен реагировать на наведениие, но при этом визуально не изменяется, так что не могу проверить. У меня Qt-шных приложений всего пара установлдена сейчас.

geekless ★★
() автор топика

Отключил в квине композитинг, все продолжает работать корректно. ГТК2.
Какие еще нужны условия для воспроизведения глюка? Пока что напоминает ситуацию с вирусами под линукс.

Tweaker ★★★★☆
()
Ответ на: комментарий от geekless

Я думаю на это не там много ресурсов тратится, но неприятно. И да, GTK не нужно. :)

thelonelyisland ★★★
()
Ответ на: комментарий от Tweaker

Какие еще нужны условия для воспроизведения глюка?

Хз. Поставить тяжелую тему оформления, нагрузить ядра? Возможно, на быстрой машине перерисовка успевает уложиться в 1 кадр, поэтому незаметно.

На Celeron D этот глюк виден абсолютно чётко в любом gtk-шном окне.

geekless ★★
() автор топика

Отговорите меня, кто-нибудь.

А чего тебя отговаривать? Всё равно ведь ниасилишь.

Relan ★★★★★
()
Ответ на: комментарий от geekless

Я не использую композитный WM.

ССЗБ.

Тулкит должен себя адекватно вести и при отсутствии композитного WM.

А он и ведёт. Кеширование изображений окон — задача именно композитора, а не тулкита.

Relan ★★★★★
()

Я такого на своей машине не наблюдаю. Debian stable, GTK+ 2, FVWM.

Raving_Zealot ★★
()
Ответ на: комментарий от Relan

ССЗБ.

ССЗБ я был бы, если бы использовал хреновый WM вместо нормального только ради наличия композитинга.

А он и ведёт. Кеширование изображений окон — задача именно композитора, а не тулкита.

Ох лол. Плохие xul и Qt устроены «неправильно», но не лагают, а хороший Gtk устроен «правильно», но лагает. Типичный «нет значит не нужно» аргумент.

Ну и если ты так напираешь на разделение задач (в принципе я согласен, что кэширование было бы логичнее проводить не в тулките, а уровнем ниже), то встаёт вопрос, какого черта backing store было выпилено из xorg. В отсутствии отдельного композитора задачу композитинга окон выполняют именно иксы. И выполняют отвратительно, поскольку не кэшируют окна.

geekless ★★
() автор топика
Ответ на: комментарий от geekless

ССЗБ я был бы, если бы использовал хреновый WM вместо нормального только ради наличия композитинга.

Ну то есть твой WM хороший, а GTK плохой. Ясно.

Типичный «нет значит не нужно» аргумент.

Ну почему же. Нужно. Но не в тулкитах.

Ну и если ты так напираешь на разделение задач

Именно. Тулкитов миллион и изобретать в каждом велосипед просто глупо.

встаёт вопрос, какого черта backing store было выпилено из xorg

Не знаю. Мне вообще всё равно, у меня таких проблем нет. Запусти xcompmgr или используй другой WM и не парь людям мозг.

Relan ★★★★★
()

Плюсую. А ещё сделали бы нормальный диалог открыть/сохранить файл в их тулките. Шёл 2012 год...

BattleCoder ★★★★★
()

Отговорите меня, кто-нибудь.

зачем отговаривать ниасиляторов, гнущих пальцы? ты и без того прекрасно не возмешься. ;)

Rastafarra ★★★★
()
Ответ на: комментарий от Artificial_Thought

Ты ещё не забывай, что Qt просто рисует один битмап, а gtk множество окон через Xembed, если я не ошибаюсь.

Ты ошибаешься. Подучи матчасть на предмет, что такое Xembed.

geekless ★★
() автор топика
Ответ на: комментарий от BattleCoder

А ещё сделали бы нормальный диалог открыть/сохранить файл в их тулките.

Ты что, вдруг юзабельный получится! Они этого не переживут.

geekless ★★
() автор топика
Ответ на: комментарий от geekless

Надеюсь, что не возьмусь.

нисцы, в этом треде никто даже не сомневается ;)

Rastafarra ★★★★
()

Очень чешутся руки взяться за допилку Gtk,

не трогай каку!

DNA_Seq ★★☆☆☆
()

Просто переходи на Qt.

Deleted
()

Когда-то у xorg была поддержка backing store, решающая именно эту проблему: графический сервер мог сохранять содержимое окон и использовать его для отрисовки при изменении расположения окон. Сейчас эта фича объявлена устаревшей и выпилена. Лол, ок.

По-моему, она не объявлена устаревшей. Вернее, старую реализацию удалили, а новую сделали. Ее реализовали через Composite Extension, кажется.

Zubok ★★★★★
()
Ответ на: комментарий от geekless

fvwm 2.6.3 c OpaqueMoveSize 0, gtk 2.24.10 ничего такого не наблюдается. дрова свободные - ati, nouveau и intel

ananas ★★★★★
()

Отговорите меня, кто-нибудь.

Ты знаешь, да, проблема есть. Только вот что — посмотри внимательнее на тот же Thunar. Там эта бяка только на левой панели, а на списке файлов её нет. А знаешь почему? Потому что это задача виджета — отрисовывать себя быстро. Встроенные виджеты кешируют себя, где надо. А панелька Thunar'а каждый раз отрисовывает себя по expose.

Ну вот сделаешь ты буферизацию принудительную. И GtkWidget будет с копией, GtkWindow тоже с твоей подачи ей обзаведётся, если ты не выпилишь буферы из конкретных виджетов, это будет не двойная, а четырёхкратная буферизация. А я пойду в магазин за новой планкой памяти.

Так что лучше пинай разработчиков Thunar'а и других провинившихся.

i-rinat ★★★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.