![]() |
|
|
![]()
|
|
| Hrundel |
|
|||
|
Новичок Профиль Группа: Участник Сообщений: 36 Регистрация: 5.8.2012 Репутация: нет Всего: нет |
Всем привет.
( Earnest, тебе отдельный, персональный привет В моей программе вид меньше клиентской области, да еще и со скролом. Внутри вида должен отображаться документ с рабочей областью. По принципу Иллюстратора - то что лежит в рабочей области выводится на печать, то что за пределами - нет. Рабочая область лежит точно в центре вида. Необходимо разместить скролы таким образом, чтобы рабочая область отображалась ровно по середине вида. Арифметика там простая. point.x = размер_самого_вида / 2 - ширина_вида_в_клиентской_области; тоже самое для высоты Но самая засада заключается в том, как получить ширину_вида_в_клиентской_области (ну и высоту тоже конечно) Значит что-то типа GetViewportOrgEx(NULL, &renderSize); могло бы помочь. Всякие GetClientRect() возвращают совсем не то что требуется. Попытался забрать Rect из CScrollView::OnNcCalcSize(bCalcValidRects, lpncsp);
но возвращаемые значения при пересчете не соответствуют истине. Будте добры подскажите. ( На картинке: вид_в_клиентской_области выделен синим ) ![]() Вообще, могу сказать, что найти какую-либо правильную, подходящую функцию в MFC - дело не простое. Всем спасибо. Это сообщение отредактировал(а) Hrundel - 1.9.2012, 10:23 |
|||
|
||||
| Earnest |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Экс. модератор Сообщений: 5962 Регистрация: 17.6.2005 Где: Рязань Репутация: 87 Всего: 183 |
Разве? А не point.x = (размер_самого_вида - ширина_вида_в_клиентской_области)/2 Почему это? Всего то возвращал. Может, у тебя не MM_TEXT? Или просто размеры скролов не учитываются? Или я просто не понимаю задачу. Точно не понимаю - что такое вид в твоей терминологии? Стандартно - это просто окно, в котором отображается содержимое (документа). Тогда вид никак не может быть своей меньше клиентской области. А если видом ты называешь некоторую область в логических координатах, то смени термин, не путай людей, пусть это будет какая-нибудь "рабочая зона". Если так, то понятно, что зона может быть как больше, так и меньше вида (его клиентской области). Но если она меньше - зачем скроллы-то? Что там прокручивать? Помести зону в центр вида и все дела? -------------------- ... |
|||
|
||||
| Hrundel |
|
|||
|
Новичок Профиль Группа: Участник Сообщений: 36 Регистрация: 5.8.2012 Репутация: нет Всего: нет |
Привет Earnest,
объяснил, конечно, запутано. Чтобы распутать - нацарапал картинку ![]() С термином "рабочая зона" в экземпляре CView согласен. Пойдет. А вот "Рабочая область" это в свою очередь просто лист, как лист бумаги. В рабочую зону можно положить векторный объект, но тогда он, скажем, не будет печататься, а печататься будет только то, что лежит в "рабочей области". По крайней мере так задумано. Понятно, что если сказать ScrollToPosition( рабочая_зона / 2); то скрол крутит и устанавливает центр рабочей зоны в верхний левый угол CView Значит, надо теперь вернуться на какое-то количество пикселей назад, чтобы центр рабочей зоны оказался в центре экземпляра CView Значит, по логике вещей, это должна быть ширина_CView / 2. Тогда и получается: ScrollToPosition( рабочая_зона - ширина_CView ) / 2 Извиняюсь, первый раз немного намудрил. А вообще, пока использую только MM_TEXT, чтобы не путаться. Другие варианты подключу позже. Да и то - если возникнет необходимость. Уж, очень хочется, всегда под рукой размер экземпляра CView иметь. Но, пока так и не получилось. Точнее говоря - получилось, но такая кустарщина, даже показывать стыдно. Об элегантности решения - даже речи нет. А цель такая: (я уже показывал в другой теме). То есть, CView для отображения документа, а в оставшейся части клиентской области CFrameWnd кнопки и прочее. ![]() Это сообщение отредактировал(а) Hrundel - 6.9.2012, 20:56 |
|||
|
||||
| Earnest |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Экс. модератор Сообщений: 5962 Регистрация: 17.6.2005 Где: Рязань Репутация: 87 Всего: 183 |
Ладно, с терминами вроде разобрались. Но все равно непонятно, какую роль должны играть скроллы, что они прокручивают? Положение рабочей области в рабочей зоне? или во View?
Еще непонятно, как соотносятся клиентская часть вида (далее просто вид) с рабочей зоной. Это одно и тоже или рабочая зона может быть больше? Если может быть больше (и должна прокручиваться во вью), то налицо необходимость в 2 органах управления: прокрутка рабочей зоны относительно вида и прокрутка рабочей области относительно зоны. И это независимые вещи, в один скрол их не впихнешь. А если зона всегда целиком влазит во вью, то давай лишний термин выбросим, и пусть будет просто вид (=клиентская часть вида).
Мне непонятно. Если таки скроллы прокручивают рабочую зону в виде, то зачем так извращаться. Если масштаб одинаковый, то диапазон скролла равен рабочая зона - вид (по каждому измерению). ScrollTo (0) - это позиция, когда 0 зоны совпадает с 0 вида. максимальная позиция скролла равна уже упомянутому (рабочая зона - вид) - это когда, допустим по горизонтали, правый конец рабочей зоны упирается в правую границу вида. Если разность (т.е. диапазон скролла) <= 0, то скроллы убираем или засериваем. При этом позиция области на зоне от этого никак не зависит, чтобы ее двигать, нужен еще один орган управления. Или я опять не так поняла? -------------------- ... |
|||
|
||||
| Hrundel |
|
|||
|
Новичок Профиль Группа: Участник Сообщений: 36 Регистрация: 5.8.2012 Репутация: нет Всего: нет |
Привет Earnest,
Во первых, спасибо, что пытаешься вникнуть в мой вопрос. Теперь постараюсь уточнить - вообще-то, все очень тривиально. Не знаю на сколько ты знакома с графическими программами на подобие Illustrator, CorelDraw, Freehand, но принцип у них один и тот же. Есть условный "лист", который логичнее всего назвать "зоной вывода" (скажем, на печать или в растровый файл). Объекты документа лежат в "рабочей зоне". Те, которые не попадают в зону вывода не подлежат печати или тому подобное.
Скролы прокручивают положение "рабочей зоны" во View Зона, конечно, больше чем View. Да, именно, так. Это я, конечно, тоже понимаю. И ты поняла все правильно. Моя проблема только в том, что если запрашиваю GetClientRect() во View, то по не совсем мне понятным причинам я получаю значения которые значительно меньше чем экземпляр View. Скажем, у меня окно 1680 шириной, экземпляр CView где-то 1648, а возвращаемое значение 1237 Как так может быть?! Я в недоумении. Может, я прописываю куда-то не туда. Посоветуй, откуда лучше всего запрашивать эти значения, чтобы не было неправильных результатов. ![]() Это сообщение отредактировал(а) Hrundel - 8.9.2012, 12:27 |
|||
|
||||
| Earnest |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Экс. модератор Сообщений: 5962 Регистрация: 17.6.2005 Где: Рязань Репутация: 87 Всего: 183 |
Насчет GetClientRect все очень странно. Эта железобетонная ф-я никогда не подводит. Единственно, хоть ты и не пишешь прямо, есть впечатление, что ты пытаешься "сэкономить", вызывая ее один раз где-то вначале. Если так, то зря. Опыт показывает, что вызывать ее надо в момент использования, и не париться с лишними вызовами.
Если нет, то воспользуйся Спаем, он показывает клиентскую область в том числе. И еще, ты с NCCalсSize не химичил? Это единственное, что может "испортить" клиентскую область, насколько я знаю. Т.е. твоя задача состоит в том, чтобы разобраться с размерами клиентской области, а не найти ей замену в формуле. -------------------- ... |
|||
|
||||
![]()
|
| 0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
| 0 Пользователей: | |
| « Предыдущая тема | Visual C++/MFC/WTL | Следующая тема » |
|
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |