При реальной разработке выбор экрана будет ограничен такими факторами, как стоимость, поставщики и эффект. В некоторых случаях необходимо повернуть приложение, чтобы оно соответствовало экрану.
AWTK по умолчанию предоставляет функцию поворота экрана на основе поворота изображения. Эта функция хорошо совместима, но её эффективность низкая, и она потребляет много ресурсов и памяти.
Теперь AWTK дополнительно предоставляет новый высокоэффективный механизм поворота, который решает вышеуказанные проблемы. Этот механизм может поддерживать высокую эффективность (почти такую же, как при отсутствии поворота), но его совместимость плохая, и для его использования необходимо выполнить следующие условия:
Примечание: высокоэффективный механизм вращения основан на векторных вычислениях. Его принцип заключается в том, что соответствующие данные преобразуются через векторные вычисления перед нижним уровнем рисования.
Если вышеуказанные условия выполнены, используйте следующий метод для эффективного поворота:
ret_t application_init(void) {
tk_enable_fast_lcd_portrait(TRUE); /* включить быстрый поворот */
tk_set_lcd_orientation(LCD_ORIENTATION_90); /* повернуть на 90 градусов */
......
return RET_OK;
}
Примечание: определение макроса WITH_FAST_LCD_PORTRAIT только компилирует связанный код в программу, а для включения функции всё ещё требуется вызвать интерфейс tk_enable_fast_lcd_portrait().
В некоторых случаях пользователь может захотеть перегрузить функцию flush для lcd. В отличие от механизма поворота по умолчанию, при включении эффективного поворота не нужно вызывать интерфейс image_rotate() для поворота изображения в функции flush. Нужно просто вызвать интерфейс image_copy() для непосредственного копирования изображения. Пример кода выглядит следующим образом:
/* awtk-linux-fb/lcd_linux/lcd_linux_fb.c */
static ret_t lcd_linux_flush(lcd_t* base, int fbid) {
......
/* Получить список грязных прямоугольников */
dirty_rects = lcd_fb_dirty_rects_get_dirty_rects_by_fb(&(lcd->fb_dirty_rects_list), buff);
if (dirty_rects != NULL && dirty_rects->nr > 0) {
for (int i = 0; i < dirty_rects->nr; i++) {
const rect_t* dr = (const rect_t*)dirty_rects->rects + i;
#ifdef WITH_FAST_LCD_PORTRAIT /* Включить эффективный поворот */
if (system_info()->flags & SYSTEM_INFO_FLAG_FAST_LCD_PORTRAIT) {
/* Повернуть грязный прямоугольник */
rect_t rr = lcd_orientation_rect_rotate_by_anticlockwise(dr, o, lcd_get_width(base), lcd_get_height(base));
/* Согласно повернутому грязному прямоугольнику, скопировать данные offline_fb в online_fb */
image_copy(&online_fb, &offline_fb, &rr, rr.x, rr.y);
} else
#endif
{ /* Если эффективный поворот не включен, вызовите интерфейс image_rotate(), чтобы повернуть изображение по умолчанию */
if (o == LCD_ORIENTATION_0) {
image_copy(&online_fb, &offline_fb, dr, dr->x, dr->y);
} else {
image_rotate(&online_fb, &offline_fb, dr, o);
}
}
}
......
}
В особых случаях пользователи могут самостоятельно адаптировать lcd, vgcanvas и g2d. В этом случае необходимо добавить соответствующий код в слой адаптации. Подробности см. ниже.
Перенос эффективного поворота требует понимания двух концепций:
/* awtk/base/bitmap.h */
/**
* @method bitmap_get_physical_line_length
* Получить фактическую длину каждой строки в памяти растрового изображения.
*
* @param {bitmap_t*} bitmap Объект растрового изображения.
*
* @return {uint32_t} Возвращает количество байтов, занимаемых каждой строкой.
*/
uint32_t bitmap_get_physical_line_length(bitmap_t* bitmap);
/**
* @method bitmap_get_physical_width
* Получить фактический физический размер растрового изображения по ширине.
* @param {bitmap_t*} bitmap Объект растрового изображения.
*
* @return {uint32_t} Возвращает ширину растрового изображения.
*/
uint32_t bitmap_get_physical_width(bitmap_t* bitmap);
/**
* @method bitmap_get_physical_height
* Получить фактический физический размер растрового изображения по высоте.
* @param {bitmap_t*} bitmap Объект растрового изображения.
*
* @return {uint32_t} Возвращает высоту растрового изображения.
*/
uint32_t bitmap_get_physical_height(bitmap_t* bitmap);
Помимо вышеуказанных интерфейсов, данные, полученные другими интерфейсами, также являются логическими данными.
Когда вы самостоятельно адаптируете lcd, vgcanvas и g2d, если вам нужно поддерживать эффективный поворот, вы можете использовать физические данные изображения при рисовании. Кроме того, при использовании грязного прямоугольника также необходимо вызвать соответствующий интерфейс для поворота координат грязного прямоугольника. Подробности см. ниже.
Необходимо добавить механизм преобразования координат данных в каждом слое рисования lcd. Например:
/* awtk/lcd/lcd_mem.inc */
/* Заполнить прямоугольник */
static ret_t lcd_mem_fill_rect_with_color(lcd_t* lcd, xy_t x, xy_t y, wh_t w, wh_t h, color_t c) {
bitmap_t fb;
#ifdef WITH_FAST_LCD_PORTRAIT
rect_t r = rect_init(x, y, w, h);
system_info_t* info = system_info();
rect_t rr = lcd_orientation_rect_rotate_by_anticlockwise(&r, info->lcd_orientation, lcd_get_width(lcd), lcd_get_height(lcd));
#else
rect_t rr = rect_init(x, y, w, h);
#endif
c.rgba.a = (c.rgba.a * lcd->global_alpha) / 0xff;
lcd_mem_init_drawing_fb(lcd, &fb);
return image_fill(&fb, &rr, c);
}
В макросе WITH_FAST_LCD_PORTRAIT мы видим, что координаты заполняемого прямоугольника преобразуются с помощью функции lcd_orientation_rect_rotate_by_anticlockwise. Функция преобразуется в новые прямоугольные координаты, после чего вызывается соответствующая функция заполнения для заполнения цветом.
/* lcd_orientation_helper.inc */
/* Ввод данных прямоугольного типа через ротацию и возврат данных прямоугольного типа */
rect_t lcd_orientation_rect_rotate_by_anticlockwise(const rect_t* rect, lcd_orientation_t o, wh_t src_limit_w, wh_t src_limit_h);
Для слоя адаптации LCD необходимо адаптировать следующие функции: (подход к адаптации можно посмотреть в коде lcd_mem.inc):
Функция | Назначение |
---|---|
fill_rect | Заполнение области прямоугольника цветом |
clear_rect | Очистка цвета области прямоугольника |
draw_image | Рисование растрового изображения |
draw_image_matrix | Рисование растрового изображения |
draw_glyph | Рисование шрифта |
get_point_color | Получение цвета по координатам |
get_physical_width | Получение реальной физической ширины |
get_physical_height | Получение реальной физической высоты |
В дополнение к основным функциям адаптации, описанным выше, при фактическом выполнении могут потребоваться дополнительные функции адаптации (например, функция set_orientation).
Адаптация слоя VGCANVAS аналогична адаптации слоя LCD, оба из которых адаптируют функции рисования, но необходимо обратить особое внимание на проблему поворота растровых изображений. Некоторые библиотеки векторных рисунков не поддерживают поворот растровых изображений.
Примечание: для повышения эффективности растровые изображения поворачиваются до указанного угла перед загрузкой в память (также называемые повернутыми растровыми изображениями), если слой VGCANVAS не поддерживает отображение повернутых изображений, необходимо определить макрос WITHOUT_FAST_LCD_PORTRAIT_FOR_IMAGE. Если используется данные растровые изображения, то при упаковке ресурсов необходимо указать угол поворота равным 0.
Основная адаптация слоя G2D заключается в добавлении следующих двух функций адаптации:
/* awtk/base/g2d.h */
/**
* @method image_rotate_ex
* @export none
* Поворачивает указанную область изображения.
* @param {bitmap_t*} dst Целевой объект изображения.
* @param {bitmap_t*} src Исходный объект изображения.
* @param {const rect_t*} src_r Область, которая должна быть повернута и скопирована.
* @param {xy_t} dx Координаты x целевого положения. (Исходная точка координат — это исходная точка повернутой системы координат, а не верхний левый угол dst).
* @param {xy_t} dy Координаты y целевого положения. (Исходная точка координат — это исходная точка повернутой системы координат, а не верхний левый угол dst).
* @param {lcd_orientation_t} o Угол поворота (обычно поддерживается 90 градусов, направление вращения против часовой стрелки).
*
* @return {ret_t} RET_OK указывает на успех, в противном случае указывает на неудачу, и в этом случае верхний уровень использует программное обеспечение для реализации.
*/
ret_t g2d_rotate_image_ex(bitmap_t* dst, bitmap_t* src, const rect_t* src_r, xy_t dx, xy_t dy, lcd_orientation_t o);
/**
* @method g2d_blend_image_rotate
* @export none
* Рендерит область изображения в указанную область framebuffer, масштабирует и поворачивает, если размеры src и dst не совпадают.
*
* @param {bitmap_t*} dst Целевой объект изображения.
* @param {bitmap_t*} src Исходный объект изображения.
* @param {const rectf_t*} dst_r Целевая область. (Исходная точка координат — это исходная точка повернутой системы координат, а не верхний левый угол dst).
* @param {const rectf_t*} src_r Исходная область.
* @param {uint8_t} global_alpha Глобальный альфа-канал.
* @param {lcd_orientation_t} o Угол поворота (обычно поддерживается 90 градусов, направление вращения против часовой стрелки).
*
* @return {ret_t} RET_OK указывает на успех, в противном случае указывает на неудачу, и в этом случае верхний уровень использует программное обеспечение для реализации.
*/
ret_t g2d_blend_image_rotate(bitmap_t* dst, bitmap_t* src, const rectf_t* dst_r, const rectf_t* src_r,
uint8_t alpha, lcd_orientation_t o);
Примечание:
- Если эти две функции не реализованы, будут вызваны soft_rotate_image_ex и soft_blend_image_rotate для программного поворота и отрисовки изображения.
- Эти две функции слоя G2D в основном используются для обработки случаев, когда угол поворота изображения равен 0, а угол поворота LCD противоположен. Если можно гарантировать, что угол поворота изображения и угол поворота LCD одинаковы, эти две функции могут не понадобиться.
Вы можете оставить комментарий после Вход в систему
Неприемлемый контент может быть отображен здесь и не будет показан на странице. Вы можете проверить и изменить его с помощью соответствующей функции редактирования.
Если вы подтверждаете, что содержание не содержит непристойной лексики/перенаправления на рекламу/насилия/вульгарной порнографии/нарушений/пиратства/ложного/незначительного или незаконного контента, связанного с национальными законами и предписаниями, вы можете нажать «Отправить» для подачи апелляции, и мы обработаем ее как можно скорее.
Опубликовать ( 0 )