Sesuai dengan janji saya pada postingan sebelumnya kali ini saya akan membahas penggunaan CMPS03 melalui jalur I2C, mungkin ini bisa juga berguna bagi yang lainnya yang ingin mencoba menggunakan CMPS03 dengan AVR (saya menggunakan AT90s2313), bahasa yang digunakan adalah C (dengan CodeVisionAVR). Untuk module CMPS03 ini terdapat dua cara interfacing, yaitu menggunakan PWM dan menggunakan I2C. Nah saya hanya akan membahas yang I2C. Yang dibutuhkan adalah: AT90s2313 (ini bisa digantikan dengan chip AVR lainnya), CMPS03 (serta 2 resistor 1K s/d 47K untuk pullup, nilai resistornya tidak menjadi masalah) dan LCD 2×16 (serta trimpot atau potensio untuk kontras LCD). Lebih bagus jika ada kompas marinir untuk kalibrasi nantinya. Jika Anda belum mengetahui susunan pin CMPS03, berikut adalah susunan pinnya:
Gambar 1. Susunan pin CMPS03 (sumber: http://www.robot-electronics.co.uk/images/cmps3pin.jpg)
Modul kompas ini membutuhkan tegangan 5 v pada nominal 15mA. Karena menggunakan I2C kita hanya perlu menggunakan 5 jalur:
- Jalur untuk Vcc (+5V) pada pin 1.
- Jalur SCL dengan pull-up resitor (nilainya saya telah jelaskan sebelumnya bisa antara 1k - 47k) yang akan terhubung dengan pin uC.
- Jalur SDA dengan pull-up resistor yang akan terhubung dengan pin uC.
- Pin 6 (Calibrate) untuk kalibrasi. Gunakan swicth tactile yang terhubung antara pin ini dan ground.
- Jalur untuk Ground pada pin 9.
Koneksi antara pin CMPS03 dan AT90s2313 yang saya gunakan:
Gambar 2. Hubungan pin antara CMPS03 dengan AT90s2313
Untuk mengetahui nilai dari CMPS03, saya menggunakan LCD 2×16. Koneksi pin LCD dengan AT90s2313 yang saya gunakan:
Gambar 3. Hubungan pin antara AT90s2313 dengan LCD
Nah kita sudah menghubungkan CMPS03 dan LCD 2×16 ke AT90s2313. Bagaimana kalau kita mencoba programnya terlebih dahulu, baru setelah itu saya akan menjelaskannya. Berikut kode untuk menampilkan byte dari pembacaan CMPS03:
#include <90s2313.h>
// I2C Bus functions
#asm
.equ __i2c_port=0x12 ; port D
.equ __sda_bit=0
.equ __scl_bit=1
#endasm
#include <i2c.h>
// Alphanumeric LCD Module functions
#asm
.equ __lcd_port=0x18 ; port B
#endasm
#include <lcd.h>
void convertToLCDStr(unsigned char inByte)
{
unsigned char data;
data = inByte / 100;
data+=0x30;
lcd_putchar(data);
inByte%=100;
data = inByte / 10;
data+=0x30;
lcd_putchar(data);
inByte%=10;
data = inByte + 0x30;
lcd_putchar(data);
}
void main(void)
{
// I2C Bus initialization
i2c_init();
// LCD module initialization
lcd_init(16);
while (1)
{
lcd_gotoxy(0,0);
i2c_start();
i2c_write(0xC0); // alamat CMPS03 & operasi tulis
i2c_write(1); // register 1 yang ingin diakses untuk bearing byte
i2c_start();
i2c_write(0xC1); // alamat CMPS03 & operasi baca
convertToLCDStr(i2c_read(0)); // baca tanpa sinyal ACK
i2c_stop();
};
}
Saya mengkalibrasi CMPS03 dengan arah utara bernilai 0 kemudian setiap penambahan 64 merupakan arah timur, selatan dan barat. Jadi datanya hanya sebesar 1 byte. Dalam aplikasi robotika ini sudah cukup untuk membantu navigasi , kita hanya tinggal mendefinisikan arah-arah berikut agar robot mengetahui sedang menghadap mana:
#define utara 0
#define timur 63
#define selatan 127
#define barat 191
Nilainya mungkin bisa berbeda, jadi sesuaikan dengan apa yang ditampilkan di LCD. Dan itu tak masalah jika arah utara tidak sama dengan 0 atau arah barat tidak sama dengan 191. Untuk mengkalibrasi ulang CMPS03 agar sesuai dengan sudut inklinasi tempat kita berada bisa lakukan hal berikut:
Pastikan CMPS03 berada dalam posisi yang datar. Arah utara dari CMPS03 ditunjukkan dari gambar berikut:
- Gambar 4. Arah utara dari CMPS03
- Pastikan arah utara dari CMPS03 (pada gambar 4) menghadap utara, lalu tekan sekali saja tactile switch yang terhubung antara pin 6 CMPS03 dan ground.
- Putar perlahan-lahan arah utara CMPS03 hingga menghadap arah timur, lalu tekan kembali sekali saja tactile switch.
- Dari posisi no. 3, putar perlahan-lahan arah utara CMPS03 hingga menghadap arah selatan lalu tekan sekali saja tactile swicth.
- Dari posisi no. 4, putar perlahan-lahan arah utara CMPS03 hingga menghadap arah barat lalu tekan sekali saja tactile switch.
- Total penekanan tactile switch adalah 4x. Hasil kalibrasi ini disimpan di EEPROM CMPS03.
Kembali ke laptop program. Baris paling atas adalah header yang berisi alamat memori register-register dari AT90s2313. Baris selanjutnya adalah pendefinisian I2C, bisa dilihat saya menggunakan PORTD.0 untuk SDA dan PORTD.1 untuk SCL. Baris selanjutnya adalah pendefinisian LCD yang dihubungkan dengan PORTB. Fungsi
convertToLCDStr
digunakan untuk mengkonversi nilai desimal sesuai dengan ASCII tiap digitnya. Misalnya nilai inByte adalah 255, maka pertama digit ratusan akan diambil dan dikonversi ke nilai ASCII-nya (2 = 32), kemudian digit puluhan (5 = 35), lalu digit satuan (5 = 35). Ini perlu dilakukan karena fungsi lcd_putchar menerima data ASCII dan jika 255 di berikan ke fungsi ini maka karakter yang nilai ASCII-nya 255 yang akan ditampilkan.OK, masuk ke fungsi main. I2C perlu diinisialisasi terlebih dahulu dan cukup sekali saja. Lalu LCD juga perlu diinisialisasi dengan parameter berupa banyaknya kolom. Nah sekarang blok
while
, barisan kode yang berada dalam blok while ini akan selalu dieksekusi oleh uC. Fungsi lcd_gotoxy(0,0)
akan menempatkan kursor LCD pada baris 0 dan kolom 0 (ujung atas kiri LCD). Fungsi i2c_start()
akan mensinyalkan START ke jalur I2C. Setelah memberikan sinyal start, master perlu menuliskan alamat slave yang dituju (dengan pemanggilan fungsi i2c_write(0xC0)
, LSB nya 0 jadi merupakan operasi tulis). Setelah mendapatkan alamat slave yang diinginkan, master perlu memberitahukan alamat / register internal slave yang diakses (dengan i2c_write(0x01)
dimana alamat 0×01 merupakan bearing byte). Selanjutnya master perlu memulai sinyal START lagi untuk operasi pembacaan dari alamat internal slave 0×01. Karena selanjutnya adalah operasi pembacaan maka menjadi i2c_write(0x0C1)
. Untuk pembacaan, gunakan fungsi i2c_read(0)
, dimana paramater 0 akan menyebabkan tidak perlunya pemberian sinyal ACK setelah pembacaan. Fungsi i2c_read jika sukses akan mengembalikan nilai pembacaan. Nilai hasil pembacaan akan menjadi parameter bagi fungsi convertToLCDStr
. Setelah selesai pembacaan, master mengirim sinyal STOP dengan i2c_stop()
. Dan program akan kembali lagi dari penempatan kursor LCD ke 0,0.Mungkin masih ada yang belum tahu register-register yang disediakan oleh CMPS03, berikut 16 register yang dapat diakses:
No Register | Fungsi |
---|---|
0 | Nomor revisi software dari CMPS03. |
1 | Pembacaan data kompas (compass bearing) dalam 1 byte. Nilainya memiliki range 0-255 untuk 360 derajat. |
2, 3 | Pembacaan data kompas dalam 1 word. Rangenya 0-3599 untuk 360 derajat. Register 2 untuk data 8 bit teratas. Dan register 3 untuk 8 bit terendah hingga LSB. |
4, 5 | Internal test - Beda sinyal sensor 1 sebanyak 16 bit (bertipe signed word) |
6, 7 | Internal test - Beda sinyal sensor 1 sebanyak 16 bit (bertipe signed word) |
8, 9 | Internal test - Nilai kalibrasi 1 sebanyak 16 bit (bertipe signed word) |
10, 11 | Internal test - Nilai kalibrasi 2 sebanyak 16 bit (bertipe signed word) |
12 | Tidak digunakan. Akan memberikan nilai 0 |
13 | Tidak digunakan. Akan memberikan nilai 0 |
14 | Tanda untuk selesainya kalibrasi. Nilainya 0 saat mode kalibrasi dan tidak terkalibrasi, selain itu nilainya 255. |
15 | Perintah untuk kalibrasi. Tulis 255 untuk memasuki mode kalibrasi. Tulis 0 untuk keluar. |
Well, mudah-mudahan cukup jelas . Saya biasanya menggunakan dua uC jika digunakan sebagai pembantu navigasi robot, dimana AT90s2313 ini akan terus memberikan nilai pembacaan ke uC lainnya melalui komunikasi USART. Jika kamu hendak membuat aplikasi kompas digital, maka register 2 dan 3 dari CMPS03 bisa membantu nilainya lebih akurat. Register 2 dan 3 akan memberikan data sebesar 1 word (0-3599 untuk 360 derajat). Register 2 untuk 8 bit teratas (dari MSB-nya) dan register 3 untuk 8 bit terendah (hingga LSB-nya).
Referensi:
- CMPS03 - Robot Compass Module
- CMPS03 - Devantech Magnetic Compass
- http://gedex.web.id/archives/2008/05/18/interfacing-antara-avr-dengan-cmps03/
bisa minta emailnya mas?soalnya mau nanya-nanya soal programing
ReplyDelete