Попиксельное заполнение буфера |
Здравствуйте, гость ( Вход | Регистрация )
Попиксельное заполнение буфера |
loh |
21.12.2011, 16:37
Сообщение
#1
|
Студент Группа: Участник Сообщений: 60 Регистрация: 11.5.2008 Пользователь №: 171 Спасибо сказали: 0 раз(а) Репутация: 0 |
Всем привет!
Задача такая, у меня есть датчик, типа линейного сканера, от него приходят данные представляющие собой двух байтные числа которые после некоторой математической обработки связанной с операциями сложения умножения деления вычитается превращаются либо в цвет точки. соответственно один пакет этих чисел это одна колонка пикселей на экране. Каждая новая колонка приходит на место старой, а вся картинка смещается на один пиксел в сторону. Проблема в том что частота прихода этих пакетов высокая - например 200 пакетов в секунду, Так вот! как организовать буфер для сохранения исходных значений с датчика, буфер с обработанными значениями для вывода на экран, как синхронизировать вывод с приёмом, что бы картинка смешалась плавно, без рывков? И как сделать быструю обработку исходных значений для преобразования их в цвет уже в офлайн режиме, когда данные берутся не с датчика, а с буфера исходных данных? :о |
|
|
BlueIceScream |
28.12.2011, 1:21
Сообщение
#2
|
Студент Группа: Участник Сообщений: 56 Регистрация: 21.11.2011 Из: Республика Дагестан Пользователь №: 3016 Спасибо сказали: 18 раз(а) Репутация: 3 |
Такое использование буфера будет на мой взгляд быстрее. Оно позволяет полность отказаться от использование QImage и от сдвигов.
Выделяете для буфера место в 2 раза больше нужного для представления картинки. Заполнение состоит из 2 этапов. Первый : Начинаете заполнять буффер с конца. При этом каждая новая порция попадает вперед. То есть каждое новое изображение образуется из предыдущего простой сменой адреса начала данных в буффере. Нет необходимости делать сдвиги. Для рисования используйте функцию: void glDrawPixels( GLsizei width, GLsizei height, GLenum format, GLenum type, const GLvoid * data); Она позволяет рисовать изображение заданного размера и типа, напрямую из памяти. Например: glDrawPixels(width, height, GL_RGBA, GL_UNSIGNED_BYTE, pointer); То есть при поступлении новых данных(сканированной строки) значения pointer(адрес начала данных для рисования) просто изменяется на необходимое значение. Никаких тяжелых сдвигов не нужно. А функция glDrawPixels использует аппартное ускорение для рисования. Единственная важная вещь это как хранятся данные в буффере. Они должны быть в GL формате. Например из QImage можно получить такой формат функцией: QImage QGLWidget::convertToGLFormat ( const QImage & img ) [static]. Но так как вам следует полностью избавится от QImage, то прочитайте про формат и используйте напрямую в буфере. Второй: Этот этап начинается когда данные заполнили размер буфера выделенный для изображения (вернее его половину так как выделяется в 2 раза больше места в памяти чем нужно). С этого момента данные начинают поступать в зарезервированную часть буфера. Рисование продолжается так же. Но запускает дополнительный поток который перекладывает поступившие данные на заднюю часть буфера. Когда уже буфер заполнится полностью, то первую половину будет дублировать вторая. Тогда переносим указатель на начало второй половины и работает как раньше. Как будто второй этап только начался. Как видите количество копирований максимально уменьшено. Используйте функцию glDrawPixels в событии void QGLWidget::paintGL () [virtual protected] Конечно синхронизация с остальной частью программы (в плане потоков) усложнится, но это позволит выжать максимум FPS. Сообщение отредактировал BlueIceScream - 28.12.2011, 1:24 |
|
|
Текстовая версия | Сейчас: 23.11.2024, 12:00 |