Kenji Arai / OSL10564_74HC595

Dependents:   Check_7segLED_driver

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers 7segLed_HC595.cpp Source File

7segLed_HC595.cpp

00001 /*
00002  * Mbed Library / Akizuki 7-segment LED driver [OSL10564-74HC595-x]
00003  *  http://akizukidenshi.com/catalog/g/gM-12643/
00004  *
00005  * Copyright (c) 2018 Kenji Arai / JH1PJL
00006  *  http://www.page.sannet.ne.jp/kenjia/index.html
00007  *  http://mbed.org/users/kenjiArai/
00008  *      Created:    January    7th, 2018
00009  *      Revised:    January   22nd, 2018
00010  */
00011 
00012 #include "7segLed_HC595.h"
00013 
00014 SevenSegLed::SevenSegLed
00015 ( PinName sdo, PinName sclk, PinName latch, PinName bright,
00016   uint8_t num_of_digit
00017 )
00018     : spi_(sdo, NC, sclk), latch_(latch), pwm_(bright)
00019 {
00020     num = num_of_digit;
00021     dot_inf = 0;
00022     zerosuppress = false;
00023     spi_.frequency(1000000);
00024     spi_.format(8,0);
00025     latch_ = 0;
00026     pwm_.period_ms(2);
00027     bright_data = 1.0f;
00028     pwm_.pulsewidth_us(bright_data);
00029 }
00030 
00031 void SevenSegLed::put_num(int32_t dt)
00032 {
00033     wrk = dt;
00034     for(uint32_t i = 0; i < num; i++) {
00035         buf[i] = wrk % 10;  // set each digit value
00036         wrk /= 10;          // next digit
00037     }
00038     num_mode = true;        // set number display mode
00039     seven_seg_n_digt();     // convert to seven segment element and send SPI
00040 }
00041 
00042 void SevenSegLed::put_ascii(const char *data)
00043 {
00044     char dt;
00045 
00046     dot_inf = 0;            // clear all dot
00047     for (uint32_t i = 0; i < BUFFER_SIZE; i++) {
00048         buf[i] = 0;
00049     }
00050     int32_t po = num - 1;
00051     for(uint32_t pi = 0; ; pi++) {
00052         dt = *(data + pi);
00053         //pc.putc(dt);
00054         if (dt == 0) {
00055             break;          // end of strings
00056         }
00057         if (dt == '.') {    // check dot
00058             if (pi == 0) {
00059                 buf[po] = 0;
00060                 po--;
00061                 dot_inf |= 1U << num - 1; // set dot
00062             } else {
00063                 dot_inf |= 1U << (po + 1); // set dot
00064             }
00065             pi++;
00066             dt = *(data + pi);
00067         }
00068         buf[po] = dt - '0';// convert ASCII number to value
00069         po--;
00070         if (po == -1) {
00071             break;
00072         }
00073     }
00074     num_mode = false;       // set none number display mode
00075     seven_seg_n_digt();     // convert to seven segment element and send SPI
00076 }
00077 
00078 void SevenSegLed::put_raw(uint8_t *data)
00079 {
00080     for(uint32_t i = 0; i < num; i++) {
00081         uint8_t dt = *(data + i);
00082         if (dt == 0) {
00083             break;
00084         }
00085         seg[i] = dt;
00086     }
00087     spi_out();
00088 }
00089 
00090 void SevenSegLed::put_dot(uint16_t position)
00091 {
00092     dot_inf = position;
00093 }
00094 
00095 void SevenSegLed::clear_all_dot()
00096 {
00097     dot_inf = 0;
00098 }
00099 
00100 void SevenSegLed::zero_suppress(bool mode)
00101 {
00102     zerosuppress = mode;
00103 }
00104 
00105 void SevenSegLed::brightness(float bright)
00106 {
00107     bright_data = bright;
00108     pwm_.pulsewidth_us((int)(2000 * (1.0f - bright)));
00109 }
00110 
00111 void SevenSegLed::frequency(int32_t freq)
00112 {
00113     spi_.frequency((int)freq);
00114 }
00115 
00116 void SevenSegLed::seven_seg_n_digt()
00117 {
00118     uint8_t const seg_bit[10] =
00119     {0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7c, 0x27, 0x7f, 0x67};
00120     //  0     1     2     3     4     5     6     7     8     9
00121 
00122     for(uint32_t i = 0; i < num; i++) {
00123         seg[i] = seg_bit[buf[i]];   // convert number to segment data
00124     }
00125     if ((num_mode == true) && (zerosuppress == true)) { // zero suppress
00126         for(uint32_t i = 0; i < num; i++) {
00127             if (seg[num -1 - i] == 0x3f) {  // if zero then zero suppress
00128                 if ((num -1 - i) == 0) {
00129                     break;
00130                 }
00131                 seg[num -1 - i] = 0;
00132             } else {
00133                 break;
00134             }
00135         }
00136     }
00137     set_dot();
00138     spi_out();
00139 }
00140 
00141 void SevenSegLed::set_dot()
00142 {
00143     for(uint8_t i = 0; i < num; i++) {
00144         if ((dot_inf >> i) & 0x0001) {      // check dot request
00145             seg[i] |= 0x80;                 // add dot
00146         }
00147     }
00148     for(uint8_t i = 0; i < num; i++) {
00149         if (seg[num -1 - i] & 0x80) {       // check dot is on or off
00150             if (seg[num -1 - i] == 0x80) {  // did zero suppress condition
00151                 seg[num -1 - i] = 0xbf;     // set zero+dot
00152                 for(i++; i < num; i++) {
00153                     if (seg[num -1 - i] == 0) { // check zero suppress
00154                         seg[num -1 - i] = 0x3f; // set zero
00155                     }
00156                 }
00157                 break;
00158             }
00159         }
00160     }
00161 }
00162 
00163 void SevenSegLed::spi_out()
00164 {
00165     pwm_.pulsewidth_us(0);
00166     for(uint32_t i = 0; i < num; i++) {
00167         spi_.write(seg[i]);     // send SPI line
00168     }
00169     latch_ = 1;                 // set latch pulse
00170     wait_us(2);
00171     latch_ = 0;
00172     pwm_.pulsewidth_us((int)(2000 * (1.0f - bright_data)));
00173 }
00174 
00175 //------------------------------------------------------------------------------
00176 // Alphabet on 7segment
00177 // refernce
00178 //  WentWayUp: WebLog
00179 //    http://wentwayup.tamaliver.jp/e400000.html
00180 //------------------------------------------------------------------------------
00181 
00182 #define OFFSET  0x20
00183 
00184 char const alphabet_7seg[] = {
00185     // space
00186     0x00,
00187     // !     "     #     $     %     &     '     (     )     *
00188     0x0a, 0x22, 0x7e, 0x2d, 0x24, 0x3c, 0x20, 0x61, 0x43, 0x63,
00189     // +     ,     -     .     /
00190     0x44, 0x0c, 0x40, 0x10, 0x52,
00191     // 0     1     2     3     4     5     6     7     8     9
00192     0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7c, 0x07, 0x7f, 0x67,
00193     // :     ;     <     =     >     ?
00194     0x09, 0x51, 0x59, 0x48, 0x4d, 0x4b,
00195     // @
00196     0x5f,
00197     // A     B     C     D     E     F     G     H     I  J (another C=0x39)
00198     0x77, 0x7c, 0x58, 0x5e, 0x79, 0x71, 0x3d, 0x74, 0x04, 0x1e,
00199     // K     L     M     N     O     P     Q     R     S     T
00200     0x75, 0x38, 0x55, 0x54, 0x5c, 0x73, 0x6b, 0x50, 0x6c, 0x78,
00201     // U     V     W     X     Y     Z (another W=0x7e)
00202     0x1c, 0x1d, 0x2a, 0x49, 0x6e, 0x1b,
00203     // [     \     ]     ^     _
00204     0x39, 0x64, 0x0f, 0x23, 0x08,
00205     // `
00206     0x02,
00207     // a     b     c     d     e     f     g     h     i     j
00208     0x77, 0x7c, 0x58, 0x5e, 0x79, 0x71, 0x3d, 0x74, 0x04, 0x1e,
00209     // k     l     m     n     o     p     q     r     s     t
00210     0x75, 0x38, 0x55, 0x54, 0x5c, 0x73, 0x6b, 0x50, 0x6c, 0x78,
00211     // u     v     w     x     y     z
00212     0x1c, 0x1d, 0x2a, 0x49, 0x6e, 0x1b,
00213     // {     |     }     ~
00214     0x46, 0x30, 0x70, 0x01
00215 };
00216 
00217 void SevenSegLed::put_strings(const char *data)
00218 {
00219     for(uint32_t i = 0; i < num; i++) {
00220         char c = *(data + i);
00221         if (c <= OFFSET) {          // control charcters
00222             seg[num -1 - i] = 0;
00223         } else if ( c > '~') {      // over '~' characters
00224             seg[num -1 - i] = 0;
00225         } else {                    // serach table
00226             seg[num -1 - i] = alphabet_7seg[c - OFFSET];
00227         }
00228     }
00229     spi_out();
00230 }