Главная » Просмотр файлов » Руководство программиста в Photon

Руководство программиста в Photon (953920), страница 61

Файл №953920 Руководство программиста в Photon (Руководство программиста в Photon) 61 страницаРуководство программиста в Photon (953920) страница 612013-09-22СтудИзба
Просмтор этого файла доступен только зарегистрированным пользователям. Но у нас супер быстрая регистрация: достаточно только электронной почты!

Текст из файла (страница 61)

event –>flags |= Ph_EVENT_DIRECT;

Вот пример:

static void send_key( long key ) {

struct {

PhEvent_t event;

PhRect_t rect;

PhKeyEvent_t pevent;

} new_event;

PhEvent_t event;

PhKeyEvent_t key_event;

PhRect_t rect;

rect.ul.x = rect.ul.y = 0;

rect.lr.x = rect.lr.y = 0;

memset( &event, 0, sizeof(event));

memset( &key_event, 0, sizeof(key_event) );

event.type = Ph_EV_KEY;

event.emitter.rid = Ph_DEV_RID;

event.num_rects = 1;

event.data_len = sizeof(key_event);

event.input_group = 1;

key_event.key_cap = key;

key_event.key_sym = key;

if ( isascii( key ) && isupper( key ) ) {

key_event.key_mods = Pk_KM_Shift;

}

/* Генерирование нажатия клавиши */

key_event.key_flags = Pk_KF_Sym_Valid | Pk_KF_Cap_Valid | Pk_KF_Key_Down;

PhEmit( &event, &rect, &key_event );

/* Генерирование отпускания клавиши */

key_event.key_flags &= ~(Pk_KF_Key_Down | Pk_KF_Sym_Valid) ;

PhEmit( &event ,&rect, &key_event );

return;

}

Координаты события

Когда генерируется событие, координаты его прямоугольника устанавливаются относительно начала координат генерирующего региона. Но когда событие принимается, его координаты становятся относительными к началу координат региона-накопителя.

Менеджер Photon'а обеспечивает это путём соответствующего пересчёта координат. Член translation в структуре PhEvent_t задаёт пересчёт между началами координат генерирующего региона и региона-накопителя.

Обработчики события – необработанные и отфильтрованные ответные реакции

Виджетный класс PtWidget предоставляет для обработки событий такие ответные реакции:

Pt_CB_FILTER

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

Pt_CB_RAW

Эти ответные реакции вызываются после того, как виджет обработал событие, даже если методы виджетного класса это событие поглощают.

Эти ответные реакции вызываются каждый раз, когда принимается событие Photon'а, совпадающее с маской событий (предоставленной приложением). Поскольку все классы виджетов библиотеки виджетов Photon'а являются потомками класса PtWidget, эти ответные реакции могут использоваться любым виджетом библиотеки виджетов Photon'а.

 Когда Вы прикрепляете к виджету необработанную или отфильтрованную ответную реакцию, библиотека виджета создаёт, если это необходимо, регион, который будет отлавливать для виджета заданные события. Это увеличивает количество регионов, которыми должен управлять менеджер Photon'а, и как результат, может приводить к понижению производительности.

Из этих соображений используйте обработчики событий только тогда, когда Вам надо делать нечто, что не может быть выполнено с помощью стандартных ответных реакций виджета. Если Вы всё-таки используете обработчики событий, рассмотрите возможность использования их только в оконных виджетах, которые уже имеют регионы.

Каждый раз, когда поступает событие Photon'а, оно спускается по иерархии семейства виджета до тех пор, пока виджет его не поглотит. (Когда виджет обработал событие и исключил взаимодействие другого виджета с этим событием, говорят, что первый виджет поглотил событие).

В основном ответные реакции Pt_CB_FILTER вызываются при проходе вниз по иерархии, а ответные реакции Pt_CB_RAW – при проходе вверх. Каждый виджет обрабатывает событие подобным образом:

  1. Ответные реакции Pt_CB_FILTER виджета вызываются, если тип события совпадает с маской ответной реакции. Код возврата ответной реакции указывает, что произошло с событием:

Pt_CONSUME

Событие поглощено, без обработки методами класса виджета.

Pt_PROCESS

Методам класса виджета было позволено обработать событие.

Pt_IGNORE

Событие проигнорировало виджет и всех его потокомков, как будто их и не существовало.

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

  1. Если виджет поглотил событие, вызываются ответные реакции Pt_CB_RAW – если тип события совпадает с маской ответной реакции. Необработанные ответные реакции родителей виджета не вызываются.

  1. Если виджет не поглотил событие, событие проходит на потомков виджета, если таковые имеются.

  1. Если никакой виджет не поглотил событие, оно проходит обратно по иерархии семейства, и вызывается каждая ответная реакция Pt_CB_RAW виджета (если тип события совпадает с маской ответной реакции). Значение, возвращаемое ответной реакцией Pt_CB_RAW виджета, указывает, что произошло с событием:

Pt_CONSUME

Событие поглотилось, и при прохождении наверх к родителю виджета никакие другие необработанные ответные реакции не вызывались

Pt_CONTINUE

Событие прошло наверх к родителю виджета

 Если виджет отключён (напр., в его флагах Pt_ARG_FLAGS выставлен флаг Pt_BLOCKED), необработанные и отфильтрованные ответные реакции не вызываются. Вместо них вызываются (если имеются) ответные реакции Pt_CB_BLOCKED виджета.

Давайте рассмотрим простенькое семейство виджетов, чтобы посмотреть, как это всё работает. Допустим, Вы имеете окно, содержащее панель, которая содержит кнопку. Вот что обычно происходит, когда Вы щёлкаете по кнопке:

  1. Вызываются ответные реакции Pt_CB_FILTER окна, но событие не поглощается. Методы класса виджета тоже не поглощают событие.

  2. Событие проходит к панели. Ни её ответные реакции Pt_CB_FILTER, ни её методы класса не поглощают событие.

  3. Событие проходит к кнопке. Её ответные реакции Pt_CB_FILTER не поглощают событие, но это делают методы её класса; вызывается соответствующая ответная реакция (напр., Pt_CB_ACTIVATE).

  4. Для события вызывается ответная реакция Pt_CB_RAW кнопки.

  5. Ответные реакции Pt_CB_RAW панели и окна не вызываются, поскольку кнопка поглотила событие.

Если ответная реакция Pt_CB_FILTER панели указывает проигнорировать событие:

  1. Окно обрабатывает событие, как и раньше

  2. Ответная реакция Pt_CB_FILTER панели указывает проигнорировать событие, так что панель и все её потомки пропускаются.

  3. Больше виджетов в семье нет, так что вызывается ответная реакция Pt_CB_RAW окна.

Более подробно о добавлении обработчиков событий смотри в:

  • разделе "Обработчики событий – необработанные и отфильтованные ответные реакции" в главе "Редактирование ресурсов и ответных реакций в PhAB";

  • разделе "Обработчики событий" главы "Уравление виджетами в программном коде приложения".

Накопление событий

Большинство приложений набирают события через вызов функции PtMainLoop(). Эта подпрограмма обрабатывает события Photon'а и поддерживает рабочие процедуры и обработку ввода. Если в Вашем приложении виджеты не используются, Вы можете накапливать события:

  • асинхронно, вызывая функцию PhEventRead(). Перед тем, как в первый раз вызвать PhEventRead(), Вы должны вызвать функцию PhEventArm().

  • синхронно, вызывая функциюPhEventNext(). Вы можете проверять наличие событий без блокировки, вызывая PhEventPeek().

Однако написание Вашей собственной функции главной петли не является тривиальной задачей; проще создать отдельный виджет (такой как PtRegion или PtWindow) и затем использовать PtMainLoop().

Функция PhGetRects() получает набор прямоугольников, и функция PhGetData() – порцию данных для события.

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

Сжатие событий

Менеджер Photon'а сжимает события перетаскивания, границ и мыши. То есть, если висит событие этого типа, когда поступает другое событие, новое событие будет подсоединено к необработанным событиям. В результате приложение видит для этих событий только самые последние значения и уберегается от накопления слишком большого количества ненужных событий.

Перетаскивание

Если Вам необходимо зафиксировать координаты мыши, например, для перетаскивания графических объектов в Вашем приложении, Вам понадобится работать с событиями.

 Если Вам надо перенести произвольные данные внутри Вашего приложения или между приложениями, почитайте главу "Тащи и бросай".

Имеется два типа перетаскивания:

  • контурное перетаскивание

Пользователь при перетаскивании видит контур. Когда перетаскивание завершено, приложение переставляет виджет.

  • непрозрачное перетаскивание

Приложение перемещает виджет как продвигающееся перетаскивание.

Перетаскивание выполняется в два этапа:

  1. Инициализация перетаскивания, обычно когда пользователь щёлкает мышью на чём-то.

  2. Обработка событий перетаскивания (Ph_EV_DRAG).

Эти шаги обсуждаются в нижеследующих подразделах.

Инициализация перетаскивания

Где Вы инициализируете перетаскивание, зависит от того, как пользователь собирается перетаскивать виджеты. Например, если пользователь удерживает нажатой левую кнопку мыши на виджете, чтобы его перетащить, перетаскивание инициализируется в ответной реакции Arm (Pt_CB_ARM) или Outbound (Pt_CB_OUTBOUND) виджета. Убедитесь, что в ресурсе Pt_ARG_FLAGS виджета установлен флаг Pt_SELECTABLE.

Перетаскивание начинается с вызова функции PhInitDrag():

int PhInitDrag(PhRid_t rid,

unsigned flags,

PhRect_t *rect,

PhRect_t *boundary,

unsigned int input_group,

PhDim_t *min,

PhDim_t *max,

const PhDim_t *step,

const PhPoint_t *ptrpos,

const PhCursorDescription_t *cursor );

где используемые аргументы:

rid

Идентификатор региона, с которым связаны rect и boundary. Вы можете получить его, вызвав функцию PtWidgetRid().

flags

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

rect

Структура RhRect_t (см. "Справочник библиотечных функций Photon'а"), которая определяет область перетаскивания.

boundary

Прямоугольная область, ограничивающая перетаскивание .

input_group

Получить это можно из события в параметре cbinfo ответной реакции, вызвав функцию PhInputGroup().

min, max

Указатели на структуры типа Ph_Dim_t (см. "Справочник библиотечных функций Photon'а"), которые определяют минимальный и максимальный размеры перетаскиваемого прямоугольника.

step

Ступенчатость перетаскивания.

ptrpos

Если не NULL, то это указатель на структуру PhPoint_t (см. "Справочник библиотечных функций Photon'а"), который определяет начальную позицию курсора для перетаскивания. Приложения должны брать его от события, которое вызывает решение на начало перетаскивания. Если курсов переместился из этой позиции за время, когда Ваш PhInitDrag() достигнул Photon'а, Ваше перетаскивание соответствующим образом обновляется. Другими словами, Photon делает поведение перетаскивания таким, что оно как бы началось оттуда, где Вы думали был курсор, а не оттуда, где он был в действительности несколькими мгновениями позже.

cursor

Если не NULL, определяет, как курсор должен выглядеть при перетаскивании.

Если во flags включён Ph_DRAG_TRACK, используется непрозрачное перетаскивание; если ph_DRAG_TRACK не включён – контурное. Следующие флаги указывают, какой край (края) перетаскиваемого прямоугольника оставляет след:

  • Ph_TRACK_LEFT – левый

  • Ph_TRACK_RIGHT – правый

  • Ph_TRACK_TOP – верхний

  • Ph_TRACK_BOTTOM – нижний

  • Ph_TRACK_DRAG – все вышеперечисленные

Контурное перетаскивание

Следующий пример демонстрирует ответную реакцию Arm (Pt_CB_ARM), которая инициализирует контурное перетаскивание:

/* Запуск перетаскивания виджета */

/* Стандартные хеадеры */

#include <stdio.h>

#include <stdlib.h>

#include <unistd.h>

#include <string.h>

/* Инструментальные хеадеры */

#include <Ph.h>

#include <Pt.h>

#include <Ap.h>

Характеристики

Тип файла
Документ
Размер
7,62 Mb
Тип материала
Высшее учебное заведение

Список файлов книги

Свежие статьи
Популярно сейчас
А знаете ли Вы, что из года в год задания практически не меняются? Математика, преподаваемая в учебных заведениях, никак не менялась минимум 30 лет. Найдите нужный учебный материал на СтудИзбе!
Ответы на популярные вопросы
Да! Наши авторы собирают и выкладывают те работы, которые сдаются в Вашем учебном заведении ежегодно и уже проверены преподавателями.
Да! У нас любой человек может выложить любую учебную работу и зарабатывать на её продажах! Но каждый учебный материал публикуется только после тщательной проверки администрацией.
Вернём деньги! А если быть более точными, то автору даётся немного времени на исправление, а если не исправит или выйдет время, то вернём деньги в полном объёме!
Да! На равне с готовыми студенческими работами у нас продаются услуги. Цены на услуги видны сразу, то есть Вам нужно только указать параметры и сразу можно оплачивать.
Отзывы студентов
Ставлю 10/10
Все нравится, очень удобный сайт, помогает в учебе. Кроме этого, можно заработать самому, выставляя готовые учебные материалы на продажу здесь. Рейтинги и отзывы на преподавателей очень помогают сориентироваться в начале нового семестра. Спасибо за такую функцию. Ставлю максимальную оценку.
Лучшая платформа для успешной сдачи сессии
Познакомился со СтудИзбой благодаря своему другу, очень нравится интерфейс, количество доступных файлов, цена, в общем, все прекрасно. Даже сам продаю какие-то свои работы.
Студизба ван лав ❤
Очень офигенный сайт для студентов. Много полезных учебных материалов. Пользуюсь студизбой с октября 2021 года. Серьёзных нареканий нет. Хотелось бы, что бы ввели подписочную модель и сделали материалы дешевле 300 рублей в рамках подписки бесплатными.
Отличный сайт
Лично меня всё устраивает - и покупка, и продажа; и цены, и возможность предпросмотра куска файла, и обилие бесплатных файлов (в подборках по авторам, читай, ВУЗам и факультетам). Есть определённые баги, но всё решаемо, да и администраторы реагируют в течение суток.
Маленький отзыв о большом помощнике!
Студизба спасает в те моменты, когда сроки горят, а работ накопилось достаточно. Довольно удобный сайт с простой навигацией и огромным количеством материалов.
Студ. Изба как крупнейший сборник работ для студентов
Тут дофига бывает всего полезного. Печально, что бывают предметы по которым даже одного бесплатного решения нет, но это скорее вопрос к студентам. В остальном всё здорово.
Спасательный островок
Если уже не успеваешь разобраться или застрял на каком-то задание поможет тебе быстро и недорого решить твою проблему.
Всё и так отлично
Всё очень удобно. Особенно круто, что есть система бонусов и можно выводить остатки денег. Очень много качественных бесплатных файлов.
Отзыв о системе "Студизба"
Отличная платформа для распространения работ, востребованных студентами. Хорошо налаженная и качественная работа сайта, огромная база заданий и аудитория.
Отличный помощник
Отличный сайт с кучей полезных файлов, позволяющий найти много методичек / учебников / отзывов о вузах и преподователях.
Отлично помогает студентам в любой момент для решения трудных и незамедлительных задач
Хотелось бы больше конкретной информации о преподавателях. А так в принципе хороший сайт, всегда им пользуюсь и ни разу не было желания прекратить. Хороший сайт для помощи студентам, удобный и приятный интерфейс. Из недостатков можно выделить только отсутствия небольшого количества файлов.
Спасибо за шикарный сайт
Великолепный сайт на котором студент за не большие деньги может найти помощь с дз, проектами курсовыми, лабораторными, а также узнать отзывы на преподавателей и бесплатно скачать пособия.
Популярные преподаватели
Добавляйте материалы
и зарабатывайте!
Продажи идут автоматически
6417
Авторов
на СтудИзбе
307
Средний доход
с одного платного файла
Обучение Подробнее