Blog. Just Blog

Особенности работы с контролом SysMonthCal32

Версия для печати Добавить в Избранное Отправить на E-Mail | Категория: Образ мышления: Assembler | Автор: ManHunter
Различная ширина SysMonthCal32 в разных локалях
Различная ширина SysMonthCal32 в разных локалях

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

Как оказалось, перед тем, как вывести календарик в диалоговом окне, надо сперва выяснить, каких размеров он будет. Для этого надо создать контрол календарика и сразу послать ему сообщение MCM_GETMINREQRECT. На выходе мы получим размеры, которые виджет календарика будет занимать. В обработчике диалогового окна это лучше всего делать на этапе инициализации. Например, так:
  1. section '.data' data readable writeable
  2.  
  3. ; Структуры для получения требуемых координат виджета
  4. crect RECT
  5. ...
  6.  
  7. section '.code' code readable executable
  8.         ; Получить нужные размеры календарика и подогнать
  9.         ; виджет под эти размеры
  10.         invoke  GetDlgItem,[hwnddlg],ID_CALENDAR
  11.         mov     ebx,eax
  12.         invoke  SendMessage,ebx,MCM_GETMINREQRECT,0,crect
  13.         push    TRUE
  14.         mov     eax,[crect.bottom]
  15.         sub     eax,[crect.top]
  16.         ; Вертикальный отступ
  17.         add     eax,30
  18.         push    eax
  19.         mov     eax,[crect.right]
  20.         sub     eax,[crect.left]
  21.         ; Горизонтальный отступ
  22.         add     eax,30
  23.         push    eax
  24.         invoke  MoveWindow,ebx,[crect.left],[crect.top]
Зная новые размеры виджета календарика можно, например, подкорректировать размеры его родительского окна, переместить другие соседние элементы и контролы окна и т.д.

Для большей надежности можно дополнительно узнать максимальную ширину надписи "Сегодня такое-то число" в текущей локали, для этого надо воспользоваться кодом:
  1.         invoke  GetDlgItem,[hwnddlg],ID_CALENDAR
  2.         invoke  SendMessage,eax,MCM_GETMAXTODAYWIDTH,0,0
  3.         ; EAX = максимальная ширина надписи
Созданному контролу отправляется сообщение MCM_GETMAXTODAYWIDTH, на выходе получаем значение ширины надписи. Делается это опять же на этапе инициализации окна. Если вдруг ширина надписи будет больше расчетной ширины календарика (в нашем случае больше значения crect.left), то ширину календарика надо увеличить до этого значения. На практике я такого не встречал, хотя знать это тоже будет полезно.

В приложении пример программы с исходным текстом, которая отрисовывает в окне виджет календарика и подгоняет размеры окна под размеры виджета в зависимости от установленной локали.

Пример программы с исходным текстом (FASM)Пример программы с исходным текстом (FASM)

Autosize.Calendar.Demo.zip (2,908 bytes)


Поделиться ссылкой ВКонтакте Поделиться ссылкой на Facebook Поделиться ссылкой на LiveJournal Поделиться ссылкой в Мой Круг Добавить в Мой мир Добавить на ЛиРу (Liveinternet) Добавить в закладки Memori Добавить в закладки Google
Просмотров: 306 | Комментариев: 2

Метки: Assembler, окна

Комментарии

Отзывы посетителей сайта о статье
ManHunter (11.09.2018 в 10:39):
Всегда пожалуйста :)
avp1965 (07.09.2018 в 17:34):
Благодарствуем.

Добавить комментарий

Заполните форму для добавления комментария
Имя*:
Текст комментария (не более 2000 символов)*:

*Все поля обязательны для заполнения.
Комментарии, содержащие рекламу, ненормативную лексику, оскорбления и т.п., а также флуд и сообщения не по теме, будут удаляться. Нарушителям может быть заблокирован доступ к сайту.
Наверх
Powered by PCL's Speckled Band Engine 0.2 RC3
© ManHunter / PCL, 2008-2018
При использовании материалов ссылка на сайт обязательна
Время генерации: 0.08 сек. / MySQL: 2 (0.0044 сек.) / Память: 5 Mb
Наверх