Sensor Kamera CMUcam3

Tujuan dari proyek CMUcam adalah untuk memberikan kemampuan visi sederhana untuk embedded system kecil dalam bentuk sebuah sensor cerdas. CMUcam3 memperluas atas gagasan ini dengan menyediakan fleksibel dan mudah untuk menggunakan lingkungan pengembangan open source yang melengkapi platform perangkat keras biaya rendah. CMUcam3 ini berbasis ARM7TDMI sepenuhnya programmable embedded computer vision sensor. Prosesor utama adalah LPC2106 NXP terhubung ke kamera CMOS sensor Omnivision modul. Custom C code dapat dikembangkan untuk CMUcam3 menggunakan port dari GNU toolchain bersama dengan satu set library open source dan program contoh. Pemrograman menggunakan port serial port tanpa perangkat eksternal tabahan.

Modul embedded vision sensor berbasis Omnivision CMOS camera dan mikrokontroler ARM7TDMI (Philips NXP LPC2106).
Spesifikasi:
– Programmable dan open source.
– RGB, resolusi CIF (352×288).
– Slot untuk MMC/SD card dengan FAT16 driver.
– 4 port servo controller.
– Kecepatan image processing 26 fps (frame/second).
– Kompresi JPEG software.
– Lua light-weight language interpreter.
– Raw images dumps melalui port serial.
– Mampu membuat histogram.
– Tersedia keluaran video analog B/W (PAL or NTSC).
– FIFO image buffer untuk image processing dengan resolusi tinggi.
– Antarmuka serial UART TTL & RS-232.
– Mendukung Teleos 802.15.4, antarmuka jaringan Wireless Mote.

Untuk melakukan pemrograman software bisa didownload di link berikut. http://cmucam.org/wiki/Software. Jika menggunakan Windows dan saat proses installasi CygWin terdapat masalah, maka installer CygWin bisa didownload dari situsnya langsung http://cygwin.com/setup.exe.

Kelengkapan Software untuk melakukan programming pada CMUcam3

Windows: Cygwin-Installer (with packages), arm-gcc, Philips-Flash utility, .NET Runtime, CMUcam3 frame grabber

Linux: arm-gcc compiled tar, LPC-isp Flash Utility

Source Code

Pada situs http://cmucam.org/wiki/Downloads terdapat CC3 Source Tree yang bisa kita gunakan sebagai acuan dasar. Jadi kita tinggal mengedit saja sesuai keperluan.

CMUcam2 pada CMUcam3

CMUcam3 dapat diisi dengan menggunakan CMUcam2 Emulation HEX file (http://cmucam.org/attachment/wiki/Downloads/cmucam2_lpc2106-cmucam3.hex?format=raw) agar mempunyai kemampuan seperti CMUcam2. Untuk mengetes firmware tersebut bisa digunakan CMUcam2 GUI (http://www.cs.cmu.edu/~cmucam2/CMUcam2GUI.zip) yang berbasis java. Emulator java sendiri bisa didownload pada situs berikut. http://www.oracle.com/technetwork/java/javase/downloads/index.html.

Compile Source Code

Untuk mengedit file.c bisa menggunakan wordpad. Setelah semua software kelengkapan telah terinstall dengan baik, maka kita bisa langsung mencoba untuk mengkompail source code CC3 Source. Berikut urutan langkah-langkah untuk mengkompail file yang ada pada CC3 Source folder Project:

1. Jalankan CygWin (windows, console pada linux)

2. Ketik “cd alamat_direktori_project_yang dipilih”. Enter.

3. Ketik “make”, enter. Jika terdapat error, cobalah untuk mengulangi langkah 2 dengan mengganti alamat direktori project menjadi alamat dari folder CC3, enter. Lalu ketik “make”, enter. Setelah selesai, kembali ke langkah 2 untuk mengkompail file terpilih pada folder Project. Jika berhasil, maka pada folder yang terpilih akan ada file yang berekstensi .hex yang akan dimasukan ke dalam CMUcam3.

Memasukan .Hex pada CMUcam3

Pertama, matikan CMUcam3 lalu nyalakan kembali sambil menekan pushbutton yang terdapat pada modul beberapa saat. Jika CMUcam3 sudah siap diprogram maka 2 led akan menyala hijau dan merah. Buka software Philips-Flash utility. Pastikan pilih COM yang akan digunakan. Klik Erase. Lalu pilih juga file .hex yang akan ditanam pada CMUcam3 dan Upload to flash. Setelah selesai, matikan CMUcam3 dan nyalakan kembali agar CMUcam3 keluar dari keadaan siap diprogram menjadi menjalankan program.

Interface CMUcam3 dengan Mikrokontroler

CMUcam3 memiliki pin UART yang tentunya bisa kita manfaatkann untuk berkomunikasi dengan mikrokontroler. Disana terdapat koneksi dengan mode RS232 atau TTL. Jika menggunakan mode RS232 maka kita tinggal mengkoneksikannya dengan conector DB9 pada CMUcam3. Akan tetapi, jika menggunakan mode TTL maka ada jumper yang harus dilepas dan hati-hati jika mengkoneksikan CMUcam3 dengan pin TTL ini karena UART dari ARM yang rawan terbakar. Perhatikan level tegangan dan konsumsi arus antara CMUcam3 dan mikrokontroler yang digunakan. Disarankan gunakan saja RS232 karena koneksi terproteksi oleh IC MAX232 yang terdapat pada modul CMUcam3.

Berikut contoh program untuk CMUcam3 yang bisa digunakan untuk deteksi warna yang bisa terkoneksi ke mikrokontroler lain.

________________________________________________________

#include <stdio.h>
#include <stdlib.h>
#include <cc3.h>
#include <cc3_ilp.h>
#include <cc3_color_track.h>
#include <cc3_color_info.h>
#include <cc3_frame_diff.h>

void simple_track_color(cc3_track_pkt_t *t_pkt);
void simple_get_mean (cc3_color_info_pkt_t * s_pkt);
int main(void) {
cc3_color_info_pkt_t s_pkt;
uint8_t data;
uint32_t threshold;
int32_t tmp;
cc3_track_pkt_t t_pkt;
uint32_t x0, y0, x1, y1;
cc3_frame_diff_pkt_t fd_pkt;
cc3_uart_init (0, CC3_UART_RATE_115200,
CC3_UART_MODE_8N1, CC3_UART_BINMODE_TEXT);
cc3_camera_init ();
cc3_camera_set_resolution(CC3_CAMERA_RESOLUTION_LOW);
cc3_pixbuf_frame_set_subsample(CC3_SUBSAMPLE_NEAREST, 2, 1);
// init pixbuf with full size width and height

x0 = 0;
x1 = cc3_g_pixbuf_frame.raw_width;
y0 = 0;
y1 = cc3_g_pixbuf_frame.raw_height;
fd_pkt.coi = 1;
fd_pkt.template_width = 8;
fd_pkt.template_height = 8;
t_pkt.track_invert = false;
t_pkt.noise_filter = 0;
cc3_pixbuf_frame_set_roi (x0, y0, x1, y1);
// Load in color tracking parameters

t_pkt.lower_bound.channel[0] = 168;
t_pkt.upper_bound.channel[0] = 240;
t_pkt.lower_bound.channel[1] = 29;
t_pkt.upper_bound.channel[1] = 36;
t_pkt.lower_bound.channel[2] = 14;
t_pkt.upper_bound.channel[2] = 18;

//set servo awal posisi
cc3_gpio_set_servo_position(0,128);
while(true) {
simple_track_color(&t_pkt);

data = getchar();
if(data==’x’)
{
printf(“%c”,t_pkt.centroid_x);
}
else if(data==’y’)
{
printf(“%c”,t_pkt.centroid_y);
}
else if(data==’d’)
{
printf(“%c”,(uint8_t)t_pkt.int_density/10);
}
else if(data==’r’) // L R
{
t_pkt.lower_bound.channel[0] = getchar();
}
else if(data==’s’) // H R
{
t_pkt.upper_bound.channel[0] = getchar();
}
else if(data==’g’) // L G
{
t_pkt.lower_bound.channel[1] = getchar();
}
else if(data==’h’) // H G
{
t_pkt.upper_bound.channel[1] = getchar();
}
else if(data==’b’) // L B
{
t_pkt.lower_bound.channel[2] = getchar();
}
else if(data==’c’) // H B
{
t_pkt.upper_bound.channel[2] = getchar();
}
else if(data==’p’)
{
printf(“\n centroid=[%d,%d] bounding box=[%d,%d,%d,%d] num pix=[%d] density=[%d] \n”,
t_pkt.centroid_x, t_pkt.centroid_y,
t_pkt.x0,t_pkt.y0,t_pkt.x1,t_pkt.y1,
t_pkt.num_pixels, t_pkt.int_density );
}
else if(data==’w’)
{
printf(“\n R=[%d,%d] G=[%d,%d] B=[%d,%d] \n”,
t_pkt.lower_bound.channel[0],t_pkt.upper_bound.channel[0],
t_pkt.lower_bound.channel[1],t_pkt.upper_bound.channel[1],
t_pkt.lower_bound.channel[2],t_pkt.upper_bound.channel[2]);
}
else if(data==’a’)
{
// init pixbuf with width and height
cc3_pixbuf_load ();

threshold = 30;

// set window to 1/2 size
x0 = cc3_g_pixbuf_frame.x0 + cc3_g_pixbuf_frame.width / 4;
x1 = cc3_g_pixbuf_frame.x1 – cc3_g_pixbuf_frame.width / 4;
y0 = cc3_g_pixbuf_frame.y0 + cc3_g_pixbuf_frame.width / 4;
y1 = cc3_g_pixbuf_frame.y1 – cc3_g_pixbuf_frame.width / 4;
cc3_pixbuf_frame_set_roi (x0, y0, x1, y1);
// call get mean
simple_get_mean (&s_pkt);
// set window back to full size
x0 = 0;
x1 = cc3_g_pixbuf_frame.raw_width;
y0 = 0;
y1 = cc3_g_pixbuf_frame.raw_height;
cc3_pixbuf_frame_set_roi (x0, y0, x1, y1);
// fill in parameters and call track color
tmp = s_pkt.mean.channel[0] – threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.lower_bound.channel[0] = tmp;
tmp = s_pkt.mean.channel[0] + threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.upper_bound.channel[0] = tmp;
tmp = s_pkt.mean.channel[1] – threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.lower_bound.channel[1] = tmp;
tmp = s_pkt.mean.channel[1] + threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.upper_bound.channel[1] = tmp;
tmp = s_pkt.mean.channel[2] – threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.lower_bound.channel[2] = tmp;
tmp = s_pkt.mean.channel[2] + threshold;
if (tmp < 16)
tmp = 16;
if (tmp > 240)
tmp = 240;
t_pkt.upper_bound.channel[2] = tmp;

}
else
{
printf(“n”);
}
}
}
void simple_track_color(cc3_track_pkt_t *t_pkt)
{
cc3_image_t img;
img.channels = 3;
img.width = cc3_g_pixbuf_frame.width;
img.height = 1;  // image will hold just 1 row for scanline processing

img.pix = cc3_malloc_rows (1);
if (img.pix == NULL) {
return;
}
cc3_pixbuf_load ();
if (cc3_track_color_scanline_start (t_pkt) != 0) {
while (cc3_pixbuf_read_rows (img.pix, 1)) {
// This does the HSV conversion

// cc3_rgb2hsv_row(img.pix,img.width);

cc3_track_color_scanline (&img, t_pkt);
}
}
cc3_track_color_scanline_finish (t_pkt);
free (img.pix);
return;
}

void simple_get_mean (cc3_color_info_pkt_t * s_pkt)
{
cc3_image_t img;
img.channels = 3;
img.width = cc3_g_pixbuf_frame.width;
img.height = 1;               // image will hold just 1 row for scanline processing
img.pix = malloc (3 * img.width);

cc3_pixbuf_load ();
if (cc3_color_info_scanline_start (s_pkt) != 0) {
while (cc3_pixbuf_read_rows (img.pix, 1)) {
cc3_color_info_scanline (&img, s_pkt);
}
cc3_color_info_scanline_finish (s_pkt);
}
free (img.pix);
}
______________________________________________________________
Keterangan instruksi untuk interfacing dengan CMUcam3 dari program di atas.

‘x’ –> jika mikrokontroler mengirim nilai ascii dari huruf x , CMUcam3 akan mengirim balasan hex titik tengah koordinat sumbu x  warna yang terdeteksi.

‘y’ –> jika mikrokontroler mengirim nilai ascii dari huruf y , CMUcam3 akan mengirim balasan hex titik tengah koordinat sumbu y  warna yang terdeteksi

‘d’ –> jika mikrokontroler mengirim nilai ascii dari huruf d , CMUcam3 akan mengirim balasan hex nilai density yaitu nilai kepadatan pixel warna yang terdeteksi dibagi 10.

‘r’ –> jika mikrokontroler mengirim nilai ascii dari huruf r ,dilanjutkan dengan nilai hex filter warna merah (0-255) minimum.

‘s’ –> jika mikrokontroler mengirim nilai ascii dari huruf s , dilanjutkan dengan nilai hex filter warna merah (0-255) maximum.

‘g’ –> jika mikrokontroler mengirim nilai ascii dari huruf g , dilanjutkan dengan nilai hex filter warna hijau (0-255) minimum.

‘h’ –> jika mikrokontroler mengirim nilai ascii dari huruf h , dilanjutkan dengan nilai hex filter warna hijau (0-255) maximum.

‘b’ –> jika mikrokontroler mengirim nilai ascii dari huruf b , dilanjutkan dengan nilai hex filter warna biru (0-255) minimum.

‘c’ –> jika mikrokontroler mengirim nilai ascii dari huruf c, dilanjutkan dengan nilai hex filter warna biru (0-255) maximum.

‘p’ –> jika mikrokontroler mengirim nilai ascii dari huruf p, maka CMUcam3 akan mengirim ascii centroid=[%d,%d] bounding box=[%d,%d,%d,%d] num pix=[%d] density=[%d]

‘w’ –> jika mikrokontroler mengirim nilai ascii dari huruf w, maka CMUcam akan mengirim ascii R=[%d,%d] G=[%d,%d] B=[%d,%d] yaitu nilai filter warna yang digunakan.

‘a’ –> jika mikrokontroler mengirim nilai ascii dari huruf a, CMUcam3 akan meng-grab warna yang ada dihadapannya dan digunakan sebagai warna yang difilter atau dideteksi selanjutnya.

Untuk mengujinya bisa juga dihubungkan dengan hyperterminal pada PC.

Berikut link untuk mendownload .hex dari program di atas. http://www.mediafire.com/file/fo8jtyjwu7w77dr/simple-track-color-wangready.wordpress.com_lpc2106-cmucam3.hex

______________________________________________________________

Berikut contoh schematic rangkaian interface CMUcam3 dengan mikrokontroler atmega128 11.0592MHz + LCD 2×16 yang berkomunikasi menggunakan UART RS232

______________________________________________________________

Contoh program dengan CVAVR untuk mendeteksi adanya warna yang difilter

/*****************************************************
Chip type           : ATmega128
Program type        : Application
Clock frequency     : 11.059200 MHz
Memory model        : Small
External SRAM size  : 0
Data Stack size     : 1024
*****************************************************/

#include <mega128.h>
#include <delay.h>

// Alphanumeric LCD Module functions
#asm
.equ __lcd_port=0x1B ;PORTA
#endasm
#include <lcd.h>

#define RXB8 1
#define TXB8 0
#define UPE 2
#define OVR 3
#define FE 4
#define UDRE 5
#define RXC 7

#define FRAMING_ERROR (1<<FE)
#define PARITY_ERROR (1<<UPE)
#define DATA_OVERRUN (1<<OVR)
#define DATA_REGISTER_EMPTY (1<<UDRE)
#define RX_COMPLETE (1<<RXC)

// USART0 Receiver buffer
#define RX_BUFFER_SIZE0 8
char rx_buffer0[RX_BUFFER_SIZE0];

#if RX_BUFFER_SIZE0<256
unsigned char rx_wr_index0,rx_rd_index0,rx_counter0;
#else
unsigned int rx_wr_index0,rx_rd_index0,rx_counter0;
#endif

// This flag is set on USART0 Receiver buffer overflow
bit rx_buffer_overflow0;

// USART0 Receiver interrupt service routine
interrupt [USART0_RXC] void usart0_rx_isr(void)
{
char status,data;
status=UCSR0A;
data=UDR0;
if ((status & (FRAMING_ERROR | PARITY_ERROR | DATA_OVERRUN))==0)
{
rx_buffer0[rx_wr_index0]=data;
if (++rx_wr_index0 == RX_BUFFER_SIZE0) rx_wr_index0=0;
if (++rx_counter0 == RX_BUFFER_SIZE0)
{
rx_counter0=0;
rx_buffer_overflow0=1;
};
};
}

#ifndef _DEBUG_TERMINAL_IO_
// Get a character from the USART0 Receiver buffer
#define _ALTERNATE_GETCHAR_
#pragma used+
char getchar(void)
{
char data;
while (rx_counter0==0);
data=rx_buffer0[rx_rd_index0];
if (++rx_rd_index0 == RX_BUFFER_SIZE0) rx_rd_index0=0;
#asm(“cli”)
–rx_counter0;
#asm(“sei”)
return data;
}
#pragma used-
#endif

// USART0 Transmitter buffer
#define TX_BUFFER_SIZE0 8
char tx_buffer0[TX_BUFFER_SIZE0];

#if TX_BUFFER_SIZE0<256
unsigned char tx_wr_index0,tx_rd_index0,tx_counter0;
#else
unsigned int tx_wr_index0,tx_rd_index0,tx_counter0;
#endif

// USART0 Transmitter interrupt service routine
interrupt [USART0_TXC] void usart0_tx_isr(void)
{
if (tx_counter0)
{
–tx_counter0;
UDR0=tx_buffer0[tx_rd_index0];
if (++tx_rd_index0 == TX_BUFFER_SIZE0) tx_rd_index0=0;
};
}

#ifndef _DEBUG_TERMINAL_IO_
// Write a character to the USART0 Transmitter buffer
#define _ALTERNATE_PUTCHAR_
#pragma used+
void putchar(char c)
{
while (tx_counter0 == TX_BUFFER_SIZE0);
#asm(“cli”)
if (tx_counter0 || ((UCSR0A & DATA_REGISTER_EMPTY)==0))
{
tx_buffer0[tx_wr_index0]=c;
if (++tx_wr_index0 == TX_BUFFER_SIZE0) tx_wr_index0=0;
++tx_counter0;
}
else
UDR0=c;
#asm(“sei”)
}
#pragma used-
#endif

// Standard Input/Output functions
#include <stdio.h>

// Declare your global variables here

void main(void)
{
// Declare your local variables here

// Input/Output Ports initialization
// Port A initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTA=0x00;
DDRA=0x00;

// Port B initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTB=0x00;
DDRB=0x00;

// Port C initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTC=0x00;
DDRC=0x00;

// Port D initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTD=0x00;
DDRD=0x00;

// Port E initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTE=0x00;
DDRE=0x00;

// Port F initialization
// Func7=In Func6=In Func5=In Func4=In Func3=In Func2=In Func1=In Func0=In
// State7=T State6=T State5=T State4=T State3=T State2=T State1=T State0=T
PORTF=0x00;
DDRF=0x00;

// Port G initialization
// Func4=In Func3=In Func2=In Func1=In Func0=In
// State4=T State3=T State2=T State1=T State0=T
PORTG=0x00;
DDRG=0x00;

// Timer/Counter 0 initialization
// Clock source: System Clock
// Clock value: Timer 0 Stopped
// Mode: Normal top=FFh
// OC0 output: Disconnected
ASSR=0x00;
TCCR0=0x00;
TCNT0=0x00;
OCR0=0x00;

// Timer/Counter 1 initialization
// Clock source: System Clock
// Clock value: Timer 1 Stopped
// Mode: Normal top=FFFFh
// OC1A output: Discon.
// OC1B output: Discon.
// OC1C output: Discon.
// Noise Canceler: Off
// Input Capture on Falling Edge
// Timer 1 Overflow Interrupt: Off
// Input Capture Interrupt: Off
// Compare A Match Interrupt: Off
// Compare B Match Interrupt: Off
// Compare C Match Interrupt: Off
TCCR1A=0x00;
TCCR1B=0x00;
TCNT1H=0x00;
TCNT1L=0x00;
ICR1H=0x00;
ICR1L=0x00;
OCR1AH=0x00;
OCR1AL=0x00;
OCR1BH=0x00;
OCR1BL=0x00;
OCR1CH=0x00;
OCR1CL=0x00;

// Timer/Counter 2 initialization
// Clock source: System Clock
// Clock value: Timer 2 Stopped
// Mode: Normal top=FFh
// OC2 output: Disconnected
TCCR2=0x00;
TCNT2=0x00;
OCR2=0x00;

// Timer/Counter 3 initialization
// Clock source: System Clock
// Clock value: Timer 3 Stopped
// Mode: Normal top=FFFFh
// Noise Canceler: Off
// Input Capture on Falling Edge
// OC3A output: Discon.
// OC3B output: Discon.
// OC3C output: Discon.
// Timer 3 Overflow Interrupt: Off
// Input Capture Interrupt: Off
// Compare A Match Interrupt: Off
// Compare B Match Interrupt: Off
// Compare C Match Interrupt: Off
TCCR3A=0x00;
TCCR3B=0x00;
TCNT3H=0x00;
TCNT3L=0x00;
ICR3H=0x00;
ICR3L=0x00;
OCR3AH=0x00;
OCR3AL=0x00;
OCR3BH=0x00;
OCR3BL=0x00;
OCR3CH=0x00;
OCR3CL=0x00;

// External Interrupt(s) initialization
// INT0: Off
// INT1: Off
// INT2: Off
// INT3: Off
// INT4: Off
// INT5: Off
// INT6: Off
// INT7: Off
EICRA=0x00;
EICRB=0x00;
EIMSK=0x00;

// Timer(s)/Counter(s) Interrupt(s) initialization
TIMSK=0x00;
ETIMSK=0x00;

// USART0 initialization
// Communication Parameters: 8 Data, 1 Stop, No Parity
// USART0 Receiver: On
// USART0 Transmitter: On
// USART0 Mode: Asynchronous
// USART0 Baud rate: 115200
UCSR0A=0x00;
UCSR0B=0xD8;
UCSR0C=0x06;
UBRR0H=0x00;
UBRR0L=0x05;

// Analog Comparator initialization
// Analog Comparator: Off
// Analog Comparator Input Capture by Timer/Counter 1: Off
ACSR=0x80;
SFIOR=0x00;

// LCD module initialization
lcd_init(16);

// Global enable interrupts
#asm(“sei”)

//delay, menunggu cmucam3 benar-benar aktif
delay_ms(1000);

//setting nilai filter RGB
//deeteksi warna Dark orange (web colour) : http://en.wikipedia.org/wiki/Orange_%28colour%29
//centre RGB (255,140,0)
putchar(‘r’);
putchar(245);   // set nilai red minimum

putchar(‘s’);
putchar(255);   // set nilai red maksimum

putchar(‘g’);
putchar(130);   // set nilai green minimum

putchar(‘h’);
putchar(150);   // set nilai green maksimum

putchar(‘b’);
putchar(0);   // set nilai blue minimum

putchar(‘c’);
putchar(10);   // set nilai blue maksimum

while (1)
{
// Place your code here
//meminta nilai density dari CMUCAM3 dan menampilakan hasilnya pada LCD atmega128
putchar(‘d’);
if(getchar() > 0)
{
lcd_clear();
lcd_gotoxy(0,1);
lcd_putsf(“warna terdeteksi”);
}
else
{
lcd_clear();
lcd_gotoxy(0,1);
lcd_putsf(“tidak ada warna terdeteksi”);
}
delay_ms(300);
};
}
______________________________________________________________

Daftar Pustaka

http://cmucam.org

http://www.cmucam.org/discussion/message/1343

http://digi-ware.com

http://en.wikipedia.org/wiki/Orange_%28colour%29

Simple Color Tracking Menggunakan Webcam Dengan Library AForge.NET

Beberapa waktu lalu saat sempat terpikir untuk membuat aplikasi image processing, saya menemukan sebuah library yang saya kira cukup simple untuk diimplementasikan yaitu AForge.NET untuk bahasa C#. Alhamdulillah saat itu ada beberapa perangkat yang tersedia di laboratorium sehigga bisa terealisasi. Berikut uraian saya.

Simple Color Tracking

Abstraksi

Robotics vision adalah salah satu bidang kajian dalam dunia robotika. Salah satu langkah awal untuk memulainya adalah robot mampu mengenali warna. Dalam kesempatan kali ini, robot didisain mampu mengenali warna lalu mengikuti gerak dari warna yang terdeteksi tersebut. Sebagai sensornya digunakan kamera dan aktuator yang digunakan adalah motor servo. Sedangkan otak dari sistem tersebut masih menggunakan PC mengingat harga IC untuk aplikasi real time sangat mahal.

1. Pendahuluan

Penggunaan kamera(digital) dalam dunia robotik dikenal sebagai robotics vision. Seperti halnya pada manusia, kamera dapat didisain sebagai mata pada robot. Dengan mata, robot dapat lebih leluasa “melihat” lingkungannya sebagaimana manusia.

Dalam dua dasawarsa terakhir ini tenologi robotics vision berkembang sangat pesat. Kemajuan ini dicapai berkat perkembangan teknologi IC yang makin kompak dan cepat, dan kemajuan di bidang komputer (sebagai pengolah), baik perangkat keras maupun perangkat lunak. Teknologi optiknya pada dasarnya masih tetap menggunakan teknik yang telah berkembang sejak lebih dari 100 tahun yang lalu, yaitu penggunaan konfigurasi lensa cembung dan cekung.

2. Deteksi Warna

Ada banyak metode yang bisa digunakan untuk dapat mendeteksi warna menggunakan kamera. Diantaranya adalah dengan menggunakan Euclidean Color Filtering. Filter ini memfilter piksel-piksel pada gambar yang berada – di dalam/di luar – dari lingkup RGB (Red Green Blue) dengan pusat dan radius terntentu. Filter tersebut membiarkan piksel-piksel dengan warna yang berada – di dalam/di luar –  dari lingkup yang telah ditentukan dan mengisi sisanya dengan warna tertentu.

Setelah warna difilter maka untuk menghasilkan gambar yang lebih baik maka digunakan Erosion dan Dilatation. Erosion memberikan nilai minimum di sekitar piksel-piksel untuk setiap piksel dari citra hasil. Di sekitar piksel-piksel yang harus diproses, ditentukan oleh penataan elemen: 1 – untuk memproses tetangga piksel tersebut, -1 – untuk melewatinya. Filter sangan berguna terutama untuk pengolahan citra biner. Dimana filter ini menghapus piksel yang tidak dikelilingi dengan jumlah tertentu tetangganya. Ini memberi kemampuan untuk menghapus piksel nois (piksel yang berdiri sendiri) atau menyusutkan objek.

Dilatation, filter ini menetapkan nilai maksimum sekitar piksel untuk setiap piksel dari citra hasil. Di sekitar piksel-piksel yang harus diproses, yang ditentukan oleh penataan elemen: 1 – untuk memproses tetangga, -1 – untuk melewatinya. Filter ini berguna untuk pengolahan citra biner, di mana memungkinkan untuk melebarkan objek terpisah atau menggabungkan objek.

1. Diagram Alur

Input Gambar (dari webcam) –> Konversi data gambar ke dalam bentuk Bitmap (PC) –> Euclidean Color Filtering (PC) –> Erosion (PC) –> Dilatation (PC) –> Deteksi koordinat warna (PC) –> Pengiriman data ke mikrokontroler (PC – mikrokontroler) –> pengontrolan servo oleh mikrokontroler (mikrokontroler).

2. Pemograman

Untuk pemograman digunakan software Visual Studio 2008 dengan menggunakan bahasa C#. Alasan menggunakan bahasa C# adalah karena tersedianya library yang cocok bagi perancang, yaitu AForge.net. Pemograman pada VS 2008 dilakukan dengan menggunakan GUI. Selain itu, digunakan pula software CodeVision AVR sebagai compiler untuk mikrokontroler yang akan mengontrol servo secara mandiri.

3. Sistem Antarmuka PC – Mikrokontroler

Pengiriman data dari PC ke Mikrokontroler menggunakan RS232 dengan Baudrate disesuaikan. Jika posisi warna terdeteksi berada pada koordinat (0,0).

Jika posisi warna terdeteksi tidak berada pada koordinat (0,0).

4. Percobaan

Percobaan dilakukan dengan sejumlah warna. Objek berwarna tersebut digerak-gerakan di depan perangkat webcam-servo yang mempunyai 2 DOF (Degrees Of Freedom). Dengan sumbu Z sekitar 1800 dan sumbu X sekitar 600.

5. Hasil Percobaan

Robot mampu mengikuti arah objek. Jika robot kehilangan objek, maka robot akan bergerak ke arah saat objek terakhir terdeteksi. Proses deteksi warna ini masih terpengaruh oleh intensitas cahaya.

6. Kesimpulan

Kamera dapat mengikuti arah gerak dari objek berwarna yang telah ditentukan walaupun masih terdapat kekurangan pada algoritma juga pada  perancangan software dan hardware.

7. Daftar Pustaka

[1] Aforge.NET-Framework-Documentaion

[2] Lee, Wei-Meng, Practical .NET 2.0 Networking Projects, Apress, 2007.

[3] Pitowarno, Endra, Robotika Desain, Kontrol, dan Kecerdasan Buatan, Andi, Yogyakarta, 2006.

[4] www.aforgenet.com

[5] www.codeproject.com

[6] www.msdn.microsoft.com

8. Lampiran


Gambar 1. Tampilan software.

Gambar 2. Tampilan setting Euclidean Color Filter. Gambar 3. Foto Perangkat.

Berikut installer demo software simple color tracking.
http://www.mediafire.com/file/304priwevhameq0/simple%20color%20tracking.rar

Berikut beberapa link referensi lainnya.

http://www.aforgenet.com/articles/step_to_stereo_vision/

http://www.aforgenet.com/articles/lego_pan_tilt_camera/

Berikut Schematic untuk rangkaian kontroler servo.

Berikut link yang bisa didownload yang berisi PCB Project EAGLE beserta firmware (.hex) untuk attiny2313 berdasarkan schematic di atas.

http://www.mediafire.com/file/mqdrsjj3qoc7777/Color_Tracking-wangready.wordpress.com.rar

________________________________________________________________________________________

Update Servo Controller dengan Fuzzy Control System LINK.
________________________________________________________________________________________

project file http://www.mediafire.com/download/rap5garamf1peb9/P3_simple_color_tracking.rar