ARV 0 17 января, 2012 Опубликовано 17 января, 2012 · Жалоба пытаюсь понять, как работать с этим контроллером (дисплей 128х160 WinStar). главное, что меня интересует: могу ли я использовать имеющуюся на борту контроллера память в качестве буферной для графики? ее вроде гораздо больше, чем нужно для одного экрана, хочу сделать видимую и фоновую страницы, чтобы пока смотрим на видимую, рисовать в фоновой, а потом резко поменять их местами. но документация моему скромному уму не поддается, я с этой адресацией не могу понять - реально это сделать или нет? если кто разобрался с этой темой - подскажите, пожалуйста! обычно для графических дисплеев в документации показано какое-то графическое соотношение между адресами памяти и позициями на дисплее - тут же нету этого, а по словесному описанию не врубаюсь :( Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
minimumlaw 0 17 января, 2012 Опубликовано 17 января, 2012 · Жалоба Да можно Суть в следующем - назначаете адрес графики допустим на ноль. Отображается страница с нулевого адреса. Считаете, что следующая (фоновая) страница начинается с (128х160/8) Рисуете там с помощью write или write auto Назначаете адрес графики на (128х160/8) Теперь фоновая страница начинается с нуля. Рисуете там Важно. Не забудьте назначить и почистить область текста и шрифта. А также правила наложения одного на другое. Контроллер знатный - легко прошивается шрифтом в основных однобайтовых кодировках - так что текст лучше выводить нативно (много быстрее получится) чем заморочиваться в отрисовкой в графику. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 17 января, 2012 Опубликовано 17 января, 2012 · Жалоба большое спасибо! я примерно так и думал. еще вопрос, если не затруднит: поясните мне, что такое Graphic Area? я так понимаю, Graphic Home - это как раз начало графической страницы, а Area что такое? в других контроллерах была возможность задать "окно" в пределах графической области, и тогда последовательный вывод данных построчно заполнял эту область переходя к очередной строке при достижении правого края (или другого края - это тонкости). а в данном контроллере что-то снова мутное написано... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
minimumlaw 0 17 января, 2012 Опубликовано 17 января, 2012 (изменено) · Жалоба Этот контроллер может работать с разными размерами экрана. Я, например, использовал его в режиме 128х64. Так вот Graphic Area это в зависимости от контекста либо текущая (отображаемая на экран) область памяти, либо значение в байтах одной строки пикселей. Про второе подробнее - у экрана формат отображения - неупакованный битмап, т.е. фактически рисуем на компе bmp и посылаем его данные прямо в контроллер. Ближе к делу - первый байт области это первые 8 горизонтальных точек в строке (у большинства контроллеров это таки первые точки восьми строк). Таким образ для моего 128х64 - GraphicsArea (182/8=16 байт). для Вашего 128х160 - (160/8=20 байт) Технически, я бы мог задать graphicsArea и в 20 - реально отображалось бы все равно 128. Но переход на новую строку происходил бы по смещению 20 - лазеечка для организации горизонтального скролинга (правда, довольно бестолковая - ибо попиксельного скрола все равно не получается) Это, конечно, если я ничего не путаю. Уже года два как его не касался. Изменено 17 января, 2012 пользователем Alex A. Mihaylov Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ARV 0 17 января, 2012 Опубликовано 17 января, 2012 · Жалоба первый байт области это первые 8 горизонтальных точек в строке (у большинства контроллеров это таки первые точки восьми строк). Таким образ для моего 128х64 - GraphicsArea (182/8=16 байт). для Вашего 128х160 - (160/8=20 байт)сразу очередной вопрос: первые точки - имеется ввиду левый верхний угол дисплея? а если я для своего дисплея задам GraphicArea = 10, и буду выводить сплошным потоком 0xFF - у меня зальется левая половина дисплея? что-то вот этот момент я не улавливаю... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 12 мая, 2012 Опубликовано 12 мая, 2012 (изменено) · Жалоба Тоже имеются траблы с этим контроллером. Точнее - RA6963 от Raio, но читал, что он полностью совместим с тошибовским. Дисплей - WG24064A. Для начала приведу часть кода инициализации: uint32_t i; // здесь настройка портов и сброс lcd_write_data (0); lcd_write_data (0); lcd_send_cmd (0x40); // Set Text Home Address lcd_write_data (30); lcd_write_data (0); lcd_send_cmd (0x41); // Set Text Area lcd_write_data (0x00); lcd_write_data (0x08); lcd_send_cmd (0x42); // Set Graphic Home Address lcd_write_data (30); lcd_write_data (0); lcd_send_cmd (0x43); // Set Graphic Area lcd_send_cmd (0x81); // Internal CG ROM mode, EXOR mode lcd_send_cmd (0x98); // Text off, graphic on, cursor off После инициализации выполняю такой цикл: lcd_write_data (0x00); lcd_write_data (0x08); lcd_send_cmd (0x24); // указатель адреса на "Graphic Home Address" for (i = 0; i < 1920; i++) { lcd_write_data (0x00); lcd_send_cmd (0xC0); // посылаем байт данных, авто-инкремент указателя адреса }; По идее, после выполнения этого кода экран должен полностью очиститься, но на деле не совсем так, последние несколько(вроде бы 64) точек последней строки остаются заполненными случайными значениями. Если медленно выполнять запись "пустых" байтов и следить за происходящим, то видно, что на подходе к концу текущей стираемой строки(т.е. данная строка еще не стерлась полностью, осталось достаточно много), начинает стираться следующая за ней строка! Ума не приложу, что за фигня происходит. Да и просто после этой "недоочистки" если попробовать записать байт в произвольное место, то, скажу кратко - на экране отображается не то, что должно быть. Ну и пара небольших вопросов: Понятия "курсор" в отношении данного дисплея действительно лишь в текстовом режиме? Не совсем понятно, зачем нужен Offset регистр, что это за смещение? Если использовать только графический режим, можно ли вообще не трогать этот регистр? Также не ясно, какую память выбрать - Internal CG ROM, или External CG RAM. Пересмотрел достаточно исходников, вроде как у меня все аналогично, но проблема откуда-то появилась... И да, даташит: RA6963.pdf Изменено 12 мая, 2012 пользователем ohmjke Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 12 мая, 2012 Опубликовано 12 мая, 2012 · Жалоба Блиин, кто бы мог подумать, вся эта ерунда была оказывается из-за того, что пин FS(font select) висел в воздухе, поэтому поочередно выбирались разные размеры шрифтов. Я как-то даже сразу и не подумал подцепить его куда-нибудь, наверное, предположил, что есть подтяжка по умолчанию. Собственно, остальные вопросы тоже отпадают, т.к. пока искал решение своей проблемы прочитал один хороший документ по этому контроллеру и со всем разобрался. Ура! Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 29 мая, 2012 Опубликовано 29 мая, 2012 (изменено) · Жалоба Не могу понять, из-за чего происходит искажение. Видно в начале видео, на 3 и 5 секундах. В памяти МК буфер, раз в секунду передаю его в память дисплея. http://youtu.be/-NpJY1v_lI8 Изменено 29 мая, 2012 пользователем ohmjke Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
GenaSPB 11 29 мая, 2012 Опубликовано 29 мая, 2012 · Жалоба Не могу понять, из-за чего происходит искажение. Видно в начале видео, на 3 и 5 секундах. В памяти МК буфер, раз в секунду передаю его в память дисплея. http://youtu.be/-NpJY1v_lI8 На 14-й странице мануала написано про необходимость проверять статус перед выдачей команд. Делаете? If a status check is not carried out in this state before the next command is sent, there is the possibility that command or data will not be received. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 30 мая, 2012 Опубликовано 30 мая, 2012 · Жалоба На 14-й странице мануала написано про необходимость проверять статус перед выдачей команд. Делаете? Да, делаю. Просто что странно - то все изображение выводится идеально, то с искажениями, в среднем соотношение 50/50. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
GenaSPB 11 30 мая, 2012 Опубликовано 30 мая, 2012 (изменено) · Жалоба Да, делаю. Просто что странно - то все изображение выводится идеально, то с искажениями, в среднем соотношение 50/50. Вставьте задержку микросекунд на 10..20 на установление данных на сигналах перед выдачей стробов. Да, не лтишне было бы выложить исходник проекта (или той функции, что зовётся lcd_write_data и lcd_send_cmd вместе с вызываемыми внутри их функциями. Изменено 30 мая, 2012 пользователем Genadi Zawidowski Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 30 мая, 2012 Опубликовано 30 мая, 2012 · Жалоба Не уверен в расчетах, так как неизвестно сколько выполняется итерация цикла, но, по-моему, от таких задержек стало еще хуже. Ниже исходники модуля(без задержек после вывода данных на шину). #include "lcd.h" uint8_t lcd_buffer [LCD_HEIGHT][LCD_WIDTH / 8]; extern void lcd_init (void) { uint32_t i; RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN; CONTROL_GPIO->CRL &= ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; CONTROL_GPIO->CRH &= ~GPIO_CRH_CNF8 & ~GPIO_CRH_MODE8 & ~GPIO_CRH_CNF9 & ~GPIO_CRH_MODE9; CONTROL_GPIO->CRL |= GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1 | GPIO_CRL_MODE6_0 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_0 | GPIO_CRL_MODE7_1; CONTROL_GPIO->CRH |= GPIO_CRH_MODE8_0 | GPIO_CRH_MODE8_1 | GPIO_CRH_MODE9_0 | GPIO_CRH_MODE9_1; DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_MODE0_0 | GPIO_CRL_MODE0_1 | GPIO_CRL_MODE1_0 | GPIO_CRL_MODE1_1 \ | GPIO_CRL_MODE2_0 | GPIO_CRL_MODE2_1 | GPIO_CRL_MODE3_0 | GPIO_CRL_MODE3_1 \ | GPIO_CRL_MODE4_0 | GPIO_CRL_MODE4_1 | GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1 \ | GPIO_CRL_MODE6_0 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_0 | GPIO_CRL_MODE7_1; CONTROL_GPIO->BSRR = CHIPEN_SET | RD_SET | WR_SET | RESET_CLEAR; for (i = 0; i < 0xFFFF; i++); CONTROL_GPIO->BSRR = RESET_SET; lcd_write_data (GRAPHIC_HOME_ADRESS & 0xFF); lcd_write_data (GRAPHIC_HOME_ADRESS >> 8); lcd_send_cmd (SET_GRAPHIC_HOME_ADRESS); lcd_write_data (GRAPHIC_AREA); lcd_write_data (0x00); lcd_send_cmd (SET_GRAPHIC_AREA); lcd_write_data (TEXT_HOME_ADRESS & 0xFF); lcd_write_data (TEXT_HOME_ADRESS >> 8); lcd_send_cmd (SET_TEXT_HOME_ADRESS); lcd_write_data (TEXT_AREA); lcd_write_data (0x00); lcd_send_cmd (SET_TEXT_AREA); lcd_send_cmd (MODE_SET | MODE_SET_OR | MODE_SET_INT_CG); lcd_send_cmd (DISPLAY_MODE | DISPLAY_MODE_TEXT_OFF_GRAPHIC_ON); }; extern void lcd_refresh (void) { uint_fast16_t i; uint8_t *ptr = &(lcd_buffer [0][0]); lcd_write_data (GRAPHIC_HOME_ADRESS & 0xFF); lcd_write_data (GRAPHIC_HOME_ADRESS >> 8); lcd_send_cmd (SET_ADRESS_POINTER); lcd_send_cmd (SET_DATA_AUTO_WRITE); for (i = 0; i < (LCD_HEIGHT * (LCD_WIDTH / 8)); i++) { lcd_auto_write_data (*ptr); ptr++; }; lcd_send_cmd (AUTO_RESET); }; extern void lcd_send_cmd (uint8_t cmd) { uint32_t i; DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_CNF0_0 | GPIO_CRL_CNF1_0 | GPIO_CRL_CNF2_0 | GPIO_CRL_CNF3_0 \ | GPIO_CRL_CNF4_0 | GPIO_CRL_CNF5_0 | GPIO_CRL_CNF6_0 | GPIO_CRL_CNF7_0; do { CONTROL_GPIO->BSRR = CHIPEN_CLEAR | RD_CLEAR | CHOOSE_CODE; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | RD_SET; } while ((DATA_GPIO->IDR & 0x03) != 0x03); DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_MODE0_0 | GPIO_CRL_MODE0_1 | GPIO_CRL_MODE1_0 | GPIO_CRL_MODE1_1 \ | GPIO_CRL_MODE2_0 | GPIO_CRL_MODE2_1 | GPIO_CRL_MODE3_0 | GPIO_CRL_MODE3_1 \ | GPIO_CRL_MODE4_0 | GPIO_CRL_MODE4_1 | GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1 \ | GPIO_CRL_MODE6_0 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_0 | GPIO_CRL_MODE7_1; DATA_GPIO->ODR &= ~0xFF; DATA_GPIO->ODR |= cmd; CONTROL_GPIO->BSRR = CHIPEN_CLEAR | WR_CLEAR | CHOOSE_CODE; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | WR_SET; }; extern void lcd_write_data (uint8_t data) { uint_fast8_t i; DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_CNF0_0 | GPIO_CRL_CNF1_0 | GPIO_CRL_CNF2_0 | GPIO_CRL_CNF3_0 \ | GPIO_CRL_CNF4_0 | GPIO_CRL_CNF5_0 | GPIO_CRL_CNF6_0 | GPIO_CRL_CNF7_0; do { CONTROL_GPIO->BSRR = CHIPEN_CLEAR | RD_CLEAR | CHOOSE_CODE; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | RD_SET; } while ((DATA_GPIO->IDR & 0x03) != 0x03); DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_MODE0_0 | GPIO_CRL_MODE0_1 | GPIO_CRL_MODE1_0 | GPIO_CRL_MODE1_1 \ | GPIO_CRL_MODE2_0 | GPIO_CRL_MODE2_1 | GPIO_CRL_MODE3_0 | GPIO_CRL_MODE3_1 \ | GPIO_CRL_MODE4_0 | GPIO_CRL_MODE4_1 | GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1 \ | GPIO_CRL_MODE6_0 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_0 | GPIO_CRL_MODE7_1; DATA_GPIO->ODR &= ~0xFF; DATA_GPIO->ODR |= data; CONTROL_GPIO->BSRR = CHIPEN_CLEAR | WR_CLEAR | CHOOSE_DATA; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | WR_SET; }; extern void lcd_auto_write_data (uint8_t data) { uint_fast8_t i; DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_CNF0_0 | GPIO_CRL_CNF1_0 | GPIO_CRL_CNF2_0 | GPIO_CRL_CNF3_0 \ | GPIO_CRL_CNF4_0 | GPIO_CRL_CNF5_0 | GPIO_CRL_CNF6_0 | GPIO_CRL_CNF7_0; do { CONTROL_GPIO->BSRR = CHIPEN_CLEAR | RD_CLEAR | CHOOSE_CODE; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | RD_SET; } while ((DATA_GPIO->IDR & 0x08) != 0x08); DATA_GPIO->CRL &= ~GPIO_CRL_CNF0 & ~GPIO_CRL_CNF1 & ~GPIO_CRL_CNF2 & ~GPIO_CRL_CNF3 \ & ~GPIO_CRL_CNF4 & ~GPIO_CRL_CNF5 & ~GPIO_CRL_CNF6 & ~GPIO_CRL_CNF7 \ & ~GPIO_CRL_MODE0 & ~GPIO_CRL_MODE1 & ~GPIO_CRL_MODE2 & ~GPIO_CRL_MODE3 \ & ~GPIO_CRL_MODE4 & ~GPIO_CRL_MODE5 & ~GPIO_CRL_MODE6 & ~GPIO_CRL_MODE7; DATA_GPIO->CRL |= GPIO_CRL_MODE0_0 | GPIO_CRL_MODE0_1 | GPIO_CRL_MODE1_0 | GPIO_CRL_MODE1_1 \ | GPIO_CRL_MODE2_0 | GPIO_CRL_MODE2_1 | GPIO_CRL_MODE3_0 | GPIO_CRL_MODE3_1 \ | GPIO_CRL_MODE4_0 | GPIO_CRL_MODE4_1 | GPIO_CRL_MODE5_0 | GPIO_CRL_MODE5_1 \ | GPIO_CRL_MODE6_0 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_0 | GPIO_CRL_MODE7_1; DATA_GPIO->ODR &= ~0xFF; DATA_GPIO->ODR |= data; CONTROL_GPIO->BSRR = CHIPEN_CLEAR | WR_CLEAR | CHOOSE_DATA; for (i = 0; i < 5; i++); CONTROL_GPIO->BSRR = CHIPEN_SET | WR_SET; }; #ifndef __LCD_H #define __LCD_H #define STM32F10X_MD_VL #include "stm32f10x.h" #define SYSCLK_FREQ (24000000UL) #define CONTROL_GPIO (GPIOB) #define DATA_GPIO (GPIOA) #define WR_SET (GPIO_BSRR_BS8) #define WR_CLEAR (GPIO_BSRR_BR8) #define RD_SET (GPIO_BSRR_BS7) #define RD_CLEAR (GPIO_BSRR_BR7) #define CHIPEN_SET (GPIO_BSRR_BS6) #define CHIPEN_CLEAR (GPIO_BSRR_BR6) #define CHOOSE_CODE (GPIO_BSRR_BS5) #define CHOOSE_DATA (GPIO_BSRR_BR5) #define RESET_SET (GPIO_BSRR_BS9) #define RESET_CLEAR (GPIO_BSRR_BR9) #define LCD_HEIGHT (64) #define LCD_WIDTH (240) #define FONT_SIZE (8) #define GRAPHIC_HOME_ADRESS (0x2000UL) #define GRAPHIC_AREA (LCD_WIDTH / 8) #define TEXT_HOME_ADRESS (0x0000UL) #define TEXT_AREA (LCD_WIDTH / FONT_SIZE) #define SET_TEXT_HOME_ADRESS (0x40) #define SET_GRAPHIC_HOME_ADRESS (0x42) #define SET_TEXT_AREA (0x41) #define SET_GRAPHIC_AREA (0x43) #define SET_ADRESS_POINTER (0x24) #define DATA_WRITE_AND_INCREMENT_ADP (0xC0) #define SET_DATA_AUTO_WRITE (0xB0) #define AUTO_RESET (0xB2) #define MODE_SET (0x80) #define MODE_SET_OR (0x00) #define MODE_SET_EXOR (0x01) #define MODE_SET_AND (0x03) #define MODE_SET_ATTRIBUTE (0x04) #define MODE_SET_INT_CG (0x00) #define MODE_SET_EXT_CG (0x08) #define DISPLAY_MODE (0x90) #define DISPLAY_MODE_TEXT_ON_GRAPHIC_OFF (0x04) #define DISPLAY_MODE_TEXT_OFF_GRAPHIC_ON (0x08) #define DISPLAY_MODE_TEXT_ON_GRAPHIC_ON (0x0C) #define DISPLAY_MODE_CURSOR_ON_BLINK_OFF (0x02) #define DISPLAY_MODE_CURSOR_ON_BLINK_ON (0x03) extern uint8_t lcd_buffer [LCD_HEIGHT][LCD_WIDTH / 8]; extern void lcd_refresh (void); extern void lcd_init (void); extern void lcd_send_cmd (uint8_t cmd); extern void lcd_write_data (uint8_t data); extern void lcd_auto_write_data (uint8_t data); #endif Кстати, использование обычного режима записи данных (не auto), ничего не меняет. extern void lcd_refresh (void) { uint_fast16_t i; uint8_t *ptr = &(lcd_buffer [0][0]); lcd_write_data (GRAPHIC_HOME_ADRESS & 0xFF); lcd_write_data (GRAPHIC_HOME_ADRESS >> 8); lcd_send_cmd (SET_ADRESS_POINTER); for (i = 0; i < (LCD_HEIGHT * (LCD_WIDTH / 8)); i++) { lcd_write_data (*ptr); lcd_send_cmd (DATA_WRITE_AND_INCREMENT_ADP); ptr++; }; }; Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
GenaSPB 11 1 июня, 2012 Опубликовано 1 июня, 2012 (изменено) · Жалоба То, что стало хуже - не наводит на размышления? В документе на контроллер нет слов про ограничения по минимальной скорости. После установки стробов внесите задержки - и не такие циклы, как у Вас, которые выкидываются при оптимизации. DATA_GPIO->ODR &= ~0xFF; /* тут поставить задержку */ DATA_GPIO->ODR |= cmd; /* тут поставить задержку */ CONTROL_GPIO->BSRR = CHIPEN_CLEAR | WR_CLEAR | CHOOSE_CODE; /* тут поставить задержку */ CONTROL_GPIO->BSRR = CHIPEN_SET; /* тут поставить задержку */ CONTROL_GPIO->BSRR = WR_SET; /* тут поставить задержку перед снятием строба */ Функция задержки хоть такая: void _delay_us(int timeUS) { const int top = timeUS * 175 / (CPU_FREQ / 1000000); // volatile int n; for (n = 0; n < top; ++ n) { } } Изменено 1 июня, 2012 пользователем Genadi Zawidowski Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
ohmjke 0 5 сентября, 2012 Опубликовано 5 сентября, 2012 (изменено) · Жалоба Пробовал по-всякому - ничего не помогает. Может ли это быть просто браком? Экранировал зад платы, подключал контур к земле - безрезультатно. Повторюсь, как я считаю, нужно обязательно учитывать тот факт, что искажение изображения происходит не постоянно, а, в среднем, в половине случаев. Изменено 5 сентября, 2012 пользователем ohmjke Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
GenaSPB 11 5 сентября, 2012 Опубликовано 5 сентября, 2012 · Жалоба Пробовал по-всякому - ничего не помогает. Может ли это быть просто браком? Покажите тестовый проект. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться