Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Как передать 16-тиричное число через com порт? Изображение. USB дисплей.

9.0K
11 февраля 2010 года
mr_smit
64 / / 03.12.2006
Здравствуйте. Необходимо передать изображение через com порт в контроллер.

1. Чтобы получить цвет каждого пиксела, мы с каждым пикселем картинки проделываем следующее:

Код:
// картинка предварительно сохранена в фотошопе в формате bmp 5-6-5
// pix - цвет пикселя
// s - строка (string) с цветом в формате hex
...
pix:= Image1.Canvas.Pixels[k,Image1.Picture.Height-1-i];

r1:=GetRValue(pix) shr 3;
g1:=GetGValue(pix) shr 2;
b1:=GetBValue(pix) shr 3;

pix:= (r1 shl 11) + (g1 shl 5) + b1; // получили цвет
 
// можем перевести его в hex формат
s:=IntToHex(pix,4);


Т.е. для каждой из 5 точек знаем её цвет: F800, 0000, 0000, FFFF, FFFF


2. Дисплей работает в -5-6-5- (-R-G-B-) режиме цветопередачи. Это означает, что в потоке данных первые 5 бит устанавливают красный цвет, следующие 6 - зеленый, и последние 5 синий. (0xFFFF белый, 0x0000 черный).

3. Необходимо передать цвета каждого пикселя картинки контроллеру ATMega8, а он отправит их в дисплей.


4. В Delphi использую компонент CPortLib.
Для записи в порт у него есть:

Write - Writes non-typed variable to output buffer.
WriteAsync - Writes non-typed variable to output buffer in asynchronous mode.

WriteStr - Writes string type variable to output buffer.
WriteStrAsync - Writes string type variable to output buffer in asnychronous mode.

5. Как их передать? Т.е. как передать 16-тиричное число через com порт?
303
12 февраля 2010 года
makbeth
1.0K / / 25.11.2004
В чем проблема? Кодируй его в слово (Word) по схеме 5-6-5 бит и отправляй.
9.0K
14 февраля 2010 года
mr_smit
64 / / 03.12.2006
Как??? Хотя бы кусочек кода. Нигде не могу найти.
 
Код:
function WriteStr (const Str: string):integer;
function Write (const mbuffer: PAnsiChar; Count: integer):integer;
9.0K
14 февраля 2010 года
mr_smit
64 / / 03.12.2006
Цитата:
... 2 байта также называют словом (word). Отсюда и название соответствующего числового типа данных - Word (число, занимающее в памяти 2 байта, значения от 0 до 65535)



 
Код:
ComPort1.WriteStr(IntToStr(pix));


И всё что ли? Но это строка.

 
Код:
PixColorArray: array of Word;
...
PixColorArray[0]:=pix; // для одной точки (пока)
ComPort1.Write(PixColorArray[0],2);

[Error]: Incompatible types: 'Word' and 'PAnsiChar'

 
Код:
ComPort1.Write(Addr(PixColorArray[0]),2);

Компилируется, но при нажатии на кнопку ошибка в этой строке PixColorArray[0]:=pix;

Пример из справки к компоненту:
 
Код:
var
  Str: String;

begin
  Str := 'Hello';
  ComPort1.WriteStr(Str); // string type variable
  ComPort1.Write(Str[1], Length(Str)); // no defined type

end;
303
15 февраля 2010 года
makbeth
1.0K / / 25.11.2004
я, конечно, не уверен, что прокатит, но можно попробовать так:
 
Код:
var Color: Word; // Здесь наш цвет
    ColorStr: string;
begin
    ColorStr := Chr(Color and $00FF);
    ColorStr := ColorStr + Chr((Color and $FF00) shr 8);
    ComPort1.Write(PAnsiChar(ColorStr), 2);
end;

Вообще, не понятно, как должны быть отосланы цвета, каков порядок байт и т.п. Кроме того, у твоего компонента все таки должен быть метод, позволяющий посылать raw буфер (просто массив байт), а то получаются какие-то пляски с бубном, ей богу...
9.0K
15 февраля 2010 года
mr_smit
64 / / 03.12.2006
Вот сам компонент: http://sourceforge.net/projects/comport/files/ там в нем есть справка. Посмотрите пожалуйста. Может я чего не углядел.

А какой компонент для com порта лучше взять? Может ещё чего есть?
9.0K
17 февраля 2010 года
mr_smit
64 / / 03.12.2006
Нашел компонент TBComPort.

У него функция:
 
Код:
function Write(const Buffer; Count: Integer): Integer;


Код:
procedure TForm1.Button2Click(Sender: TObject);
var i: integer;
    r1,g1,b1:integer;
begin
  i:=clred;
  r1:=GetRValue(i) shr 3;
  g1:=GetGValue(i) shr 2;
  b1:=GetBValue(i) shr 3;
  i:= (r1 shl 11) + (g1 shl 5) + b1;

  form1.Caption :=' Старший байт='+IntToHex(Hi(i),2)+'Младший байт='+IntToHex(Lo(i),2);
end;


Как эти 2 байта отправить в ком порт???????

 
Код:
BComPort1.Open;
  BComPort1.Write(Hi(i),sizeof(Hi(i))); //ругается [Error] Unit1.pas(71): Variable required
9.0K
18 февраля 2010 года
mr_smit
64 / / 03.12.2006
Свершилось!!!!!!!!!!!!!


Существенный прогресс!!!!!!!! Работает!!!!!!!! Я поставил компонент TBComPort

Код:
procedure TForm1.Button2Click(Sender: TObject);
var r1,g1,b1:integer;
    Data: Byte;
begin
  r1:=GetRValue(i) shr 3;
  g1:=GetGValue(i) shr 2;
  b1:=GetBValue(i) shr 3;
  i:= (r1 shl 11) + (g1 shl 5) + b1;  // i - глобальная integer, из ColorDialog1

  BComPort1.Open;
  Data := Hi(i);
  BComPort1.Write(Data, SizeOf(Data));
  Data := Lo(i);
  BComPort1.Write(Data, SizeOf(Data));
end;


Т.е. делим полученный цвет на 2 отдельных байта, Hi и Lo, и побайтно отправляем. Сначала первый, затем второй.



Я счастлив...!!! И это всё на ATMega8...

Теперь осталось разобраться с выводов изображения в заданную область и передачей текста в дисплей.



Единственное только картинка выводится ооочень долго, 4-5 сек, но я думаю это из-за скорости COM порта. Я поставил 38400. Надо будет увеличить. Потому что заливка экрана одним цветом происходила очень быстро, < 1сек.

P.S. Кстати, в диспетчере устройств для TUSB 3410 можно выставить максимум 128000 бит/сек. Хотя вроде бы производитель обещает гораздо больше, странно.
303
18 февраля 2010 года
makbeth
1.0K / / 25.11.2004
Цитата: mr_smit
Единственное только картинка выводится ооочень долго, 4-5 сек, но я думаю это из-за скорости COM порта. Я поставил 38400. Надо будет увеличить. Потому что заливка экрана одним цветом происходила очень быстро, < 1сек.

P.S. Кстати, в диспетчере устройств для TUSB 3410 можно выставить максимум 128000 бит/сек. Хотя вроде бы производитель обещает гораздо больше, странно.


Узкое место скорее всего не в скорости порта, а в алгоритме вытаскивания и преобразования пикселей перед посылкой в порт. Можешь привести код отправки картинки?

9.0K
22 февраля 2010 года
mr_smit
64 / / 03.12.2006
На форме находятся Image1, Button1 и BComPort1. В Image1 загружена картинка bmp 176х132, которая предварительно сохранена в фотошопе в формате RGB 5-6-5.
Код:
procedure TForm1.Button1Click(Sender: TObject);
var r1,g1,b1:integer;
    PixColor:integer;
    i,j:integer;
    Data: Byte;
begin
BComPort1.Open;
  for i:=0 to Image1.Picture.Height-1 do
    begin
      for j:=0 to Image1.Picture.Width-1 do
        begin
          PixColor:= Image1.Canvas.Pixels[j,Image1.Picture.Height-1-i];
          r1:=GetRValue(PixColor) shr 3;
          g1:=GetGValue(PixColor) shr 2;
          b1:=GetBValue(PixColor) shr 3;
          PixColor:= (r1 shl 11) + (g1 shl 5) + b1;

          Data := Hi(PixColor);
          BComPort1.Write(Data, SizeOf(Data));
          Data := Lo(PixColor);
          BComPort1.Write(Data, SizeOf(Data));
       end;
    end;
end;
303
24 февраля 2010 года
makbeth
1.0K / / 25.11.2004
 
Код:
PixColor:= Image1.Canvas.Pixels[j,Image1.Picture.Height-1-i];

Это очень медленная операция. Копай в сторону TBitmap.Scanline. Кроме того, здесь вовсе не нужны вложенные циклы.
9.0K
25 февраля 2010 года
mr_smit
64 / / 03.12.2006
А как с помощью Scanline добраться до цвета одного пикселя? Читал читал так и не понял.

Цитата:
Это очень медленная операция.


У меня загрузка процессора не меняется вообще при выполнении этой операции. Как была 0-2% так и остается.

303
25 февраля 2010 года
makbeth
1.0K / / 25.11.2004
Цитата: mr_smit
А как с помощью Scanline добраться до цвета одного пикселя? Читал читал так и не понял.


Воспринимай Свойство Scanline как одномерный массив указателей на строки картинки. Сама строка представляет собой массив байт, значения которого зависят от формата изображения (например, для pf24, первые 3 байта этой строки кодируют первый пиксель строки в формате RGB).
В общем, должно получится что-то типа:

 
Код:
var line: PByteArray;
begin
    line := Bitmap1.Scanline[0]; // Самая нижняя строка (строки нумеруются снизу вверх)
    // R := line[0];
    // G := line[1];
    // B := line[2];
end;
Да... это все находится в гугле в течении минуты.
ЗЫ: Предензии по ошибкам не принимаются - Delphi не видел уже года 2 :rolleyes::D


Цитата:
У меня загрузка процессора не меняется вообще при выполнении этой операции. Как была 0-2% так и остается.

А при чем здесь процессор? Просто вызов функции GDI GetPixel (который скрывается под свойством TBitmap.Pixels) весьма тормозной.

9.0K
01 марта 2010 года
mr_smit
64 / / 03.12.2006
Всё равно не понял. Как мне получить цвет TColor ?
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог