document and correct VFD library
This commit is contained in:
parent
c68ab36d97
commit
8002255525
152
lib/vfd_hv518.c
152
lib/vfd_hv518.c
|
@ -12,10 +12,13 @@
|
|||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
/* Copyright (c) 2016 King Kévin <kingkevin@cuvoodoo.info> */
|
||||
/* this library is used to drive the vacuum fluorescent display extracted from a Samsung SER-6500 cash register
|
||||
* it uses three chained supertex HV518 shift register VFD drivers */
|
||||
|
||||
/** library to drive vacuum fluorescent display using supertex HV518 shift register VFD drivers (code)
|
||||
* @details the current configuration is for a VFD extracted from a Samsung SER-6500 cash register
|
||||
* @file vfd_hv518.c
|
||||
* @author King Kévin <kingkevin@cuvoodoo.info>
|
||||
* @date 2016
|
||||
* @note peripherals used: SPI @ref vfd_hv518_spi , GPIO @ref vfd_hv518_gpio , timer @ref vfd_hv518_timer
|
||||
*/
|
||||
/* standard libraries */
|
||||
#include <stdint.h> // standard integer types
|
||||
#include <stdlib.h> // general utilities
|
||||
|
@ -30,53 +33,37 @@
|
|||
#include "global.h" // global definitions
|
||||
#include "vfd_hv518.h" // VFD library API
|
||||
|
||||
/* supertex HV518 VFD driver pins */
|
||||
/* port on which the pins to control the supertex HV518 VFD driver are
|
||||
* we use port A because of the SPI interface */
|
||||
#define VFD_PORT GPIOA
|
||||
#define VFD_PORT_RCC RCC_GPIOA
|
||||
/* SPI port to use */
|
||||
#define VFD_SPI SPI1
|
||||
#if (VFD_SPI==SPI1)
|
||||
#define VFD_SPI_RCC RCC_SPI1
|
||||
#define VFD_SPI_IRQ NVIC_SPI1_IRQ
|
||||
#elif (VFD_SPI==SPI2)
|
||||
#define VFD_SPI_RCC RCC_SPI2
|
||||
#define VFD_SPI_IRQ NVIC_SPI2_IRQ
|
||||
#endif
|
||||
/* strobe pin to enable high voltage output
|
||||
* high voltage is output on low
|
||||
* drive using a GPIO PA6 (normally MISO) */
|
||||
#define VFD_STR GPIO6
|
||||
/* latch enable pin
|
||||
* store the shifted data on low
|
||||
* output the parallel data on high
|
||||
* use GPIO (PA4) (NSS does not work as SS) */
|
||||
#define VFD_NLE GPIO4
|
||||
/* clock signal
|
||||
* drive using SPI SCK (PA5) */
|
||||
#define VFD_CLK GPIO_SPI1_SCK
|
||||
/* data input, where the data is shifted to
|
||||
* drive using SPI MOSI (PA7) */
|
||||
#define VFD_DIN GPIO_SPI1_MOSI
|
||||
/* timer for automatic refresh */
|
||||
#define VFD_TIMER TIM2
|
||||
#if (VFD_TIMER==TIM2)
|
||||
#define VFD_TIMER_RCC RCC_TIM2
|
||||
#define VFD_TIMER_IRQ NVIC_TIM2_IRQ
|
||||
#elif (VFD_TIMER==TIM3)
|
||||
#define VFD_TIMER_RCC RCC_TIM3
|
||||
#define VFD_TIMER_IRQ NVIC_TIM3_IRQ
|
||||
#elif (VFD_TIMER==TIM4)
|
||||
#define VFD_TIMER_RCC RCC_TIM4
|
||||
#define VFD_TIMER_IRQ NVIC_TIM4_IRQ
|
||||
#elif (VFD_TIMER==TIM5)
|
||||
#define VFD_TIMER_RCC RCC_TIM5
|
||||
#define VFD_TIMER_IRQ NVIC_TIM5_IRQ
|
||||
#endif
|
||||
/** @defgroup vfd_hv518_gpio GPIO to control supertex HV518 VFD drivers
|
||||
* @{
|
||||
*/
|
||||
#define VFD_PORT GPIOA /**< GPIO port */
|
||||
#define VFD_PORT_RCC RCC_GPIOA /**< GPIO port peripheral clock */
|
||||
#define VFD_STR GPIO6 /**< strobe pin to enable high voltage output, high voltage is output on low */
|
||||
#define VFD_NLE GPIO4 /**< latch enable pin, stores the shifted data on low, output the parallel data on high */
|
||||
/** @} */
|
||||
|
||||
/* ASCII characters encoded for 7 segments display
|
||||
* starts with space
|
||||
/** @defgroup vfd_hv518_spi SPI to send data to supertex HV518 VFD drivers
|
||||
* @{
|
||||
*/
|
||||
#define VFD_SPI_RCC RCC_SPI1 /**< SPI peripheral */
|
||||
#define VFD_SPI_PORT GPIOA /**< GPIO port */
|
||||
#define VFD_SPI_PORT_RCC RCC_GPIOA /**< GPIO port peripheral clock */
|
||||
#define VFD_SPI_IRQ NVIC_SPI1_IRQ /**< SPI peripheral interrupt signal */
|
||||
#define VFD_SPI_ISR spi1_isr /**< SPI interrupt service routine */
|
||||
#define VFD_CLK GPIO_SPI1_SCK /**< clock signal */
|
||||
#define VFD_DIN GPIO_SPI1_MOSI /**< data input, where the data is shifted to */
|
||||
/** @} */
|
||||
|
||||
/** @defgroup vfd_hv518_timer timer for automatic display blocks refresh
|
||||
* @{
|
||||
*/
|
||||
#define VFD_TIMER_RCC RCC_TIM2 /**< timer peripheral clock */
|
||||
#define VFD_TIMER_IRQ NVIC_TIM2_IRQ /**< timer interrupt signal */
|
||||
#define VFD_TIMER_ISR tim2_isr /**< timer interrupt service routine */
|
||||
/** @} */
|
||||
|
||||
/** ASCII characters encoded for the 7 segments digit block
|
||||
* @note starts with space
|
||||
*/
|
||||
static const uint8_t ascii_7segments[] = {
|
||||
0b00000000, // space
|
||||
|
@ -176,10 +163,9 @@ static const uint8_t ascii_7segments[] = {
|
|||
0b01000000, // ~
|
||||
};
|
||||
|
||||
/* font for the 5x7 dot matrix display
|
||||
* from http://sunge.awardspace.com/glcd-sd/node4.html
|
||||
* first value is left-most line
|
||||
* LSB is top dot, MSB is not used
|
||||
/** font for the 5x7 dot matrix block
|
||||
* @details first value is left-most line, LSB is top dot, MSB is not used
|
||||
* @note from http://sunge.awardspace.com/glcd-sd/node4.html
|
||||
*/
|
||||
static const uint8_t font5x7[][5] = {
|
||||
{0x00, 0x00, 0x00, 0x00, 0x00}, // (space)
|
||||
|
@ -279,9 +265,8 @@ static const uint8_t font5x7[][5] = {
|
|||
{0b00001000, 0b00000100, 0b00001100, 0b00001000, 0b00000100} // ~
|
||||
};
|
||||
|
||||
/* pictures for the 5x7 dot matrix display
|
||||
* first value is left-most line
|
||||
* LSB is top dot, MSB is not used
|
||||
/** pictures for the 5x7 dot matrix block
|
||||
* @details first value is left-most line, LSB is top dot, MSB is not used
|
||||
*/
|
||||
static const uint8_t pict5x7[][5] = {
|
||||
{0x08, 0x08, 0x2A, 0x1C, 0x08}, // ->
|
||||
|
@ -300,18 +285,23 @@ static const uint8_t pict5x7[][5] = {
|
|||
{0x00, 0x00, 0x00, 0x00, 0x00} // nothing
|
||||
};
|
||||
|
||||
/* the 32 bits values to be shifted out to the VFD driver
|
||||
* split into 16 bit for SPI transfer
|
||||
* since the bits for digits and matrix are independent, they can be combined
|
||||
* we have more matrix (12) than digits (10)
|
||||
/** the 32 bits values to be shifted out to the VFD driver
|
||||
* @note split into 16 bit for SPI transfer
|
||||
* @note since the bits for digits and matrix are independent, they can be combined
|
||||
* @note we have more matrix (12) than digits (10)
|
||||
*/
|
||||
static uint16_t driver_data[VFD_MATRIX][VFD_DRIVERS*2] = {0};
|
||||
static volatile uint8_t spi_i = 0; // which driver data is being transmitted
|
||||
static volatile uint8_t vfd_grid = 0; // which grid/part to activate (single digits and matrix can be combined)
|
||||
static const uint32_t digit_mask = 0x00fffff0; // the bits used for selecting then digit and 7 segment anodes (for the second driver)
|
||||
/** which driver data is being transmitted */
|
||||
static volatile uint8_t spi_i = 0;
|
||||
/** which grid/part to activate
|
||||
* @note digits and matrix can be combined
|
||||
*/
|
||||
static volatile uint8_t vfd_grid = 0;
|
||||
/** the bits used for selecting then digit and 7 segment anodes
|
||||
* @note for the second driver
|
||||
*/
|
||||
static const uint32_t digit_mask = 0x00fffff0;
|
||||
|
||||
/* set digit <nb> to ASCII character <c>
|
||||
* use the MSB of <c> to enable the dot */
|
||||
void vfd_digit(uint8_t nb, char c)
|
||||
{
|
||||
if (!(nb<VFD_DIGITS)) { // check the digit exists
|
||||
|
@ -352,8 +342,6 @@ void vfd_digit(uint8_t nb, char c)
|
|||
driver_data[nb][3] = (digit_data>>16); // write back data (most significant half)
|
||||
}
|
||||
|
||||
/* set dot matrix <nb> to ASCII character <c>
|
||||
* non ASCII characters are used for pictures */
|
||||
void vfd_matrix(uint8_t nb, char c)
|
||||
{
|
||||
// check the matrix exists
|
||||
|
@ -399,7 +387,6 @@ void vfd_matrix(uint8_t nb, char c)
|
|||
}
|
||||
}
|
||||
|
||||
/* clear VFD display */
|
||||
void vfd_clear(void)
|
||||
{
|
||||
for (uint8_t i=0; i<LENGTH(driver_data); i++) {
|
||||
|
@ -409,7 +396,6 @@ void vfd_clear(void)
|
|||
}
|
||||
}
|
||||
|
||||
/* test VFD display (light up all anodes) */
|
||||
void vfd_test(void)
|
||||
{
|
||||
for (uint8_t i=0; i<LENGTH(driver_data); i++) {
|
||||
|
@ -419,21 +405,18 @@ void vfd_test(void)
|
|||
}
|
||||
}
|
||||
|
||||
/* switch VFD display on */
|
||||
void vfd_on(void)
|
||||
{
|
||||
gpio_clear(VFD_PORT, VFD_STR); // enable HV output
|
||||
timer_enable_counter(VFD_TIMER); // start timer to periodically output that to the parts
|
||||
}
|
||||
|
||||
/* switch VFD display off */
|
||||
void vfd_off(void)
|
||||
{
|
||||
gpio_set(VFD_PORT, VFD_STR); // disable HV output
|
||||
timer_disable_counter(VFD_TIMER); // stop timer to periodically output that to the parts
|
||||
}
|
||||
|
||||
/* setup VFD */
|
||||
void vfd_setup(void)
|
||||
{
|
||||
/* setup GPIO to control the VFD */
|
||||
|
@ -446,8 +429,9 @@ void vfd_setup(void)
|
|||
|
||||
/* setup SPI to transmit data */
|
||||
rcc_periph_clock_enable(VFD_SPI_RCC); // enable SPI clock
|
||||
gpio_set_mode(VFD_PORT, GPIO_MODE_OUTPUT_50_MHZ, GPIO_CNF_OUTPUT_ALTFN_PUSHPULL, VFD_CLK); // set VFD pin to alternative function push-pull
|
||||
gpio_set_mode(VFD_PORT, GPIO_MODE_OUTPUT_50_MHZ, GPIO_CNF_OUTPUT_ALTFN_PUSHPULL, VFD_DIN); // set VFD pin to alternative function push-pull
|
||||
rcc_periph_clock_enable(VFD_SPI_PORT_RCC); // enable clock for VFD SPI GPIO
|
||||
gpio_set_mode(VFD_SPI_PORT, GPIO_MODE_OUTPUT_50_MHZ, GPIO_CNF_OUTPUT_ALTFN_PUSHPULL, VFD_CLK); // set VFD pin to alternative function push-pull
|
||||
gpio_set_mode(VFD_SPI_PORT, GPIO_MODE_OUTPUT_50_MHZ, GPIO_CNF_OUTPUT_ALTFN_PUSHPULL, VFD_DIN); // set VFD pin to alternative function push-pull
|
||||
|
||||
spi_reset(VFD_SPI); // clear SPI values
|
||||
/* set SPI:
|
||||
|
@ -485,11 +469,8 @@ void vfd_setup(void)
|
|||
vfd_clear(); // initialize values
|
||||
}
|
||||
|
||||
#if (VFD_SPI==SPI1)
|
||||
void spi1_isr(void)
|
||||
#elif (VFD_SPI==SPI2)
|
||||
void spi2_isr(void)
|
||||
#endif
|
||||
/** SPI interrupt service routine called when data has been transmitted */
|
||||
void VFD_SPI_ISR(void)
|
||||
{
|
||||
if (SPI_SR(VFD_SPI) & SPI_SR_TXE) { // transmission buffer empty
|
||||
if (spi_i<LENGTH(driver_data[0])) { // check if data is available
|
||||
|
@ -504,15 +485,8 @@ void spi2_isr(void)
|
|||
}
|
||||
}
|
||||
|
||||
#if (VFD_TIMER==TIM2)
|
||||
void tim2_isr(void)
|
||||
#elif (VFD_TIMER==TIM3)
|
||||
void tim3_isr(void)
|
||||
#elif (VFD_TIMER==TIM4)
|
||||
void tim4_isr(void)
|
||||
#elif (VFD_TIMER==TIM5)
|
||||
void tim5_isr(void)
|
||||
#endif
|
||||
/** timer interrupt service routine called time passed */
|
||||
void VFD_TIMER_ISR(void)
|
||||
{
|
||||
if (timer_get_flag(VFD_TIMER, TIM_SR_UIF)) { // overflow even happened
|
||||
timer_clear_flag(VFD_TIMER, TIM_SR_UIF); // clear flag
|
||||
|
|
|
@ -12,28 +12,40 @@
|
|||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
/* Copyright (c) 2016 King Kévin <kingkevin@cuvoodoo.info> */
|
||||
/* this library is used to drive the vacuum fluorescent display extracted from a Samsung SER-6500 cash register
|
||||
* it uses three chained supertex HV518 shift register VFD drivers */
|
||||
/** library to drive vacuum fluorescent display using supertex HV518 shift register VFD drivers (API)
|
||||
* @details the current configuration is for a VFD extracted from a Samsung SER-6500 cash register
|
||||
* @file vfd_hv518.h
|
||||
* @author King Kévin <kingkevin@cuvoodoo.info>
|
||||
* @date 2016
|
||||
* @note peripherals used: USART @ref usart
|
||||
*/
|
||||
|
||||
/* the number of blocks available on the VFD */
|
||||
/** number HV518 VFD drivers */
|
||||
#define VFD_DRIVERS 3
|
||||
/** number of digits blocks on SER-6500 VFD */
|
||||
#define VFD_DIGITS 10
|
||||
/** number of dot matrix blocks on SER-6500 VFD */
|
||||
#define VFD_MATRIX 12
|
||||
|
||||
/* set digit <nb> to ASCII character <c>
|
||||
* use the MSB of <c> to enable the dot */
|
||||
/** set character to digit block
|
||||
* @param[in] nb digit block to set
|
||||
* @param[in] c ASCII character to set
|
||||
* @note use the MSB of @p nb to enable the dot
|
||||
*/
|
||||
void vfd_digit(uint8_t nb, char c);
|
||||
/* set dot matrix <nb> to ASCII character <c>
|
||||
* non ASCII characters are used for pictures */
|
||||
/** set character to matrix block
|
||||
* @param[in] nb matrix block to set
|
||||
* @param[in] c ASCII character to set
|
||||
* @note on ASCII characters are used for pictures
|
||||
*/
|
||||
void vfd_matrix(uint8_t nb, char c);
|
||||
/* clear VFD display */
|
||||
/** clear VFD display */
|
||||
void vfd_clear(void);
|
||||
/* test VFD display (light up all anodes) */
|
||||
/** test VFD display (light up all segments) */
|
||||
void vfd_test(void);
|
||||
/* transmit every digit and matrix */
|
||||
/** switch VFD on */
|
||||
void vfd_on(void);
|
||||
/* switch VFD display off */
|
||||
/** switch VFD display off */
|
||||
void vfd_off(void);
|
||||
/* setup VFD */
|
||||
/** setup VFD */
|
||||
void vfd_setup(void);
|
||||
|
|
Loading…
Reference in New Issue