updated RGBLEDscrn

This commit is contained in:
Edward Emelianov 2021-04-20 01:36:01 +03:00
parent a438f0515f
commit 59fe90b9e0
7 changed files with 100 additions and 55 deletions

View File

@ -310,12 +310,12 @@ const afont *curfont = &FONTS[FONT14];
/** /**
* @brief choose_font - font selector * @brief choose_font - font selector
* @param newfont - font to choose * @param newfont - font to choose
* @return 0 if all OK * @return 1 if all OK
*/ */
int choose_font(font_t newfont){ int choose_font(font_t newfont){
if(newfont >= FONT_T_MAX || newfont <= FONT_T_MIN) return 1; if(newfont >= FONT_T_MAX || newfont <= FONT_T_MIN) return 0;
curfont = &FONTS[newfont]; curfont = &FONTS[newfont];
return 0; return 1;
} }
/* /*
// getters for current font values // getters for current font values

View File

@ -28,6 +28,29 @@ uint8_t transfer_done = 0; // ==1 when DMA transfer ready
// buffer for DMA // buffer for DMA
static uint32_t dmabuf[SCREEN_WIDTH]; static uint32_t dmabuf[SCREEN_WIDTH];
void iwdg_setup(){
uint32_t tmout = 16000000;
/* Enable the peripheral clock RTC */
/* (1) Enable the LSI (40kHz) */
/* (2) Wait while it is not ready */
RCC->CSR |= RCC_CSR_LSION; /* (1) */
while((RCC->CSR & RCC_CSR_LSIRDY) != RCC_CSR_LSIRDY){if(--tmout == 0) break;} /* (2) */
/* Configure IWDG */
/* (1) Activate IWDG (not needed if done in option bytes) */
/* (2) Enable write access to IWDG registers */
/* (3) Set prescaler by 64 (1.6ms for each tick) */
/* (4) Set reload value to have a rollover each 2s */
/* (5) Check if flags are reset */
/* (6) Refresh counter */
IWDG->KR = IWDG_START; /* (1) */
IWDG->KR = IWDG_WRITE_ACCESS; /* (2) */
IWDG->PR = IWDG_PR_PR_1; /* (3) */
IWDG->RLR = 1250; /* (4) */
tmout = 16000000;
while(IWDG->SR){if(--tmout == 0) break;} /* (5) */
IWDG->KR = IWDG_REFRESH; /* (6) */
}
static inline void gpio_setup(){ static inline void gpio_setup(){
// Enable clocks to the GPIO subsystems, turn on AFIO clocking to disable SWD/JTAG // Enable clocks to the GPIO subsystems, turn on AFIO clocking to disable SWD/JTAG
RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN; RCC->APB2ENR |= RCC_APB2ENR_IOPAEN | RCC_APB2ENR_IOPBEN | RCC_APB2ENR_IOPCEN | RCC_APB2ENR_AFIOEN;
@ -49,13 +72,14 @@ static inline void gpio_setup(){
// setup timer3 for DMA transfers & SCK @ TIM3_CH1 (PA6) // setup timer3 for DMA transfers & SCK @ TIM3_CH1 (PA6)
static inline void tim_setup(){ static inline void tim_setup(){
SET(nOE); // turn off output SCRN_DISBL(); // turn off output
GPIOA->CRL |= CRL(6, CNF_AFPP|MODE_FAST); GPIOA->CRL |= CRL(6, CNF_AFPP|MODE_FAST);
RCC->APB1ENR |= RCC_APB1ENR_TIM3EN; RCC->APB1ENR |= RCC_APB1ENR_TIM3EN;
// 72MHz & 7ARR = 9MHz // PCS=1 don't work;
TIM3->PSC = 20000; TIM3->PSC = 9; // 7.2MHz
TIM3->ARR = 7; TIM3->ARR = 7; // 900kHz
TIM3->CCMR1 = TIM_CCMR1_OC1M; // PWM mode 2 (inactive->active) TIM3->CCMR1 = TIM_CCMR1_OC1M; // PWM mode 2 (inactive->active)
//TIM3->CCMR1 = TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC1M_1; // PWM mode 1 (active->inactive)
TIM3->CCER = TIM_CCER_CC1E; // output 1 enable TIM3->CCER = TIM_CCER_CC1E; // output 1 enable
TIM3->DIER = TIM_DIER_UDE; // enable DMA requests TIM3->DIER = TIM_DIER_UDE; // enable DMA requests
RCC->AHBENR |= RCC_AHBENR_DMA1EN; RCC->AHBENR |= RCC_AHBENR_DMA1EN;
@ -114,12 +138,12 @@ static inline uint8_t getcolrvals(uint8_t colr, uint8_t Ntick){
* @param Nrow - current row number * @param Nrow - current row number
* @param Ntick - tick number (0..7) for quasi-PWM colors * @param Ntick - tick number (0..7) for quasi-PWM colors
*/ */
void ConvertScreenBuf(uint8_t *sbuf, uint8_t Nrow, __attribute__((unused)) uint8_t Ntick){ void ConvertScreenBuf(uint8_t *sbuf, uint8_t Nrow, uint8_t Ntick){ // __attribute__((unused))
//USB_send("ConvertScreenBuf\n"); //USB_send("ConvertScreenBuf\n");
uint8_t *_1st = &sbuf[SCREEN_WIDTH*Nrow], *_2nd = _1st + SCREEN_WIDTH*NBLOCKS; // first and second lines uint8_t *_1st = &sbuf[SCREEN_WIDTH*Nrow], *_2nd = _1st + SCREEN_WIDTH*NBLOCKS; // first and second lines
for(int i = 0; i < SCREEN_WIDTH; ++i){ // ~50us for 64 pixels for(int i = 0; i < SCREEN_WIDTH; ++i){ // ~50us for 64 pixels
uint8_t pinsset = getcolrvals(_1st[i], 0); uint8_t pinsset = getcolrvals(_1st[i], Ntick);
pinsset |= getcolrvals(_2nd[i], 0) << 3; pinsset |= getcolrvals(_2nd[i], Ntick) << 3;
//dmabuf[i] = (i%2) ? ((COLR_pin<<16) | i) : (0b100010); //dmabuf[i] = (i%2) ? ((COLR_pin<<16) | i) : (0b100010);
dmabuf[i] = (COLR_pin << 16) | pinsset; // All BR are 1, BS depending on color dmabuf[i] = (COLR_pin << 16) | pinsset; // All BR are 1, BS depending on color
} }
@ -147,16 +171,18 @@ void TIM_DMA_transfer(uint8_t blknum){
// DMA transfer complete - stop transfer // DMA transfer complete - stop transfer
void dma1_channel3_isr(){ void dma1_channel3_isr(){
TIM3->SR = 0;
TIM3->CR1 |= TIM_CR1_OPM; // set one pulse mode to turn off timer after last CLK pulse TIM3->CR1 |= TIM_CR1_OPM; // set one pulse mode to turn off timer after last CLK pulse
DMA1_Channel3->CCR &= ~DMA_CCR_EN; // stop DMA DMA1_Channel3->CCR &= ~DMA_CCR_EN; // stop DMA
while(TIM3->CNT < 7); while(!(TIM3->SR & TIM_SR_UIF)); // wait for last pulse
SET(nOE); // clear main output //while(TIM3->CNT < 7);
SCRN_DISBL(); // clear main output
ADDR_port->ODR = (ADDR_port->ODR & ~(ADDR_pin)) | (blknum_curr << ADDR_roll); // set address ADDR_port->ODR = (ADDR_port->ODR & ~(ADDR_pin)) | (blknum_curr << ADDR_roll); // set address
SET(LAT); // activate latch SET(LAT); // activate latch
DMA1->IFCR = DMA_IFCR_CGIF3; DMA1->IFCR = DMA_IFCR_CGIF3;
transfer_done = 1; transfer_done = 1;
CLEAR(LAT); CLEAR(LAT);
CLEAR(nOE); // activate main output SCRN_ENBL(); // activate main output
//USB_send("transfer done\n"); //USB_send("transfer done\n");
} }

View File

@ -27,8 +27,10 @@
#include "stm32f1.h" #include "stm32f1.h"
#include "screen.h" #include "screen.h"
// define this if screen is negative // define this if screen colors are negative
// #define SCREEN_IS_NEGATIVE // #define SCREEN_IS_NEGATIVE
// define if nOE is negative
#define NOE_IS_NEGATIVE
// LED0 - PC13 (bluepill), blinking each second // LED0 - PC13 (bluepill), blinking each second
#define LED0_port GPIOC #define LED0_port GPIOC
@ -62,6 +64,15 @@
#define CLEAR(x) pin_clear(x ## _port, x ## _pin) #define CLEAR(x) pin_clear(x ## _port, x ## _pin)
#define TOGGLE(x) pin_toggle(x ## _port, x ## _pin) #define TOGGLE(x) pin_toggle(x ## _port, x ## _pin)
#ifdef NOE_IS_NEGATIVE
#define SCRN_ENBL() SET(nOE)
#define SCRN_DISBL() CLEAR(nOE)
#else
#define SCRN_ENBL() CLEAR(nOE)
#define SCRN_DISBL() SET(nOE)
#endif
void iwdg_setup();
void hw_setup(); void hw_setup();
void TIM_DMA_transfer(uint8_t blknum); void TIM_DMA_transfer(uint8_t blknum);
void stopTIMDMA(); void stopTIMDMA();

View File

@ -27,36 +27,13 @@
#include "usb_lib.h" #include "usb_lib.h"
volatile uint32_t Tms = 0; volatile uint32_t Tms = 0;
uint8_t countms = 0; uint8_t countms = 0, rainbow = 0;
/* Called when systick fires */ /* Called when systick fires */
void sys_tick_handler(void){ void sys_tick_handler(void){
++Tms; ++Tms;
} }
void iwdg_setup(){
uint32_t tmout = 16000000;
/* Enable the peripheral clock RTC */
/* (1) Enable the LSI (40kHz) */
/* (2) Wait while it is not ready */
RCC->CSR |= RCC_CSR_LSION; /* (1) */
while((RCC->CSR & RCC_CSR_LSIRDY) != RCC_CSR_LSIRDY){if(--tmout == 0) break;} /* (2) */
/* Configure IWDG */
/* (1) Activate IWDG (not needed if done in option bytes) */
/* (2) Enable write access to IWDG registers */
/* (3) Set prescaler by 64 (1.6ms for each tick) */
/* (4) Set reload value to have a rollover each 2s */
/* (5) Check if flags are reset */
/* (6) Refresh counter */
IWDG->KR = IWDG_START; /* (1) */
IWDG->KR = IWDG_WRITE_ACCESS; /* (2) */
IWDG->PR = IWDG_PR_PR_1; /* (3) */
IWDG->RLR = 1250; /* (4) */
tmout = 16000000;
while(IWDG->SR){if(--tmout == 0) break;} /* (5) */
IWDG->KR = IWDG_REFRESH; /* (6) */
}
#define USBBUFSZ (127) #define USBBUFSZ (127)
// usb getline // usb getline
static char *get_USB(){ static char *get_USB(){
@ -79,8 +56,17 @@ static char *get_USB(){
return NULL; return NULL;
} }
static void nxtrainbow(){
for(int i = 0; i < SCREEN_WIDTH; ++i){
for(int j = 0; j < SCREEN_HEIGHT; ++j){
DrawPix(i, j, rainbow + i);
}
}
if(++rainbow == 0) rainbow = 1;
}
int main(void){ int main(void){
uint32_t lastT = 0, mscnt = 0, Tmscnt = 0; uint32_t lastT = 0, mscnt = 0, Tmscnt = 0, lastR = 0;
sysreset(); sysreset();
StartHSE(); StartHSE();
SysTick_Config(72000); SysTick_Config(72000);
@ -89,7 +75,7 @@ int main(void){
hw_setup(); hw_setup();
USBPU_OFF(); USBPU_OFF();
USB_setup(); USB_setup();
PutStringAt(5, SCREEN_HEIGHT-1-curfont->baseline, "Test string"); PutStringAt(1, SCREEN_HEIGHT-1-curfont->baseline, "Test string");
iwdg_setup(); iwdg_setup();
USBPU_ON(); USBPU_ON();
@ -107,7 +93,7 @@ int main(void){
if(Tms - Tmscnt > 99){ if(Tms - Tmscnt > 99){
Tmscnt = Tms; Tmscnt = Tms;
ClearScreen(); ClearScreen();
PutStringAt(5, SCREEN_HEIGHT-1-curfont->baseline, u2str(++mscnt)); PutStringAt(5, curfont->height + 1, u2str(++mscnt));
ScreenON(); ScreenON();
} }
} }
@ -115,6 +101,10 @@ int main(void){
mscnt = 0; mscnt = 0;
Tmscnt = 0; Tmscnt = 0;
} }
if(rainbow && Tms - lastR > 99){
lastR = Tms;
nxtrainbow();
}
IWDG->KR = IWDG_REFRESH; IWDG->KR = IWDG_REFRESH;
process_screen(); process_screen();
usb_proc(); usb_proc();

View File

@ -21,7 +21,7 @@
#include "screen.h" #include "screen.h"
#include "usb.h" #include "usb.h"
extern uint8_t countms; extern uint8_t countms, rainbow;
char *omit_spaces(const char *buf){ char *omit_spaces(const char *buf){
while(*buf){ while(*buf){
@ -156,6 +156,7 @@ char *getnum(const char *txt, uint32_t *N){
const char* helpmsg = const char* helpmsg =
"'0/1' - screen off/on\n" "'0/1' - screen off/on\n"
"'2,3' - select font\n" "'2,3' - select font\n"
"'B' - start/stop rainBow\n"
"'C' - clear screen with given color\n" "'C' - clear screen with given color\n"
"'F' - set foreground color\n" "'F' - set foreground color\n"
"'f' - get FPS\n" "'f' - get FPS\n"
@ -178,12 +179,21 @@ const char *parse_cmd(const char *buf){
return "ON\n"; return "ON\n";
break; break;
case '2': case '2':
choose_font(FONT14); if(choose_font(FONT14)) return "Font14\n";
return "Font14\n"; return "err\n";
break; break;
case '3': case '3':
choose_font(FONT16); if(choose_font(FONT16)) return "Font16\n";
return "Font16\n"; return "err\n";
break;
case 'B':
if(rainbow){
rainbow = 0;
return "Stop rainbow\n";
}else{
rainbow = 1;
return "Start rainbow\n";
}
break; break;
case 'f': case 'f':
if(SCREEN_RELAX == getScreenState()) return "Screen is inactive\n"; if(SCREEN_RELAX == getScreenState()) return "Screen is inactive\n";
@ -233,7 +243,7 @@ const char *parse_cmd(const char *buf){
default: default:
ScreenOFF(); ScreenOFF();
ClearScreen(); ClearScreen();
PutStringAt(5, SCREEN_HEIGHT-1-curfont->baseline, buf); PutStringAt(1, curfont->height + 3, buf);
ScreenON(); ScreenON();
} }
return buf; return buf;

View File

@ -46,12 +46,20 @@ void setFGcolor(uint8_t c){fgColor = c;}
void ClearScreen(){ void ClearScreen(){
for(int i = 0; i < SCREENBUF_SZ; ++i) for(int i = 0; i < SCREENBUF_SZ; ++i)
screenbuf[i] = bgColor; screenbuf[i] = bgColor;
for(int i = 0; i < 32; ++i){ /*for(int i = 0; i < 32; ++i){
DrawPix(0,i,0b11111111); // white DrawPix(0,i,0b11111111);
DrawPix(27,i,0b11100000); // red DrawPix(1,i,0b1001010);
DrawPix(34,i,0b00011100); // green DrawPix(2,i,0b00100101);
DrawPix(63,i,0b00000011); // blue DrawPix(20,i,0b11100000);
} DrawPix(21,i,0b10000000);
DrawPix(22,i,0b00100000);
DrawPix(30,i,0b00011100);
DrawPix(31,i,0b00010000);
DrawPix(32,i,0b00000100);
DrawPix(60,i,0b00000011);
DrawPix(61,i,0b00000010);
DrawPix(62,i,0b00000001);
}*/
// memset -> halt // memset -> halt
//memset(screenbuf, pattern, SCREENBUF_SZ); //memset(screenbuf, pattern, SCREENBUF_SZ);
} }
@ -90,7 +98,7 @@ uint8_t DrawCharAt(int16_t X, int16_t Y, uint8_t Char){
// height and width of letter in pixels // height and width of letter in pixels
uint8_t h = curfont->height, w = *curchar++; // now curchar is pointer to bits array uint8_t h = curfont->height, w = *curchar++; // now curchar is pointer to bits array
uint8_t lw = curfont->bytes / h; // width of letter in bytes uint8_t lw = curfont->bytes / h; // width of letter in bytes
for(uint8_t row = 0; row <= h; ++row){ for(uint8_t row = 0; row < h; ++row){
for(uint8_t col = 0; col < w; ++col){ for(uint8_t col = 0; col < w; ++col){
if(curchar[row*lw + (col/8)] & (1 << (7 - (col%8)))) if(curchar[row*lw + (col/8)] & (1 << (7 - (col%8))))
DrawPix(X + col, Y + row, fgColor); DrawPix(X + col, Y + row, fgColor);
@ -167,7 +175,7 @@ void ScreenON(){
void ScreenOFF(){ void ScreenOFF(){
stopTIMDMA(); stopTIMDMA();
SET(nOE); SCRN_DISBL();
ScrnState = SCREEN_RELAX; ScrnState = SCREEN_RELAX;
currentB = 0; currentB = 0;
Ntick = 0; Ntick = 0;