
: 메인 칩 + 필요한 최소한의 회로
쪽보드라고도 한다
뒷면을 확인해 보면 메인 칩이 2개 있음
메인칩(TM74HC595) + 7세그먼트

메인칩 없이 7세그먼트를 다루려면 LED를 제어한 것처럼 하나당 한 개의 GPIO를 연결하여 제어해야한다
-> 7세그먼트 하나 당 GPIO 8개가 필요
LCD 드라이버(메인칩)과 7세그먼트와 연결하고 LCD 드라이버와 칩이 통신해서 사용하는 GPIO를 줄일 수 있다.
데이터시트 2개를 찾아야 한다
1. 메인칩 데이터시트
2. 모듈 자체에 대한 데이터시트(없는 경우가 많다)
동작 온도, 동작 전원, ...
SPI 통신 (다음시간에 공부하고 다룰예정이다)
SCLK : Input pin latch clock
RCLK
QA,QB,QC, .. : FND에 연결되어 있는 핀
데이터시트만 보고 동작시키기에는 너무 어려울 수 있다
샘플코드를 찾아서 동작시키면서 제어방법을 이해해 볼 예정이다


SPI 통신을 이용하는 방법도 있지만 오늘은 GPIO로 설정해서 해볼 예정이다


fnd_controller.c : c파일
fnd_controller.h : 헤더파일
#include "fnd_controller.h"
원본 파일이 c++ 이여서 수정이 필요함
원본 파일(c++)
void TM74HC595Display::send(unsigned char X)
{
for (int i = 8; i >= 1; i--)
{
if (X & 0x80)
{
digitalWrite(_DIO, HIGH);
}
else
{
digitalWrite(_DIO, LOW);
}
X <<= 1;
digitalWrite(_SCLK, LOW);
digitalWrite(_SCLK, HIGH);
}
}
수정내용
unsigned char -> uint8_t
digitalWrite(_DIO, HIGH) -> HAL_GPIO_WritePin(FND_DIO_GPIO_Port, FND_DIO_Pin, HIGH);
수정 후 적용
fnd_controller.c(c파일)
void send(uint8_t X){
for (int i = 8; i >= 1; i--)
{
if (X & 0x80)
{
HAL_GPIO_WritePin(FND_DIO_GPIO_Port, FND_DIO_Pin, HIGH);
}
else
{
HAL_GPIO_WritePin(FND_DIO_GPIO_Port, FND_DIO_Pin, LOW);
}
X <<= 1;
HAL_GPIO_WritePin(FND_SCLK_GPIO_Port, FND_SCLK_Pin , LOW);
HAL_GPIO_WritePin(FND_SCLK_GPIO_Port, FND_SCLK_Pin , HIGH);
}
}
보내고 싶은 8bit 데이터 X가 만약 0101 0010 이면
0x80 과 and 연산을 해서 1이 나오면 HIGH, 0이 나오면 LOW 보낸다
= 0x80 (1000 0000)
0101 0010 & 1000 0000 = 0000 0000 = 0
그 후 쉬프트 연산으로 왼쪽으로 1 미루고 다시 and 연산
1010 0100 & 1000 0000 = 1000 0000 = 128
원하는 데이터가 0101 0010 이면 LHLH LLHL 로 보내는 코드이다
SCLK 는 클럭을 만드는 것이다
LOW -> HIGH 로 올려주는 클럭을 만든다
기본적으로 HIGH를 유지하는 상태이다
원하는 데이터 세팅 후 클럭을 올림


FND에 적용해서 생각하면 만약에
0을 만들고 싶으면 A,B,C,D,E,F 만 켜지면 된다
LED ON : LOW
LED OFF : HIGH
DPGFE DCBA
1100 0000 : 0xC0
uint8_t _LED_0F[29];
void init_fnd(){
_LED_0F[0] = 0xC0; //0
_LED_0F[1] = 0xF9; //1
_LED_0F[2] = 0xA4; //2
_LED_0F[3] = 0xB0; //3
_LED_0F[4] = 0x99; //4
_LED_0F[5] = 0x92; //5
_LED_0F[6] = 0x82; //6
_LED_0F[7] = 0xF8; //7
_LED_0F[8] = 0x80; //8
_LED_0F[9] = 0x90; //9
_LED_0F[10] = 0x88; //A
_LED_0F[11] = 0x83; //b
_LED_0F[12] = 0xC6; //C
_LED_0F[13] = 0xA1; //d
_LED_0F[14] = 0x86; //E
_LED_0F[15] = 0x8E; //F
_LED_0F[16] = 0xC2; //G
_LED_0F[17] = 0x89; //H
_LED_0F[18] = 0xF9; //I
_LED_0F[19] = 0xF1; //J
_LED_0F[20] = 0xC3; //L
_LED_0F[21] = 0xA9; //n
_LED_0F[22] = 0xC0; //O
_LED_0F[23] = 0x8C; //P
_LED_0F[24] = 0x98; //q
_LED_0F[25] = 0x92; //S
_LED_0F[26] = 0xC1; //U
_LED_0F[27] = 0x91; //Y
_LED_0F[28] = 0xFE; //hight -
}
c에서는 함수 이름 중복이 되지 않아서 따로 이름을 변경해 줘야 함
-> 함수 이름을 변경하면 함수 적용한 부분도 인자 개수 확인해서 변경해줘야 한다
void send_port(uint8_t X, uint8_t port)
{
send(X);
send(port);
HAL_GPIO_WritePin(FND_RCLK_GPIO_Port, FND_RCLK_Pin , LOW);
HAL_GPIO_WritePin(FND_RCLK_GPIO_Port, FND_RCLK_Pin , HIGH);
}
void digit4_show(int n, int replay, uint8_t showZero)
{
int n1, n2, n3, n4;
n1 = (int) n % 10;
n2 = (int) ((n % 100)-n1)/10;
n3 = (int) ((n % 1000) - n2 - n1) / 100;
n4 = (int) ((n % 10000) - n3 - n2 - n1) / 1000;
for(int i = 0; i<=replay; i++){
send_port(_LED_0F[n1], 0b0001);
if(showZero | n>9)send_port(_LED_0F[n2], 0b0010);
if(showZero | n>99)send_port(_LED_0F[n3], 0b0100);
if(showZero | n>999)send_port(_LED_0F[n4], 0b1000);
}
}
void digit4_replay (int n, int replay)
{
digit4_show(n,replay,false);
}
void digit4(int n)
{
digit4_show(n,0,false);
}
void digit4showZero_replay(int n, int replay)
{
digit4_show(n, replay, true);
}
void digit4showZero(int n)
{
digit4_show(n, 0, true);
}
void digit2_replay(int n, int port, int replay)
{
int n1, n2;
n1 = (int) n % 10;
n2 = (int) ((n % 100)-n1)/10;
for(int i = 0; i<=replay; i++){
send_port(_LED_0F[n1], port);
send_port(_LED_0F[n2], port<<1);
}
}
void digit2(int n, int port)
{
digit2_replay(n, port, 0);
}
main.h 에 fnd port, pin 이 정의되어 있으므로
#include "main.h"
main.h 파일
#define FND_RCLK_Pin GPIO_PIN_13
#define FND_RCLK_GPIO_Port GPIOB
#define FND_DIO_Pin GPIO_PIN_14
#define FND_DIO_GPIO_Port GPIOB
#define FND_SCLK_Pin GPIO_PIN_15
#define FND_SCLK_GPIO_Port GPIOB
#define HIGH 1
#define LOW 0
#define false 0
#define true 1
void init_fnd();
void send(uint8_t X);
void send_port(uint8_t X, uint8_t port);
void digit4_show(int n, int replay, uint8_t showZero);
void digit4_replay (int n, int replay);
void digit4(int n);
void digit4showZero_replay(int n, int replay);
void digit4showZero(int n);
void digit2_replay(int n, int port, int replay);
void digit2(int n, int port);
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "fnd_controller.h"
/* USER CODE END Includes */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_USART1_UART_Init();
/* USER CODE BEGIN 2 */
init_fnd();
while (1)
{
for (int i = 0; i <= 99; i++) {
digit2_replay(i, 0b0001, 50); //send counter 0-99 with delay 50 cicles int 1st and 2nd view ports
}
}

for (int i = 0; i <= 100; i++) {
digit4showZero_replay(i, 50); //send counter 0-100 with delay 50 cicles with zero
}

for (int i = 0; i <= 9999; i++) {
digit4_replay(i, 50); //send counter 0-9999 with delay 50 cicles and hide zero
}
send_port(0x88, 0b0001);