Projekte
BirgerT
nibo2_fork#01
bt_lib_terminal.c
Projekte
Forum
Doku
Öffentliche Projekte
Startseite
Beispielprogramme
Projekte von anderen
Welcome
Username
Passwort
Eingeloggt bleiben
Zugangsdaten vergessen?
Registrieren
Projektverwaltung
⇨ Please choose! ⇦
——————————————————
✎ Create new project...
★ Browse existing projects...
——————————————————
⚬ MotorTest#1
⚬ C Tutorial 8#1
⚬ NIBO2 C Project#1
⚙ C Tutorial 15#1
⚬ 2010_11_18_el_test001#1
nibo2_fork#01
BSD_license.h
bt_lib_debugutil.c
bt_lib_debugutil.h
bt_lib_glcd.c
bt_lib_glcd.h
bt_lib_grafix.c
bt_lib_grafix.h
bt_lib_terminal.c
bt_lib_terminal.h
bt_lib_uart.c
bt_lib_uart.h
bt_lib_utils.h
lumpylumpy.h
main.c
nibo2_audio.c
nibo2_audio.h
nibo2_copro.c
nibo2_copro.h
nibo2_copro_cmd.h
nibo2_font.h
nibo2_global.h
nibo2_main_menu.h
nibo2_pwm_leds.c
nibo2_pwm_leds.h
nibo2_register.c
nibo2_register.h
nibo2_sensors.c
nibo2_sensors.h
test_debugutil.h
test_gfx_draw.h
xmas1.h
Project details
Compiler settings
Nachrichten
Sie sind nicht eingeloggt.
Neuigkeiten
★
NiboRoboLib 3.6
2017-01-17: Neue Version 3.6
★
NiboRoboLib 3.4.1
2016-04-16: Neue Version 3.4.1
★
Coding Tutorial
2015-11-22: Jetzt auch für den NIBO burger!
Site-Statistic
7426 private projects
385 public projects
16180353 lines compiled
58212 builds
NIBO
@
nibo2_fork_01/bt_lib_terminal.c [read only]
////////////////////////////////////////////////////////////////////////// // // BT LIB TERMINAL // // (c) Birger Töpelmann toepelmann(A)web.de Version 141012a // // Funktionen für die (serielle) Kommunikation mit der AVR MEGA MCU // über UART0, UART1 und GLCD im Textmodus mit 8 Zeilen a 21 Zeichen: // // Dokumentation in bt_lib_terminal.h // // // TODO // // ////////////////////////////////////////////////////////////////////////// // // BSD License see "license.h" // #include "BSD_license.h" // #include "nibo2_global.h" //#include "bt_lib_utils.h" // Sammlung von Makros und Typedefs //#include "bt_lib_uart.h" // UART Kommunikation mit FIFOs //#include "bt_lib_terminal.h" // Mensch Mikrocontroller Kommunikation // // // ================================================= Ausgabe States // uint8_t term_dev; // Terminal Device Mask = Geräte, an die Ausgabe erfolgen soll uint8_t term_state = 0; // Ausgabestatus uint8_t term_lastscr = 0; // letzter Ausgabescreen /* // // unterstützte // =========================================== VT100 / ANSI Controls // #define ESC "\x1b" // Escape #define ED ESC"[2J" // Erase Display #define RST ESC"2c" // Display Reset #define CUP(z,s) ESC"["#z";"#s"H" // Cursor Position Zeile,Spalte #define CUU(z) ESC"["#z"A" // Cursor Up z Zeilen #define CUD(z) ESC"["#z"B" // Cursor Down z Zeilen #define CUF(s) ESC"["#s"C" // Cursor Forward s Spalten #define CUB(s) ESC"["#s"D" // Cursor Backward s Spalten #define SCP ESC"[s" // Save Cursor Position #define RCP ESC"[u" // Restore Cursor Position // // Zeichenattribute setzen #define SGR(p) ESC"["#p"m" // Set Grafics Rendition p // - Nibo2 GLCD - Tera Term - PuTTYtel // SGR(0) -> Standard Werte // SGR(1) -> Intensität (Fett) - ignoriert - Gelbe Schrift - hell // SGR(4) -> Unterstreichen ein - i.O. - i.O. - i.O. // SGR(5) -> Blinken ein - invers - Rote Schrift - i.O. (Setup) // SGR(7) -> Inverse Schrift - i.O. - i.O. - i.O. // SGR(8) -> Unsichtbare Schrift - ignoriert - ohne Funktion - ohne Funktion // // Lineattribute // - Nibo2 GLCD = Zeichen Attribut, // - Teraterm ohne Funktion, // - PuTTYtel = i.O. (ganze Zeile) // #define DHO ESC"#3" // doppelte Höhe + doppelte Breite (obere Hälfte) #define DHU ESC"#4" // doppelte Höhe + doppelte Breite (untere Hälfte) #define DZB ESC"#6" // doppelte Zeichenbreite #define NRM ESC"#5" // Normale Zeichenbreite und -höhe */ //const char term_clsstr[] PROGMEM = {ESC"[2J"}; const char term_cursor[] PROGMEM = {ESC"[@;@H"}; ////////////////////////////////////////////////////////////////////////// // // Terminal Zeichenausgabe // ////////////////////////////////////////////////////////////////////////// // /* // // ALTE VERSION mit Direktausgabe (und Bufferüberlauf) // void print_char(char ch){ // direkte Ausgabe zu den UARTs if ((term_dev & UART0) == UART0 ) { uart0_txd_char(ch); } if ((term_dev & UART1) == UART1 ) { // uart1_txt_char(ch); } // TODO // direkte Ausgabe an GLCD if ((term_dev & GLCD) == GLCD ) { // {glcd_print_char(ch); } // Ausgabe in Terminal Textbuffer } */ /* ----------------------------------------------------- GLCD ANSI PRINT STRING: GLCD über ANSI Sequenzen steuern und Text im Terminalmodus ausgeben -> x, y == absolute Pixeladresse -------------------------------------------------------*/ // /***************************************************** VT100 / ANSI Controls // // #define ESC "\x1b" // Escape #define ED ESC"[2J" // Erase Display #define RST ESC"2c" // Display Reset #define CUP(z,s) ESC"["#z";"#s"H" // Cursor Position Zeile,Spalte #define CUU(z) ESC"["#z"A" // Cursor Up z Zeilen #define CUD(z) ESC"["#z"B" // Cursor Down z Zeilen #define CUF(s) ESC"["#s"C" // Cursor Forward s Spalten #define CUB(s) ESC"["#s"D" // Cursor Backward s Spalten #define SCP ESC"[s" // Save Cursor Position #define RCP ESC"[u" // Restore Cursor Position // // Zeichenattribute setzen #define SGR(p) ESC"["#p"m" // Set Grafics Rendition p // - Nibo2 GLCD - Tera Term - PuTTYtel // SGR(0) -> Standard Werte // SGR(1) -> Intensität (Fett) - ignoriert - Gelbe Schrift - hell // SGR(4) -> Unterstreichen ein - i.O. - i.O. - i.O. // SGR(5) -> Blinken ein - invers - Rote Schrift - i.O. (Setup) // SGR(7) -> Inverse Schrift - i.O. - i.O. - i.O. // SGR(8) -> Unsichtbare Schrift - ignoriert - ohne Funktion - ohne Funktion // // Lineattribute - Nibo2 GLCD = Attribut, Teraterm ohne Funktion, PuTTYtel = i.O. (ganze Zeile) #define DHO ESC"#3" // doppelte Höhe + doppelte Breite (obere Hälfte) #define DHU ESC"#4" // doppelte Höhe + doppelte Breite (untere Hälfte) #define DZB ESC"#6" // doppelte Zeichenbreite #define NRM ESC"#5" // Normale Zeichenbreite und -höhe // ***********************************************************************/ // // #define TERM_NORM 0 // normale Zeichen #define TERM_HELL 0x01 // intensiv #define TERM_LINE 0x02 // unterstrichen #define TERM_BLINK 0x04 // Blinken #define TERM_INV 0x08 // invertiert // Zeilenattribute #define TERM_BREIT 0x10 // Breitschrift #define TERM_BIG_O 0x20 // Doppelte Höhe oben #define TERM_BIG_U 0x40 // Doppelte Höhe unten // // ////////////////////////////////////////////////////////////////////////// // // Textbuffer für 8 Zeilen mit 21 ASCII Zeichen + '\n' für // - das GLCD im Terminalmodus oder // - als Ausgabebuffer für das Terminal im GFX Modus // #define Z_max 8 // !! maximale Zeilennummer // darf nicht größer als 8 sein; Zeichenattributflags #define S_max 21 // maximale Spaltennummer #define Z_len 22 // = (S_max + 1) Buffer Zeilenlänge (+"\n") #define TextBuffer_size (Z_max * Z_len) // Platz für ASCII Zeichen #define TermBuffer_size TextBuffer_size + 3 * Z_len // + ANSI Attribute // // der ASCII Text- und ANSI Attribute Buffer char term_glcd_textbuffer[TermBuffer_size]; // #define term_dm_blink term_glcd_textbuffer + TextBuffer_size #define term_dm_inv term_dm_blink + Z_len #define term_dm_uline term_dm_inv + Z_len // ////////////////////////////////////////////////////////////////////////// // // Textbuffer Verwaltung // - Bufferzeiger // - Attribute // - Merker // typedef struct { char* buffer_di; // Schreibposition char* buffer_si; // Leseposition uint8_t zeile; // Cursorposition uint8_t spalte; uint8_t ch_attr; // aktuelles Zeichenattribut uint8_t dm_mask; // Zeilen Maske für dm setzen // uint8_t dm_blink[Z_len];// GLCD Zeichenattribut Blinken // uint8_t dm_inv[Z_len]; // GLCD Zeichenattribut Invers // uint8_t dm_uline[Z_len];// GLCD Zeichenattribut Underline uint8_t li_attr[Z_max]; // Zeilenattribute (ESC#3,.4,.5,.6) uint8_t cursavz; // gespeicherte Cursorposition uint8_t cursavs; uint8_t input_state; // Control State Eingabe uint8_t print_state; // Control State Ausgabe }term__buffer_t; // term__buffer_t terminal; // ////////////////////////////////////////////////////////////////////////// // void terminal_init(){ char ze; // Leerzeichen o. Newline für die Zeilenenden uint8_t zi, si; // Zeilen- und Spaltenzähler // zum Buffer löschen -> Zeiger ans Bufferende terminal.buffer_di = term_glcd_textbuffer + TermBuffer_size -1; // Buffer ANSI Attributflags löschen si = 3 * Z_len; do { *terminal.buffer_di-- = 0; } while (--si > 0); // Zeiger auf das letzte Byte ASCII Buffer terminal.buffer_si = terminal.buffer_di; // Buffer ASCII Zeichen löschen // Alle Zeilen und.. zi = Z_max; do { // ..alle Spalten von hinten her löschen si = S_max; ze = '\n'; *terminal.buffer_di-- = ze; ze = ' '; do { *terminal.buffer_di-- = ze; } while (--si > 0); terminal.li_attr[--zi] = 0; } while (zi > 0); // ASCII Bufferende als Stringende markieren *terminal.buffer_si = 0; // Terminal Merker Variablen Reset // terminal.buffer_di zeigt nach dem Löschen vor den Bufferanfang terminal.buffer_di = term_glcd_textbuffer; terminal.buffer_si = terminal.buffer_di; terminal.zeile = 0; terminal.spalte = 0; terminal.ch_attr = 0; terminal.dm_mask = 0; // si = S_max; // do { // terminal.dm_blink[si] = 0; // terminal.dm_inv[si] = 0; // terminal.dm_uline[si] = 0; // } while (si-- > 0); terminal.cursavz = 0; terminal.cursavs = 0; terminal.input_state = 0; terminal.print_state = 0; } // ////////////////////////////////////////////////////////////////////////// // void terminal_curpos(uint8_t zeile, uint8_t spalte){ // Wertebegrenzung if ((zeile > 0) && (zeile <= Z_max)) { terminal.zeile = zeile -1; } if ((spalte > 0) && (spalte <= S_max)) { terminal.spalte = spalte -1; } // Buffer Adresse setzen terminal.buffer_di = term_glcd_textbuffer; terminal.buffer_di += terminal.zeile * Z_len; terminal.buffer_di += terminal.spalte; } // ////////////////////////////////////////////////////////////////////////// // void terminal_put_char(char ch){ enum terminal_char_states{ NORMAL_CHAR, ESC_DETECTED, CSI_DETECTED, LINE_ATTR, BIG_CHAR, CU_POS, CU_SAVE, CU_REST, GETNUM1, GETNUM2 }; static uint8_t state, csi; static int8_t num1, num2; ///////////////////////////////////// CONTROL CHAR if (ch < ' ') { if (ch == 0x1b) { // ESCAPE Zeichen state = ESC_DETECTED; } else if (ch == 0x0d) { // Return terminal_curpos(0,1); } else if (ch == 0x0a) { // neue Zeile // print_curpos(term.zeile+2,0); terminal_curpos(terminal.zeile+2,1); } else if (ch == 0) { // Stringendezeichen ?! state = NORMAL_CHAR; } } // if CONTROL CHAR // ///////////////////////////////////// NORMAL CHAR -> ASCII Buffer // else if (state == NORMAL_CHAR) { //debug_printf(".zeile %u .spalte %u, di %x = %c", terminal.zeile, terminal.spalte, terminal.buffer_di,ch); // muss char in nächste Zeile ? if (terminal.spalte >= S_max) { terminal.spalte = 0; if (terminal.zeile >= Z_max-1) { terminal.zeile = 0; } else { terminal.zeile++; } // Bufferpointer neu berechnen terminal_curpos(terminal.zeile+1,terminal.spalte+1); } *terminal.buffer_di++ = ch; terminal.spalte++; //debug_memory_dump(BYTES,RAM,term_glcd_textbuffer,48); //debug_wait_for_char('c'); } // if NORMAL_CHAR // ////////////////////////////////////// ESC SEQUENCE // else if (state == ESC_DETECTED) { if (ch == '[') { state = CSI_DETECTED; csi = NORMAL_CHAR; } else if (ch == 'c') { // ESC"c" Reset Display terminal_init(); state = NORMAL_CHAR; } else if (ch == '#') { // ESC"#" Lineattribut state = LINE_ATTR; } else { state = NORMAL_CHAR; // unbekannt -> ignorieren } } // if ESC_DETECTED /////////////////////////////////////// ESC"[" else if (state == CSI_DETECTED) { if (csi == NORMAL_CHAR) { csi = GETNUM1; num1 = 0; num2 = 0; } // die Zeichen hinter CSI sollten eine Zahl sein if ((ch >= '0') && (ch <= '9')) { ch &= 0x0f; if (csi == GETNUM1) { num1 = 10 * num1 + ch; } else if (csi == GETNUM2) { num2 = 10 * num2 + ch; } } else if (ch == ';') { // auf zweite Zahl abfragen csi = GETNUM2; } // das eigentliche Kommando in der ESC Sequenz else if (ch == 'J') { // Bildschirm loeschen if (num1 == 2) { terminal_init(); state = NORMAL_CHAR; } state = NORMAL_CHAR; } /////////////////////////////////////// CURSOR else if (ch == 'H') { // Cursor positionieren if (num1 == 0) num1 = 1; if (num2 == 0) num2 = 1; csi = CU_POS; } else if (ch == 'A') { // Cursor auf if (num1 == 0) num1 = 1; num1 = terminal.zeile; // - num1; csi = CU_POS; } else if (ch == 'B') { // Cursor ab if (num1 == 0) num1 = 1; num1 = terminal.zeile + num1 +1; csi = CU_POS; } else if (ch == 'C') { // Cursor rechts if (num1 == 0) num1 = 1; num2 = terminal.spalte + num1 +1; num1 = 0; csi = CU_POS; } else if (ch == 'D') { // Cursor links if (num1 == 0) num1 = 1; num2 = terminal.spalte; // - num1; num1 = 0; csi = CU_POS; } ///////////////////////////////////////// ATTRIBUTE else if (ch == 'm') { if(num1 == 0) {terminal.ch_attr = TERM_NORM;} else if(num1 == 1) {terminal.ch_attr |= TERM_HELL;} else if(num1 == 4) {terminal.ch_attr |= TERM_LINE;} else if(num1 == 5) {terminal.ch_attr |= TERM_BLINK;} // Blinken ? else if(num1 == 7) {terminal.ch_attr |= TERM_INV;} state = NORMAL_CHAR; } /////////////////////////////////////// CURSOR else if (ch == 's') { // Cursor speichern terminal.cursavz = terminal.zeile; terminal.cursavs = terminal.spalte; state = NORMAL_CHAR; } else if (ch == 'u') { // Cursor herstellen num1 = terminal.cursavz +1; num2 = terminal.cursavs +1; csi = CU_POS; } else { // kommt hier noch was? state = NORMAL_CHAR; } ////////////////////////////////////////////////////////////////// if (csi == CU_POS) { // passiert in print_curpos // // num1 = zeile 1..8 // if (num1 < 1) num1 = 1; // else if (num1 > Z_max) num1 = Z_max; // // num2 = spalte 1..21 // if (num2 < 1) num2 = 1; // else if (num1 > S_max) num1 = S_max; // // .. terminal_curpos(num1, num2); state = NORMAL_CHAR; } } // if CSI_DETECTED ///////////////////////////////////////// ZEILEN ATTRIBUT else if (state == LINE_ATTR) { if (ch == '3') { ch = TERM_BIG_O; } // ESC"#3" BigChar oben else if (ch == '4') { ch = TERM_BIG_U; } // ESC"#4" BigChar unten else if (ch == '5') { ch = TERM_NORM; } // ESC"#5" normale Groesse else if (ch == '6') { ch = TERM_BREIT; } // ESC"#6" Breitschrift state = NORMAL_CHAR; // unbekannt -> ignorieren terminal.li_attr[terminal.zeile] = ch; } // if LINE_ATTR else state = NORMAL_CHAR; // unbekannt -> ignorieren } // ////////////////////////////////////////////////////////////////////////// // char* terminal_put_str(char* str){ do { char c = *str++; if (c != 0) { terminal_put_char(c); } else return str; } while (1 == 1); while(*str != 0) { terminal_put_char(*str++); } return str; } // ////////////////////////////////////////////////////////////////////////// // PGM_P terminal_put_str_P(PGM_P str){ //debug_memory_dump(BYTES,RAM,term_glcd_textbuffer,64); do { char c = pgm_read_byte(str++); if (c != 0) { terminal_put_char(c); } else { //debug_memory_dump(BYTES,RAM,term_glcd_textbuffer,64); return str; } } while (1 == 1); /* while(*str != 0) { terminal_put_char(pgm_read_byte(str++)); } return str; */ } // ////////////////////////////////////////////////////////////////////////// // void print_strvar_P(PGM_P str,uint8_t var1, uint8_t var2){ uint8_t varnum = 0; uint8_t var = var1; // Normales String Senden bis fertig do { char c = pgm_read_byte(str++); if (c == 0) break; if (c == '@') { c = pgm_read_byte(str++); if (c != '@') { if (varnum++ != 0) { var = var2; } print_99(var); } } terminal_put_char(c); } while (1); } // ////////////////////////////////////////////////////////////////////////// // // Variablen/Zahlen konvertieren und ausgeben // ////////////////////////////////////////////////////////////////////////// // void print_i16d(int16_t val){ if (val < 0) { terminal_put_char('-'); if (val == 0x8000) { // Sonderfall -32768 terminal_put_str_P(PSTR("32768")); } else { // Absolutwert 2*(-1) = +1 print_u16d((uint16_t)(0-val)); } } else { terminal_put_char('+'); print_u16d((uint16_t)val); } } // ////////////////////////////////////////////////////////////////////////// // void print_u16d(uint16_t val){ char digit = '0'; if (val >= 256) { // Zehntausender Stelle if (val >= 40000) { val -= 40000; digit += 4; } if (val >= 20000) { val -= 20000; digit += 2; } if (val >= 10000) { val -= 10000; ++digit; } terminal_put_char(digit); // Tausender Stelle digit = '0'; if (val >= 8000) { val -= 8000; digit += 8; } else if (val >= 4000) { val -= 4000; digit += 4; } if (val >= 2000) { val -= 2000; digit += 2; } if (val >= 1000) { val -= 1000; ++digit; } terminal_put_char(digit); // Hunderter Stelle digit = '0'; if (val >= 800) { val -= 800; digit += 8; } else if (val >= 400) { val -= 400; digit += 4; } if (val >= 200) { val -= 200; digit += 2; } if (val >= 100) { val -= 100; ++digit; } terminal_put_char(digit); // Zehner und Einer = die letzten beiden Stellen 0..99 print_99((uint8_t)val); } // Zahlen kleiner 256 else { terminal_put_char(digit); // digit == '0' terminal_put_char(digit); print_u8d((uint8_t)val); } } // ////////////////////////////////////////////////////////////////////////// // void print_i8d(int8_t val){ if (val < 0) { terminal_put_char('-'); if (val == 0x80) { // Sonderfall -128 terminal_put_str_P(PSTR("128")); } else { // Absolutwert 2*(-1) = +1 print_u8d((uint8_t)(0-val)); } } else { terminal_put_char('+'); print_u8d((uint8_t)val); } } // ////////////////////////////////////////////////////////////////////////// // void print_u8d(uint8_t val){ char digit = '0'; // Hunderter Stelle if (val >= 200) { val -= 200; digit += 2; } else if (val >= 100) { val -= 100; ++digit; } terminal_put_char(digit); // Zehner und Einer = die letzten beiden Stellen 0..99 print_99((uint8_t)val); } // ////////////////////////////////////////////////////////////////////////// // void print_99(uint8_t val){ // >100 dann Text "ON" if (val >= 100) { terminal_put_char('O'); terminal_put_char('N'); } else { uint8_t digit = '0'; // Zehner Stelle if (val >= 80) { val -= 80; digit += 8; } else if (val >= 40) { val -= 40; digit += 4; } if (val >= 20) { val -= 20; digit += 2; } if (val >= 10) { val -= 10; ++digit; } terminal_put_char(digit); // Einer Stelle = Rest von val terminal_put_char('0'+val); } } // ////////////////////////////////////////////////////////////////////////// // char bin2asc(uint8_t bin){ bin &= 0x0f; if(bin <= 9) return bin + '0'; else return bin + 'A' -10; } // ////////////////////////////////////////////////////////////////////////// // void print_h16(uint16_t val){ print_h8(HIBYTE(val)); print_h8(LOBYTE(val)); } // ////////////////////////////////////////////////////////////////////////// // void print_h8(uint8_t val){ terminal_put_char(bin2asc(val/16)); terminal_put_char(bin2asc(val)); } // ////////////////////////////////////////////////////////////////////////// // void print_b8(uint8_t val){ uint8_t mask = 0x80; do { if ((val & mask)==0) { terminal_put_char('0'); } else { terminal_put_char('1'); } } while ((mask >>= 1) !=0); } // //////////////////////////////////////////////////////////////////////// // // Terminal Funktionstest mit Debug Util // #ifdef _TEST_TERMINAL_H_ // #include "test_terminal.h" // #endif /////////////////////////////////////////////////////////////////// // // EOF
Compiler results:
Werbung
Online
brittney747920000
KylieSat
romanrendall465571132
ruebenmendes25697
warrenhinder6456