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

Вниз

ScrollBox - видимая область   Найти похожие ветки 

 
BMouradov   (2006-04-14 20:23) [0]

Как узнать координаты прямоугольника, отображаемого в данный момент в ScrollBox-е? Что-нибудь вроде sb.Canvas.ClipRect есть?


 
BMouradov   (2006-04-15 00:21) [1]

Ещё один вопрос на ту же тему - как получить облать ScrollBox-а, которую надо перерисовать? Мне кажется, что отслеживать OnScroll - это не совсем красивый метод, может, есть что-нибудь красивее?


 
MTsv DN ©   (2006-04-15 09:06) [2]

Привет...

Что-то вроде этого...
function TfrmMain.ScrollBox1Message(var Msg: tagMSG;
 var Rslt: Integer): Boolean;
var
R : TRect;  
begin
Result := false;
if (Msg.message = WM_VSCROLL) or
   (Msg.message = WM_HSCROLL) then
 begin
  ZeroMemory(@R, SizeOf(R));
  Windows.GetClipBox(Memo.Canvas.Handle, R);
  MsgOK(
        "Left: " + int2str(R.Left) + #13#10 +
        "Right: " + int2str(R.Right) + #13#10 +
        "Top: " + int2str(R.Top) + #13#10 +
        "Bottom: " + int2str(R.Bottom)
       );
 end;
end;


С Уважением MTsv DN


 
ECM ©   (2006-04-17 13:35) [3]

Думаю здесь надо кое-что уточнить :))
GetClipRect - это общая (применимая к любым окнам, т.е. не только к ScrollBox) фунуция позволяющая узнать какая часть окна действительно видна (не заслонена другими, не выходит за пределы экрана и т.п) и должна быть перерисована.
Здесь как мне кажется вопрос был немного о другом. Какая часть элемента помещенного в ScrollBox будет видна в нем в данный момент и должна быть отрисована при необходимости...?
Тут все просто - ScrollBox всегда отрисовывает свой ClientRect (т.е. это видимая часть его "внутреннего содержания" ). Все "дети" помещенные в него имеют свой BoundsRect (Left,Top,Width,Height). Изменение которого заставляет ScrollBox пересчитывать параметры своих ScrollBar-ов и наооборот изменение позиции ScrollBar-а воздействует на позицию потомков внутри ScrollBox (меняются Top и Left). Поэтому ответ  - достаточно найти пересечение ScrollBox.ClientRect и BoundsRect потомка.


 
Vladimir Kladov   (2006-04-17 15:34) [4]

Иногда проще дать практический совет, чем разводить теорию.

R := ScrollBox1.ClientRect;
R.TopLeft := ScrollBox1.Client2Screen( R.TopLeft );
R.BottomRight := ScrollBox1.Client2Screen( R.BottomRight );
R.TopLeft := PaintBox1.Screen2Client( R.TopLeft );
R.BottomRight := PaintBox1.Screen2Client( R.BottomRight );

Все, в R: TRect - видимая часть PaintBox1, который дочерен к ScrollBox1.


 
ECM ©   (2006-04-17 16:07) [5]


> Иногда проще дать практический совет, чем разводить теорию

Иногда знание теории дает лучший результат :))

 R  := ScrollBox1.ClientRect;
 R1 := PaintBox1.BoundsRect;
 R2.Left := -R1.Left;
 R2.Top := -R1.Top;
 R2.Right := R2.Left+(R.Right-R.Left);
 R2.Bottom := R2.Top+(R.Bottom-R.Top);

Всё в R2: TRect то же самое что и в R из [4] но с меньшими затратами кода, (почти вдвое)   и немного лучше в быстродействии.
:)


 
BMouradov   (2006-04-18 16:20) [6]

ECM и Кладову: спасибо, R2 - это именно то, что нужно.

Однако второй вопрос остался - не всегда нужно перерисовывать всю область компонента, "видимую" через Scrollbox. Например, если чужое окно лишь частично перекрывало Ваше, либо при скроллировании, либо сам ScrollBox не полностью виден на экране. Нет ли стандартных способов узнать ту область, которую надо именно сейчас перерисовать, или лучше всегда полностью отрисовывать?


 
BMouradov   (2006-04-18 16:46) [7]

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


 
ECM ©   (2006-04-18 17:06) [8]

Накладно буферировать видимую часть?!!!
Это у Вас за конфигурация системы такая слабая?
Я при отображении карты (города, области и т.д - неважно) так и делаю - и не считаю это накладным (Windows все равно создает буфер в памяти для окна - ну и пускай их будет два!).
....
Попробуйте повозится с GetClipBox в OnPaint(или там где у Вас идет отрисовка)


 
Vladimir Kladov   (2006-04-18 17:51) [9]

40000х40000 пикселов? Огогошеньки. Никаких гигагерцев не хватит. Частями надо перерисовывать, все-таки. Хотя бы по квадратам, которые в область попали или пересеклись. Иначе (|).


 
Vladimir Kladov   (2006-04-18 18:00) [10]

Пардон, не тоак прочитал. Решил, что вообще все перерисовывается, а не видимая часть. :)


 
ECM ©   (2006-04-18 18:57) [11]


> 40000х40000 пикселов? Огогошеньки. Никаких гигагерцев не
> хватит. Частями надо перерисовывать, все-таки. Хотя бы по
> квадратам, которые в область попали или пересеклись.

Это, да... :)

> Иначе (|).

Я бы даже сказал  (__|__)  !

В свое время /* ух ты а ведь это было уже 10 лет назад :(  */ - чтобы отображать такую массу пикселов я разбивал предварительно изображение по квадратам 400x600 в отдельные пронумерованные bmp-шки. И делал их динамичекую подкачку в память - так чтобы в памяти сидели только реально отображаемые куски.


 
BMouradov   (2006-04-19 14:31) [12]

Всем спасибо! Буду пробовать.


 
Barloggg   (2006-05-18 14:17) [13]

Еще вопрос.
Есть ScrollBox на нем лежит PaintBox.

PaintBox маленький - полос прокрутки нету.
Увеличиваю PaintBox - полосы прокрутки появляются.
Двигаю ползунки чтобы рассмотреть нижнюю часть PaintBox.
После этого уменьшаю PaintBox до первоначального размера - полосы прокрутки исчезают на PaintBox так и остается за краями кадра. И как его возвращать обратно???


 
Barloggg   (2006-05-18 14:25) [14]

О!!! я понял. оказывается все детки сдвигаются в глубоко отрицательную сторону и надо их возвращать ручками.... надо же... в VCL кажись детки сами возвращались на первоначальное место...


 
ECM ©   (2006-05-18 15:24) [15]


> надо их возвращать ручками

...

> После этого уменьшаю PaintBox до первоначального размера

Это же вы тоже делаете "ручками" ? Вот и одновременно возвращайте куда Вам нравится - можно в ноль а можно и пересчитать через разницу масштабов... ИМХО такое поведение ScrollBox - "более гибкое" чем автоматическая перестройка. Да и код надо экономить - KOL всё-таки :)


 
Barloggg   (2006-05-18 16:28) [16]

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

> "более гибкое"

скорее уж более кодоэкономичное...чем гибкое.
надеюсь Владимир упомянет об этом в книжке-справочнике по KOL.


 
ECM ©   (2006-05-18 17:31) [17]

Я тут еще посмотрел на код - возможно его можно будет поправить
(в последней версии KOL в этом месте мои исправления). Если не сложно
сделайте простенький проект где этот эффект проявляется (я бы и сам, но у меня со временем пока неочень) - и мне в мыло (анкета)


 
Barloggg   (2006-05-22 10:41) [18]

проект? не вопрос.
но словами короче:
берем ScrollBox.
ложим в него чего-нибудь. например панель.

в сторонке ложим две кнопки.
по клику первой увеличиваем панель в несколько раз.
по клику второй - уменьшаем.

Как работает.
кликаем первую кнопку. потом сдвигаем ползунки на scrollbox.
кликаем вторую кнопку. и потом пытаемся вернуть все на место...

О! а вот и проект подоспел. Высылаю.

Кстати обнаружил один неприятный эффект. Панель - то лежит произвольно в центре ScrollBox. А как только начинается движение ползунка - панель прыгает к левой стенке Scrollbox.



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

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

Наверх




Память: 0.49 MB
Время: 0.043 c
3-1164780850
Монг
2006-11-29 09:14
2007.02.18
Коппонент ADOQuery


3-1164339759
REM02
2006-11-24 06:42
2007.02.18
D7+ IB7.5 Помогите с запросом


15-1168729488
Rouse_
2007-01-14 02:04
2007.02.18
Барановичи - есть такой город.


15-1168795073
IMHO
2007-01-14 20:17
2007.02.18
Падение Шевченко


15-1168099871
Алексей С.
2007-01-06 19:11
2007.02.18
Алгоритм проведения соревнования по олимпийскаой системе.





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
Английский Французский Немецкий Итальянский Португальский Русский Испанский