Руководство программиста в Photon (1037671), страница 36
Текст из файла (страница 36)
Эти функции имеют дело с геометрией поверхностей управления:
PtCalcSurface() | Вынуждает поверхность вычислить свою геометрию | |
PtCalcSurfaceByAction() | Вынуждает все поверхности, связанные с действием, вычислить свою геометрию | |
PtCalcSurfaceById() | Вынуждает поверхность управления с заданным идентификатором вычислить свою геометрию | |
PtSurfaceCalcBoundingBox(), PtSurfaceCalcBoundingBoxById() | Вычисляет окаймляющий прямоугольник для поверхности управления | |
PtSurfaceExtent(), PtSurfaceExtentById() | Вычисляет пределы поверхности управления | |
PtSurfaceHit() | Находит поверхность управления для заданной точки | |
PtSurfaceRect(), PtSurfaceRectById() | Получает ограничивающий прямоугольник для поверхности управления | |
PtSurfaceTestPoint() | Проверяет, находится ли точка на поверхности управления |
Прорисовка поверхностей управления
Поверхности управления опрашиваются на самопрорисовку от заднего плана вперёд, после того как виджет перерисовал себя. Никакого отсечения для Вас не производится. Если Вы хотите отсечения, Вы осуществляете необходимую логику подгонки списка отсечений по ходу прохождения поверхностей, и затем восстанавливаете стек отсечений после того, как прорисована последняя поверхность. В противном случае Вы получите какие-то непредсказуемые результаты.
Следующие функции инициируют перерисовку поверхностей управления:
PtDamageSurface(), PtDamageSurfaceById() | Помечает поверхность как повреждённую, так что она будет перерисована. |
PtDamageSurfaceByAction() | Повреждает все поверхности, связанные с действием. |
Активация поверхностей управления
Эта функция активирует поверхность управления:
PtCheckSurfaces() Сопоставляет событие с поверхностями управления, принадлежащими виджету.
Включение и отключение поверхностей управления
Вы можете включать и отключать поверхности управления, подобно виджетам:
PtDisableSurface(), PtDisableSurfaceById() | Отключает поверхность управления |
PtDisableSurfaceByAction() | Отключает все поверхности управления, связанные с действием |
PtEnableSurface(), PtEnableSurfaceById() | Включает поверхность управления |
PtEnableSurfaceByAction() | Включает все поверхности управления, связанные с действием |
PtSurfaceIsDisabled() | Определяет, отключена ли поверхность управления |
PtSurfaceIsEnabled() | Определяет, включена ли поверхность управления |
Нахождение поверхностей управления
Чтобы найти поверхность управления, используйте эти функции:
PtFindSurface() | Отыскивает поверхность управления с заданным идентификатором |
PtFindSurfaceByAction() | Ищет поверхность управления, связанную с заданным действием |
PtWidgetActiveSurface() | Получает текущую активную в данный момент поверхность управления виджета |
Скрытие и демонстрирование поверхностей управления
Вы можете также скрыть и показать поверхности управления:
PtHideSurface(), PtHideSurfaceById() | Скрывает поверхность управления |
PtHideSurfaceByAction() | Скрывает все поверхности управления, связанные с действием |
PtShowSurface(), PtShowSurfaceById() | Показывает скрытую поверхность управления |
PtShowSurfaceByAction() | Показывает все скрытые поверхности управления, связанные с акцией |
PtSurfaceIsHidden() | Определяет, скрытой ли является поверхность управления |
PtSurfaceIsShown() | Определяет, видна ли поверхность управления |
Установление порядка поверхностей управления
Как и в случае виджетов, Вы можете собирать поверхности управления в стек:
PtInsertSurface(), PtInsertSurfaceById() | Вставляет поверхность управления впереди или позади другой |
PtSurfaceBrotherBehind() | Получает поверхность управления, находящуюся позади данной |
PtSurfaceBrotherInFront() | Получает поверхность управления, находящуюся впереди заданной |
PtSurfaceInBack() | Получает самую заднюю поверхность управления, принадлежащую виджету |
PtSurfaceInFront() | Получает самую переднюю поверхность управления, принадлежащую виджету |
PtSurfaceToBack(), PtSurfaceToBackById() | Перемещает поверхность управления назад за все другие поверхности управления, принадлежащие виджету |
PtSurfaceToFront(), PtSurfaceToFrontById() | Перемещает поверхность управления впереди всех других поверхностей управления, принадлежащих виджету |
Размещение пользовательских данных вместе с поверхностями управления
В функциях, связанных с поверхностями управления, нет данных по ответным реакциям; Вы можете размещать данные пользователя вместе с поверхностями управления, вызывая:
PtSurfaceAddData(), PtSurfaceAddDataById() | Добавляет данные к поверхности управления |
PtSurfaceGetData(), PtSurfaceGetDataById() | Получает данные, связанные с поверхностью управления |
PtSurfaceRemoveData(), PtSurfaceremoveDataById() | Удаляет данные из поверхности управления |
Пример
Вот Вам программа, создающая несколько поверхностей управления:
#include <Pt.h>
/* Это функция, вызываемая, когда для нашей прямоугольной поверхности
управления происходит событие. Когда пользователь щёлкает
на этой поверхности, мы подсчитаем итог и напечатаем, сколько раз это приключилось. */
static int rect_surface_callback( PtWidget_t *widget, PtSurface_t *surface, PhEvent_t *event) {
static int rclicks = 1;
printf("Щелчков по прямоугольнику: %d\n", rclicks++);
return(Pt_END);
}
/* Эта функция, рисующая содержание нашей прямоугольной поверхности
управления. Это очень простой пример; он рисует красный прямоугольник. */
static void rect_surface_draw( PtWidget_t *widget, PtSurface_t *surface, PhTile_t *damage) {
PgSetFillColor(Pg_RED);
PgDrawRect(PtSurfaceRect(surface, NULL), Pg_DRAW_FILL);
}
/* Это функция, синхронизирующая размер поверхности управления с размером виджета.
PtWidgetExtent() возвращает прямоугольник, охватывающий текущий размер виджета.
PtSurfaceRect() является макросом; это означает, что Вы имеете прямой доступ к данным
внутри Вашей поверхности управления. Вам нет нужды вызывать какую-либо функцию,
чтобы изменить её размер. Изменяйте напрямую данные. */
static void rect_surface_calc( PtWidget_t *widget, PtSurface_t *surface, uint8_t post) {
/* Делать это только после того, как виджет расширится. */
if (post) {
/* Прямоугольник занимает верхний левый квадрант окна. */
PhRect_t *extent;
PhRect_t *srect;
extent = PtWidgetExtent(widget, NULL);
srect = PtSurfaceRect(surface, NULL);
srect->ul = extent->ul;
srect->lr.x = (extent->ul.x + extent->lr.x) / 2;
srect->lr.y = (extent->ul.y + extent->lr.y) / 2;
}}
/* Это функция, вызываемая, когда случается событие для нашей эллиптической
поверхности управления. Когда пользователь щёлкает на этой поверхности, мы
подсчитаем итог и напечатаем, сколько раз это приключилось. */
static int ell_surface_callback( PtWidget_t *widget, PtSurface_t *surface, PhEvent_t *event) {
static int eclicks = 1;
printf("Ellipse clicks: %d\n", eclicks++);
return(Pt_END);
}
/* Эта функция, рисующая содержание нашей эллиптической поверхности
управления. Это очень простой пример; он рисует зелёный эллипс. */
static void ell_surface_draw( PtWidget_t *widget, PtSurface_t *surface, PhTile_t *damage) {
PhRect_t *s = PtSurfaceRect(surface, NULL);
PgSetFillColor(Pg_GREEN);
PgDrawEllipse(&(s->ul), &(s->lr), Pg_DRAW_FILL | Pg_EXTENT_BASED);
}
/* Это наша main-функция. Мы создаём окно, инициализируем наше приложение
с сервером Photon и создаём две поверхности управления.
Заметьте, что вторая поверхность не обеспечивает последний параметр, функцию
вычисления занимаемого пространства. Это не нужно, так как пятый параметр,
высота и ширина хранятся в указываемой структуре. Это указатель на реальную
указываемую структуру внутри виджета окна. Поэтому, если объём окна изменился,
изменяя структуру указания пространства, поверхность управления обновляет свои
значения автоматически! */
int main(int argc, char **argv) {
PtArg_t args[1];
PtWidget_t *window;
const PhDim_t dim = { 200, 200 };
PtSetArg(&args[0], Pt_ARG_DIM, &dim, 0);
window = PtAppInit(NULL, &argc, argv, 1, args);
/* Создание прямоугольной поверхности управления. */
PtCreateSurface( window, 0, 0, Pt_SURFACE_RECT, NULL, Ph_EV_BUT_PRESS,
rect_surface_callback, rect_surface_draw, rect_surface_calc);
/* Создание эллиптической поверхности управления для заполнения окна. */
PtCreateSurface( window, 0, 0, Pt_SURFACE_ELLIPSE,
(PhPoint_t*)PtWidgetExtent(window, NULL),
Ph_EV_BUT_PRESS, ell_surface_callback, ell_surface_draw, NULL);
PtRealizeWidget(window);
PtMainLoop();
return(EXIT_SUCCESS);
}
Глава 13. Доступ к модулям PhAB из программного кода
В этой главе обсуждается:
-
Создание внутренних связей
-
Использование внутренних связей в Вашем коде
-
Базы данных виджетов
Вы можете получить доступ к любому модулю напрямую из программного кода Вашего приложения, создав внутреннюю связь к этому модулю.
Внутренняя связь подобна связи ответной рекции – она позволяет Вам задать тип модуля, функцию предустановки и там, где это присуще, расположение. Но в отличие от связи ответной реакции, которая всегда привязана непосредственно к ответной реакции виджета, внутренняя связь не привязана ни к какому виджету. Вместо этого PhAB сгенерирует описание, которое Вы используете в своём программном коде, чтобы задать, какую внутреннююю связь Вы хотите использовать. PhAB предоставляет несколько функций, помогающих Вам использовать внутренние связи (обсуждаются ниже).