Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "WinAPI";
Текущий архив: 2009.05.31;
Скачать: [xml.tar.bz2];

Вниз

Как правильно отрисовать в WM_PAINT?   Найти похожие ветки 

 
Тимохов   (2008-05-10 21:01) [0]

Здравствуйте.

Предпосылки моей проблемы
Мне нужно написать компонент, который представляет собой грид (матрицу из примоугольников). Грид содерит только статическую информацию: никакого ввода.
Одной из задач является создание возможности объединения ячеек по горизонтали. Ну т.е. как в Екселе.

Как я делал
Рассмотрим такой грид:

-----
|A|B|
-----
|C|D|
-----

Ячейки C и D объеденены. Т.е. ячейка C является головой объединения.
Я перекрыл метод Paint и отрисовываю там свой грид.
Я не обращаю внимание на регион клипинга, т.е. рисую во всей области компонента (отрисовка тривиальная и быстрая, незачем экономить).

При отрисовке ячейки С я определяю, что она является головой объединения. Поэтому я ее отрисовываю, задавая ее область, равную объединению областей С и D. Ячейку D я вообще не отрисовываю, просто пропускаю.

Проблемы
Если в рассмотренном примере чем-то инвалидейтить область ячейки D (например, провести по ней другим окном), но не затронуть ячейку C, то ячейка D отрисовывается некорректно (либо мусор, либо затирается). Если же затронуть ячейку C, то и C и D коорректно перерисовываются.

Почему такое получается я более-менее понимаю. Т.е. теорию вопроса про инвалидацию, валидаци, клипинг, WM_PAINT и пр. я знаю неплохо - сегодня прочел соответствующий раздел. Хотя, видимо, не до конца понимаю :)

Вопросы
1. Теоретический. Когда портится область ячейки D, то происходит инвалидация, потом WM_PAINT, причем регион клипиинга ограничивается только испорченной областью (т.е. не затрагивает ячейку С). Однако в WM_PAINT я делаю полную перерисовку области компонента и ячейки С (и как следствие области, занимаемой ячейкой В) в том числе. Почему не видно изменение ячейки D?
2. Практический. Что делать?


 
Тимохов   (2008-05-10 21:57) [1]

Немного ошибся в формулировке вопроса :(
Надо так

1. Теоретический. Когда портится область ячейки D, то происходит инвалидация, потом WM_PAINT, причем регион клипиинга ограничивается только испорченной областью (т.е. не затрагивает ячейку С). Однако в WM_PAINT я делаю полную перерисовку области компонента и ячейки С (и как следствие области, занимаемой ячейкой D) в том числе. Почему не видно изменение ячейки D?


 
{RASkov} ©   (2008-05-10 22:17) [2]

Написано слов много, а ведь в тумане все это... :(
ВинАПИ, Грид, Ячейки.... почему, что, как?


 
Тимохов   (2008-05-10 22:54) [3]

слуш, давай по делу. вопрос сформулирован вполне четко.
объясни, если сможешь, поведение системы (ОС, в смысле) в указанном случае? почему так?

я думаю, если пойму, то и проблему решу.


 
DVM ©   (2008-05-10 23:48) [4]


> Тимохов

Ты можешь привести упрощенный вариант кода (желательно рабочий), на котором повторяется такой глюк? Без этого очень сложно судить о твоей проблеме (она скорее всего в твоем коде).


 
Тимохов   (2008-05-10 23:54) [5]


> DVM ©   (10.05.08 23:48) [4]


Ок, попробую.

Еще раз перечитал Painting and drawing :) Я тоже начинаю приходить к мнению, что это в коде что-то такое есть, что не дает перерисовывать правильно.

Вообще изначально код был взят года 4 назад из TCustomGrid. Путем жесткой кастрации он был преобразован к текущему виду. Работает уже года 2, но только сегодня я захотел сделать span. Вот и напоролся.

В общем - попробую упростить код.


 
{RASkov} ©   (2008-05-11 00:25) [6]

> .... Почему не видно изменение ячейки D?

> [3] Тимохов   (10.05.08 22:54)
> вопрос сформулирован вполне четко.

Согласен.... Вопрос более чем четкий.
Тогда вот ответ: Потому что она не перерисовывается.)

Сорри... но присоединяюсь к [4] посту...
Грид - на то он и содержит ячейки и рисует их по отдельности... стала ячейка инвалидом - перерисовали ее только.... но если она рисуется в другом месте - то нужно это учитывать...

Да видел я:

> Однако в WM_PAINT я делаю полную перерисовку области компонента
> и ячейки С

...тут как запрограммируешь, так и будет.... и ничего другого не бывает....


 
Германн ©   (2008-05-11 00:50) [7]


> Тимохов   (10.05.08 21:57) [1]
>
> Немного ошибся в формулировке вопроса :(
> Надо так
>
> 1. Теоретический. Когда портится область ячейки D, то происходит
> инвалидация, потом WM_PAINT, причем регион клипиинга ограничивается
> только испорченной областью (т.е. не затрагивает ячейку
> С). Однако в WM_PAINT я делаю полную перерисовку области
> компонента и ячейки С (и как следствие области, занимаемой
> ячейкой D) в том числе. Почему не видно изменение ячейки
> D?
>

Что-то похожее тут на форуме как-то было. То бишь был вопрос про "объединение ячеек грида". Правда там была работа со стандартным гридом, а не с собственным компонентом.

> Вообще изначально код был взят года 4 назад из TCustomGrid.
>  Путем жесткой кастрации он был преобразован к текущему
> виду.

Вот в этом участке кода скорее всего собака и порылась.


 
тимохов   (2008-05-11 13:22) [8]

Да, видимо, где-то в коде есть что-то :)
Буду искать.

Потому как вроде не должно себя вести так: WM_PAINT приходит, перерисовку я делаю полную, поэтому полюбому D должен перерисовать.


 
тимохов   (2008-05-11 13:58) [9]

Прошу прощения, за шум. Я все понял.

Если интересно, то я разобрался в чем дело.

Мой компонент - это когда-то сильно кастрированный TCustomGrid.
Вчера я в него дописывал объединения ячеек. Делал это в функции DrawCells в методе TCustomGrid.Paint.

Алгоритм отрисовки я уже писал выше: видя, что ячейка С - голова объединения я присоединял к ней прямоугольник ячейки D. Потом отрисовывал C в новом прямоугольнике, а D вообще пропускал.

В функции DrawCell есть проверка
if (Where.Right > Where.Left) and RectVisible(Canvas.Handle, Where) then ...
Собсно ошибка была моя в том, что у меня Where - это область исходной ячейки С, без присоединенной D. А т.к. RectVisible возвращает True, если Where внутри региона клипинга, то, если портить только D, то отрисовки C вообще не было. Отсюда и мусор в ячейке D, так как ее область вообще не отрисовывалась.

В общем я во всем разобрался. Никаких чудес.

ЗЫ
Блин, в голову не могло, что RectVisible имеет какое-то отношение к клипингу. Назвали бы ее что-ли как-то удачней :)



Страницы: 1 вся ветка

Форум: "WinAPI";
Текущий архив: 2009.05.31;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.47 MB
Время: 0.005 c
2-1239991640
Индеец
2009-04-17 22:07
2009.05.31
Родитель и потомок сообща


2-1239819150
Андрей (начинающий)
2009-04-15 22:12
2009.05.31
DrawGrid и рисование


15-1238413691
Галинка
2009-03-30 15:48
2009.05.31
База данных для MySQL


2-1239942805
товарищ вася
2009-04-17 08:33
2009.05.31
Вопрос про объявление


2-1240165745
daxter
2009-04-19 22:29
2009.05.31
Помогите с indy 9





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский