Raspberry PI 3 + OpenCV + Arduino UNO + ......(поледнее решение и вопрос в последнем сообщении)

Тема в разделе "Флудилка", создана пользователем Igor68, 21 ноя 2016.

  1. Alex19

    Alex19 Гуру

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

    Это классика, все по рекомендациям от производителя.

    Перед данным вызовом идет проверка, занят ли модуль и есть ли не обработанные данные. Потом копируем массив, разбираем команду. Да Вы можете переписать и отправить пакет, а не значение, но есть ли в этом смысл это решать Вам.

    Не использую родную библиотеку, поэтому пришлось покопаться. Там есть переход, вызов Wire.beginTransmission(returnaddress);.

    Теперь смотрим код - https://github.com/arduino/Arduino/blob/master/hardware/arduino/avr/libraries/Wire/src/Wire.cpp, там есть еще ссылка на https://github.com/codebendercc/arduino-library-files/blob/master/libraries/Wire/utility/twi.c. Так вот, выяснилось, что там тоже все сделано на прерывании и буфере:), ввел Вас в заблуждение, извините.

    beginTransmission - задаем адрес, выставляем переменную передачи данных и обнуляем переменные.
    endTransmission, вызывается twi_writeTo, делаем проверки и копируем данные в буфер I2C, и запускаем мастер.
    Код (C++):
    // send start condition
    TWCR = _BV(TWINT) | _BV(TWEA) | _BV(TWEN) | _BV(TWIE) | _BV(TWSTA);    // enable INTs
    Коротко, очищаем флаг прерывания (TWINT), разрешения бита подтверждения (TWEA), разрешаем работу модуля (TWEN), разрешения прерывания (TWIE), формируем старт (TWSTA).

    Когда данные переданы в прерывании мы попадаем twi_stop(), там формируем команду стоп, освобождая линию. Теперь когда придет другой мастер, он без труда займет I2C и сможет командовать нашим модулем.

    Как я понял, это просто шаблон.
    Просто не зачем отправлять каждый раз значения, которые могут секундами не меняться.
    Тоже самое по и IndividualMotorControl.
     
    Igor68 нравится это.
  2. Igor68

    Igor68 Гуру

    Скорее всего вы правы... точнее вы правы полностью! Эта связка доводится только с целью устранения узких мест. Программа связи + сервер на малине + управление шилдами через ардуино - это только подготовка. В планах на устройство смонтировать саму малину... конструкция вообще не понятна. С питанием надо что-то делать. Поворачивать камерой должен не я. Да и управление движением то же. Кроме этой связки на малине надо реализовать некоторый модуль с применением OpenCV. Насколько производительности его хватит для этих целей пока не определил. Для основной работы планирую стационарную сборку из малин - было в первом посте. Не смейтесь... но хочу железку сделать... самостоятельной... ну относительно... в какой-то степени. Cвязь между собой по WIFI, но организация сети на первой малине(RPi3), что установлена на устройстве. На остальных тоже и OpenCV и MPI (или OpenMP). Одним словом опыты... и опыты.

    Что остального - курю инструкции. За них спасибо. Правда опасаюсь... уж больно не хочется отвыкать от AT91SAM3U4E, AT91SAM7S256, ADuC7024 и других ARM/Cortex. Хоть и давно их не трогал... но придётся... работа такая. А это для души. Хотя заметил, что схемы и правила периферии контроллеров практически идентичны - я про Atmel.

    Опыты с командой 16 показали - львиная доля задержки обращения только к одному регистру по команде 6. Пока готово только обращение к ComMotion - моторы управляются одновременно.
     
  3. Alex19

    Alex19 Гуру

    Тогда зачем вообще Ардуины (AVR) и т.д., у Вас 2 устройства которые работают по I2C, почему бы сразу не прикурить их к Raspberry?

    Зачем какие-то тесты, так Вы еще библиотеки пишите (говорю о Modbus), разбираетесь в прерываниях и т.д., на контролере будете разбираться с 1-ними проблемами, на Raspberry с другими. И там Вам не нужен будет Modbus, Вы будете сразу слать команды на прямую.

    Если это все расположено на подвижной платформе, то тут нужно думать. Потребление энергии нескольких Raspberry с Wi-Fi будет не меньше 10W в час, камера, модули, моторы, сервы, преобразователи питания будут тоже что-то терять. Хотя тут много завит от автономности и режимов работы.

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

    Если все таки решите делать с контролером, и не хотите отвыкать, используйте то с чем больше опыта AT91SAM3U4E прекрасный контролер (есть 2 независимых TWI). Не хотите разводить плату, тогда почему бы не попробовать Arduino Due, он на базе Cortex M3?

    Значит где-то косяк, не понимаю, почему Вы не хотите воспользоваться хорошей и проверенной библиотекой - https://github.com/smarmengol/Modbus-Master-Slave-for-Arduino. Увеличьте скорость до 115200, введите в ней понятия шага, чтобы не ждать ни где по аналогии с Вашем switch в программе r1_uno_plus.zip, замените подсчет CRC на табличный и постоянно вызывайте его в loop и все.

    Делать свои реализации долго по времени, даже для хобби, хотя иногда сам путь ценнее результата.
     
    Igor68 нравится это.
  4. Igor68

    Igor68 Гуру

    Уже было напрямую... точнее через ARPI600...
    ARPI600-Schematic.pdf
    шилды садились на неё... был доволен до тех пор, пока не умер RPi2. Понадеялся на рекламу - в которой только одна ложь, ведь развязку не делали. Искал что бы применить... и вот! Arduino!
    Перелопачиваю под неё!
    Подвижная как говорил будет только одна малина на устройстве. "Батарея" из малин должна быть стационарной... и в зоне досягаемости по WIFI подвижной малины на устройстве. Так что потребление для подвижного устройства RPi3 + Arduino UNO plus + ComMotion + Multiservo + приводы. И всё! Хотя может есть и другое решение, но камера с малиной должны быть на устройстве.
    После поспешного приобретения ардуины нет смысла... да и если от шилдов что-то временами "проскакивает" в цепи Cortex , то и в Arduino Due проскочит. Arduino вместе с IDE рассматриваю как что-то закрытое... т.е. не вникая глубоко.
    Кстати уже не по теме: про AT91SAM3U4E никак не доделаю прибор... USB доступ в режиме MASTORAGE + HID (одновременная работа). Всё нормально когда работаю с флешкой (параллеьный доступ). Но она быстро нагнётся если происходит перезапись в сектора с FAT и каталогом. Потому с самого начала была прикручена RFAM по SPI. Она и должна была заменить младшие сектора диска. Кстати на SPI ещё часы, ацп, программируемые ОУ. Одним словом если комбинированная схема то по USB не успеваю отрабатывать.
    Работаю!
     

    Вложения:

  5. Alex19

    Alex19 Гуру

    Что-то зарываюсь на работе, на хобби не остается времени:(.

    Шилд с Ардуиной, чего только не делают, сам покупаю у этой фирмы различные модули.
    Увы, многие китайцы этим грешат.

    Значит не внимательно прочел, так будет повеселее.

    Там только I2C, по идее проблем не должно быть, питание у Arduino Due 3.3V, а у шильдов 5V, обычный конвертер уровней, с опторазвязкой и все. Для Arduino Due значительно меньше библиотек, но I2C есть, подумал Вам будет приятнее работать с привычным для Вас контролером.

    Не сталкивался 32 разрядными Amtel, кроме Arduino Due в рамках Arduino IDE, как и с USB. Да и к тому же, всего лишь любитель.

    Если правильно сориентировался в названии чипа, то вот его описание - http://www.atmel.com/devices/ATSAM3U4E.aspx?tab=parameters. Получается у Вас только 1 SPI, 7 прерываний для SPI и поддержка DMA, не нашел приоритета прерываний, но полагаю они есть. Хотя наверняка у Вас уже задействованы все аппаратные возможности. Схема одна, использовать все аппаратные возможности, убирать лишние вызовы и поиск виновника торжества, что именно мешает USB.

    Если допилю выше озвученную библиотеку, скину. Просто сейчас ковыряюсь с архитектурой и бизнес логикой.
     
    Igor68 нравится это.
  6. Igor68

    Igor68 Гуру

    По идее да... но на RPI600 RESET(и он на порт IO малины) и ещё ряд сигналов проходят напрямую... без джамперов. I2C действительно нормально... да и его сигналы нормально реализованы на самой малине. Но что сделыно то сделано.
    Плата (первая) разведена до меня... да и компактно очень... детали аж с двух сторон... но это нормально. DMA применить не могу по SPI... там разные типы устройств вплоть до размера данных 8;16;24 бита. хотя последний я делал комбинированно. Аппаратный доступ к памяти флеш с параллельным доступом на плате c DMA смысла никакого... посмотрел коды примеров для двух случаев... и испытал. Для SPI одно прерывание... по завершении обмена... определение другого устройства для работы и с другими настройками... запуск обмена. Хотя у меня товарищ балдеет от DMA... понять можно... у него только один ADC на SPI. У меня на SPI как говорил FRAM. часы, 3 настраиваемых операционника, два ацп (один на 3 канала на 24 бита, второй через "изолятор" на 16 бит). Один выход заменить флешку на FRAM... если бы ещё pin-to-pin был бы рай! В приборе кроме кнопки ничего не предусматривалось... управление и настройка по HID USB. Сделал! Сделал и чтение... тоже по HID. И калибровка там же! И просмотр реальных параметров тоже... но хотят ещё и как USB диск что бы был. А переключение режима? Сделал и одновременно и HID и USB-DISK... в натяг конечно... но работает. Только при регистрации в диск "Открыть файл;записать.дописать;Закрыть файл" всё нормально... но место на диске умрёт в тех местах, где фат и каталог. Старать надо ведь целый блок. Если с FAT16 это только заполнение занятых кластеров... то каталог с указанием размера и т.п. FRAM и ничего более.
    В Cortex прерывания не только с указанием(выбора) приоритетов (кроме SysTimer, AddrAbort, DataAbort и др. - они фиксированы), так они ещё многоуровневые. То есть находясь в прерывании низкого приоритета может быть вызвано прерывание более высокого приоритета и т.д. Возврат из прерываний в обратной последовательности. И в прерывании свой стек - системный. А в простом режиме стек пользователя. Соответственно в нём два аппаратных указателя стека. Ну и наборы регистров понятное дело.
    Что касается моего то пока остановил допиливать прошивку для ардуины... убрал мусор... сформировал две команды, т.к. читать из шилдов не планирую... пока. Допиливаю сервер на связь по IP и тестовую программу управления. Хочу туда добавить картинку с камеры. Скорее всего это не потоковое видео. Фактически должен быть результат после OpenCV... походу подниму ещё один порт на малине кроме контроля для передачи картинки клиенту. Наверное тоже просто по TCP. Не реального времени понятно. Но и подвижная малина должна что-то делать. Форма данных пока не ясна.
     
  7. Igor68

    Igor68 Гуру

    Вот пока остановился на этом:
    Для ардуино... реализовал только необходимые команды, убрал пустые обращения:
    r1_uno_plus.zip

    Со стороны сервера для связи (либо малина либо другая машина с линукс) с ардуино сделал так же сокращения - убрал передачу пустых команд:
    arbot.zip

    Тестовая программа - QtCreator:
    snapshot5.png
    snapshot6.png
    Собственно архив:
    qtarpi.zip

    Соответственно на форме "окно" для отображения картинки с камеры. Ну и инструменты для подключения к серверу с OpenCV. Предполагается для начала передача кадров изображения после "обработки".... чёрно-белая картинка. Сейчас в этом окне только один красный пиксель на чёрном фоне. В дальнейшем надеюсь вместо картинки что-то другое. Да и смотреть для проверки надо.

    При реализации сервера... начинаю потихоньку привыкать к g++(я имед ввиду необходимое к OpenCV)... ранее только gcc и применял. Сейчас собираю начальные примеры OpenCV в комплекте с сокетами. Это пока. Конечно много чего не ясно... По крайней мере этот пример для того, что бы другие не наступали на мои грабли!

    Спасибо!
     

    Вложения:

    • r1_uno_plus.zip
      Размер файла:
      16,4 КБ
      Просмотров:
      399
    • arbot.zip
      Размер файла:
      31,4 КБ
      Просмотров:
      443
    • qtarpi.zip
      Размер файла:
      141,2 КБ
      Просмотров:
      445
    Последнее редактирование: 4 дек 2016
    Alex19, ZAZ-965 и ИгорьК нравится это.
  8. Igor68

    Igor68 Гуру

    Да! Однако привычку менять... да и не особо приавык...
    Вот Makefile... не сразу получилось... да и g++....
    Код (Bash):
    #Makefile for OpenCV

    CPP               := g++
    CC        := gcc
    #
    CFLAGS        := -c -Wall
    #
    LDFLAGS        :=
    #
    CFLAGS        :=
    #CPPFLAGS        := -I/usr/local/include/opencv -L/usr/local/lib
    INCL        := -I/usr/local/include/opencv
    LIB        := -L/usr/local/lib
    #
    CPPLIBRARIES    := -lopencv_core -lopencv_imgproc -lopencv_highgui -lpthread
    #

    all: camserver


    camserver: main.o wcam.o vsocket.o
        $(CPP) $(LIB) $(CPPLIBRARIES) main.o wcam.o vsocket.o -o camserver

    main.o:    main.cpp
        $(CPP) -c main.cpp

    wcam.o:    wcam.o
        $(CPP) $(INCL) -c wcam.cpp

    vsocket.o: vsocket.o
        $(CPP) -c vsocket.cpp
       
    clean:
        rm -f *.o camserver
     
    Пробую на базе ранее упомянутого "универсального" сервера. Получилась по тестовая часть. Но все заготовки установил.
    camserver.zip
    В принципе пока только тестирую... но возможно кто будет пробовать самостоятельно. Как привык у меня не вышло... но Makefile кое как сваял. И Pthread совместно с OpenCV и сокетами дружат. Протокол пока не могу определить...:( что передавать... как в дальнейшем прикрутить для дальнейшей обработки, а не просто отображения.
     

    Вложения:

    • camserver.zip
      Размер файла:
      60,5 КБ
      Просмотров:
      415
    Последнее редактирование: 4 дек 2016
    Alex19 нравится это.
  9. Igor68

    Igor68 Гуру

    По протоколу передачи картинки:
    Код (C++):
    /*
    ********************
    * для всех пакетов *
    ********************
    */

    //начальные адреса пакета
    #define _vtcp_szl               0x0000      //младший байт размера
    #define _vtcp_szh               0x0001      //старший байт размера
    #define _vtype                  0x0002      //тип обращения - выбор режима (картинка и т.п.)
    #define _vcop                   0x0003      //код операции (чтение/запись)
    #define _vwidht                 0x0004      //ширина в случае работы с картинкой
    #define _vheight                0x0006      //высота в случае работы с картинкой
    #define _mtime                  0x0008      //маркер времени для синхронизации
    //байты с одресами 0x000A...0x000F резервируем для возможного дальнейшего расширения
    #define _vdaddr                 0x0010      //начало данных
    //команда для _vcop - собственно код операции
    #define    _vcop_rd                0x01        //чтение (от сервера клиенту) - в случае с картинкой байтовый массив картинки
    #define _vcop_wr                0x02        //запись (от клиента серверу) - в случае с картинкой параметры
    #define _vcop_rdwr              0x03        //чтение-запись

    /*
    ************************
    прямая передача картинки
    8 бит
    ************************
    */

    #define _vtype_scr8             0x01        //тип обращения - указывает, что от OpenCV картинка чёрно-белая 8 бит
    Собственно требуется предусмотреть работу OpenCV на нескольких устройствах по сетевому соединению. На устройстве (малине), что будет на подвижной платформе вместе с веб-камерой будет запущен сервер с OpenCV. Данные это не только картинка, но и данные выбранного региона на изображении, массив контуров, ключевых точек и т.д. Предполагается для каждого типа обращения
    Код (C++):
    #define _vtype                  0x0002      //тип обращения - выбор режима (картинка и т.п.)
    выбирать серверу свои данные для передачи.
    Может у кого есть какие идеи... ну или опыт? Понятное дело, что к серверу могут обращаться сразу несколько клиентов с разными типами запросов.
    Спасибо!
     
    Последнее редактирование: 5 дек 2016
  10. Alex19

    Alex19 Гуру

    Извините за паузу в общении, на удивление много работы под новый год.

    Можно с начало обкатать и на Ардуине с ней все проще.

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

    Остается только как-то заставить все это работать. Как мне это видеться, часы мы опрашиваем редко, ADC в зависимости от возможности ADC (макс. кол-во выборок, у моего 16 битного всего 860 в сек., режим опроса) и т.д., попытаться опрашивать их по очереди. Поиск узких мест, кроме отладчика иногда полезен логический анализатор и/или осциллограф.

    Увы, моих знаний не достаточно, чтобы помочь Вам.

    Очень похоже на STM32, по определенным причинам остановился на этих 32-раз. контролерах, а не на Atmel.

    Баловался лишь с передачей данных на Raspberry в виде массивов с node.js по UDP. Но там все проще, но принцип был тот же, стартовый бит, длина, номер команды, сам массив, CRC. Если будет полезно пишите.
     
  11. Igor68

    Igor68 Гуру

    Доброго времени суток!
    Забудьте! Не обращайте внимания!
    Да и на STM32 тоже Cortex M3. "Джозеф Ю. Ядро Cortex-M3 компании ARM. Полное руководство (2012).djvu" - к сожалению у меня она весит 20 Мб (отсканирована). Скинуть не могу. STM32 дешевле, и доступнее.

    Сейчас пилю связь для передачи картинки с камеры в эту же тестовую программу. Что-то я с размерами намудрил. Пока что делаю общий шаблон.
    Курю копию данных
    OpenCV_matrix.pdf
    Пробую из массива камеры после преобразования в чёрно-белое. Где-то косяк.
     

    Вложения:

    Alex19 нравится это.
  12. Alex19

    Alex19 Гуру

    День добрый.

    Вот именно из-за доступности, как плат для разработчиков, так программаторов, огромного кол-во документации (порой в ней тонешь:)) и большим кол-во примеров на русском, английском. Спасибо, за книгу, найду.

    Может будет полезно - http://robocraft.ru/page/opencv/.

    Там не мало статей по OpenCV, когда-то хотел стартовать и был проект, но поговорив с программистами, понял, что проще механикой. Хотел в мешке определять цифры (пластмассовые цифры, как раньше были в сырах:)), нужно было достать 1 из 1000 тысячи и выставить определенным образом, в заготовке. А потом проект заглох.
     
    Последнее редактирование: 5 дек 2016
    Igor68 нравится это.
  13. Igor68

    Igor68 Гуру

    Книга посвящена можно сказать ядру и контроллеров, являющихся его неотъемлемой частью. Там очень неплохо описана организация многозадачности и сопутствующим механизмам.
    Кстати я с этого и начинал. Спасибо.

    Но ошибку нашел!
    Если посмотреть:
    Код (C++):
    */
    //начальные адреса пакета
    #define _vtcp_szl               0x0000      //младший байт размера
    #define _vtcp_szh               0x0001      //старший байт размера
    #define _vtype                  0x0002      //тип обращения - выбор режима (картинка и т.п.)
    #define _vcop                   0x0003      //код операции (чтение/запись)
    то значение размера пакета получается два байта (параметр _vtcp_szl): до 0xFFFF (65535)
    но у меня (<размер по горизонтали> * <размер по вертикали>) + <служебная шапка> = (640 * 480) + 16 = 307216 байт т.е. 0x4B010 - уже более 2-х байт. В то время как принимал 45072 байта т.е. 0xB010. Вот я тормоз этакий в размере долбанулся! Надо выделить на описание размера не два а четыре байта. А то принимаю маленький кусок экрана, точнее камеры. Смотрится как дефект строчной развёртки - смещено влево и не полно. Вот блин!
    Но завтра в поликлинику с утра... сегодня уже не смогу доделать!
     
  14. Alex19

    Alex19 Гуру

    Доделал реализацию Slave Modbus RTU, она основана на данной библиотеке - https://github.com/smarmengol/Modbus-Master-Slave-for-Arduino. Эта версия будет оптимизирована, но уже под занавес моего проекта, сейчас нет времени.

    Что изменено.
    1. Адресация, поддержка адресов от 0 до 65535, в базовой версии до 255.
    2. Изменен подсчет CRC, код был позаимствован из данного документа - http://www.modbus.org/docs/PI_MBUS_300.pdf. Сами массивы для расчета сохранены в PROGMEM, функция расчета CRC - uint16_t Modbus::CRC16(uint8_t *puchMsg, uint16_t usDataLen).
    3. Убрана задержка loop при получении данных по RS485, в базовой версии на получение пакета из 120 слов, loop выполнялся до 15ms. Сейчас, тот же пакет до 1,2ms с стандартной библиотекой Serial и до 0,5ms c библиотекой UART.
    4. Добавлена поддержка библиотеки UART, из проекта Multiwii.

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

    Теперь о файлах.
    ModbusRtuSlave.cpp, ModbusRtuSlave.h - сам Slave Modbus RTU.
    ModbusVar.h - храню переменные, связанные с Modbus массивом, к примеру
    Код (C++):
    #define TURNING_MACHINE                 MC_GET_BIT(modbusData[12], 0)
    #define TURNING_HEATING                 MC_GET_BIT(modbusData[12], 1)
    #define TURNING_TEMPERATURE_ZONES_1     MC_GET_BIT(modbusData[12], 2)
     
    Это удобно, когда у Вас 1000 адресов.

    Config.h - файл настроек проекта. Тут лежат все настройки, порт UART используемый для Modbus, скорость и т.д..
    Def.h - файл настроек контролера, пинов.
    Timer.cpp, Timer.h - тут ни чего полезного, используются для определения скорости loop и других функций.
    UART.cpp, UART.h - библиотека работы с UART.
    UARTDebug.cpp, UARTDebug.h - отладка по UART, простое решение работает как с UART, так и с обычной Serial.

    Как работать, все как с базовым вариантом библиотеки.
    Объявляем
    Код (C++):
    Modbus modbusSlave(MODBUS_SLAVE_ADDRESS, MODBUS_UART_PORT, PIN_RS485_RE_DE);
    Запускаем в setup
    Код (C++):
    modbusSlave.begin(UART_PORT_SPEED);
    В начале loop
    Код (C++):
    // Проверяем, поступил ли запрос и если поступил даем ответ.
      int8_t modbusError = modbusSlave.poll(modbusData, MODBUS_DATA_COUNT);
      if (modbusError < 7
        && modbusError != 0)
      {
        //DEBUG_PRINTLN(modbusError);
      }  
    В конце loop
    Код (C++):
    // Обновляем данные в регистрах Modbus и в пользовательской программе.
      UpdateModbusData();
    Пару слов о буферах, буфер Modbus.
    Код (C++):
    // Массив данных для сети Modbus. Это массив, с адресами нашей памяти, MODBUS_DATA_COUNT в файле Config. Если мы обращаемся к слову по 0-му адресу, то мы просто обращаемся к modbusData[0]
    uint16_t modbusData[MODBUS_DATA_COUNT];
    Буфер обмена Modbus задается в ModbusRtuSlave.h, это массив для получения и отправки сообщений Modbus.
    Код (C++):
    #define  MAX_BUFFER  64 //!< maximum size for the communication buffer in bytes
    Теперь о буферах Serial, находится тут - arduino\hardware\arduino\avr\cores\arduino, файл HardwareSerial.h.
    Код (C++):
    #if !defined(SERIAL_TX_BUFFER_SIZE)
    #if ((RAMEND - RAMSTART) < 1023)
    #define SERIAL_TX_BUFFER_SIZE 16
    #else
    #define SERIAL_TX_BUFFER_SIZE 256
    #endif
    #endif
    #if !defined(SERIAL_RX_BUFFER_SIZE)
    Использование библиотеки UART, раскомментируем строку USE_AVR_UART в файле Config. Настраиваем параметры в файле Config, UART_PORT и UART_PORT_SPEED. Настраиваем буфер UART, файл UART.h.
    Код (C++):
    // Размер буфера RX
    #define RXBufferSize 64

    // Размер буфера TX
    #define TXBufferSize 64
    Вроде все, надеюсь не о чем не забыл.

    Данная библиотека UART имеет недостатки, для плат на базе Atmega32u4, Atmega2560 связанные с использованием памяти, о чем когда-то писал:
    Подробнее тут - http://forum.amperka.ru/threads/Реализация-uart-rs-485.6791/

    В архиве, проект в VS 2012.
     

    Вложения:

    Igor68 нравится это.
  15. Alex19

    Alex19 Гуру

    Важная вещь, нужно будет найти время и почитать.

    Со всеми бывает, главное, что разобрались.

    Погода такая, что-то все болеют:(.
     
  16. Igor68

    Igor68 Гуру

    Доброго времени суток!
    С основными ошибками вроде что-то сделал. Но вот:
    snapshot7.png
    Складывается ощущение... будто у старого телевизора частота кадров убежала. Изображение в градациях серого принимал от сервера. Преобразование картинки и заполнение массива для передачи в сервере на малине вот:
    Код (C++):
    //рабочий процесс камеры
    void* CamLoop(void * pr)
    {
        U32    cntx, cnty, cntbyte;
        cv::Mat src;
        cv::Mat gray;
        //
        printf("start camm loop...\n");
        //
        while(1)
        {
            src = cvQueryFrame(capture);
            cv::cvtColor(src, gray, CV_BGR2GRAY);
            cnty     = 0;
            cntbyte    = 0;
            pthread_mutex_lock(&ServerMutex);
            while(cnty < height)
            {
                cntx = 0;
                while(cntx < width)
                {
                    ocvbuf[cntbyte] = gray.at<char>(cntx,cnty);
                    cntx++;
                    cntbyte++;
                }
                cnty++;
            }
            pthread_mutex_unlock(&ServerMutex);
            usleep(_wait_cam);
        }
        //
        pthread_exit(0);
    }
     
    Вообще никаких изменений в данные не вносил... передавал из вышесказанного одномерным массивом. Но исходная картинка с того же положения камеры и тем же сервером в тестовом режиме (по "--test") вот:
    snapshot8.png
    Ведь где-то накосячил! Вот только где?
    Архив сервера:
    camserver.zip
    Архив тестовой программы (честно сказать с отображением картинок тут впервые):
    qtarpi.zip

    Вот пилю! курю маны! Но хоть с мёртвой точки что-то сдвинулось!
    Возможно у кого-то есть опыт... и посоветуют!
    Спасибо!
     

    Вложения:

    • camserver.zip
      Размер файла:
      64,3 КБ
      Просмотров:
      407
    • qtarpi.zip
      Размер файла:
      150,8 КБ
      Просмотров:
      411
    Последнее редактирование: 6 дек 2016
    Alex19 и ИгорьК нравится это.
  17. Alex19

    Alex19 Гуру

    День добрый.

    Немного терпения и все получиться.

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

    С удовольствием присоединился бы к Вашей разработке, но пока не хватает ни знаний ни времени.
    Желаю Вам терпения и удачи в Вашей разработке!
     
  18. ZAZ-965

    ZAZ-965 Гуру

    @Igor68, у меня тоже нет знаний в этой теме чтобы что-то советовать, но в paintEvent по моему у не обнуляется
    Код (C++):
    int x,y;
        x = 0; //? может y=0
        while(y < 480)
        {
            x = 0;
            while(x < 640)
            {
                paint->setPen(QColor(0,0,0,0));
                paint->drawPoint(x,y);
                paint->setPen(QColor(255,0,0,(dpix[x][y])));
                paint->drawPoint(x,y);

                x++;
            }
            y++;
        }
     
     
    Igor68 нравится это.
  19. Igor68

    Igor68 Гуру

    Искренне рад слышать! ...Точнее видеть ответ!

    Вы и так достаточно много помогли! В свою очередь так же буду делиться всем, что знаю!

    Сейчас курю вот это о по прилагаемому Slave Modbus RTU.zip:
    Смущает пункт 1 - поддержка адресов 0...65535. Адрес ведомого уже 2 байта.
    - Можно рассматривать как количество устройств на шине... но это уже не Modbus RTU.
    - Можно рассматривать как размер данных, что вообще-то логично но:
    в команде 16 - "запись в группу регистров"
    0: адрес ведомого 1 байт
    1: код команды 1 байт
    2: старший байт адреса начального регистра
    3: младший байт адреса начального регистра
    4: старший байт количества регистров
    5: младший байт количества регистров
    6: счетчик байтов в поле данных (количество до 255)
    .... собственно данные
    N: контрольная сумма.
    Меня самого смущает значение счётчика байтов до 255, в то время как количество регистров определено двух-байтным значением т.е. 65535 регистров по два байта на каждый регистр.
    Ну да ладно не мы протокол придумали! Про табличный метод CRC вы говорили, но я пока не испытал.

    Моя малина далеко от домашнего роутера и на ноутбуке нет ETHRNET физически. В интернет через малину не надёжно - расстояние. Так, что подключаюсь по очереди по WIFI то в инет то в малину для испытаний.
     
  20. Igor68

    Igor68 Гуру

    Простите это глупость, что осталась от предыдущего. Не удалил.
    Раньше было определение в начале программы (сейчас закоментировано)
    Код (C++):
    pix                 = new QPixmap(640,480);
    paint               = new QPainter(pix);
    Но в функции paintEvent не было:
    Код (C++):
    pix                 = new QPixmap(640,480);
    paint               = new QPainter(pix);
    И у меня "накладывалась" новая картинка на старую... в результате чего была постепенная "засветка". Ну и соответственно:
    paint->setPen(QColor(0,0,0,0));
    paint->drawPoint(x,y);

    было глупой попыткой избавиться от неё... по недоумию моему... и моей безграмотности!

    Спасибо!
    С Глубоким уважением!