/*****************************************************************************
 * Module    : ledseg
 * File      : led_7p7s.c
 * Author    : Hanny
 * Function  : led_7p7s数码管显示屏驱动
 *****************************************************************************/
#include "include.h"
#include "led_seg.h"

#if IS_LEDSEG_7PIN_DISPLAY

#include "led_7p7s.h"
extern __no_init u8 disp_buf[5];
__no_init u8 pin_disp_buf[7];
u8 led_seg_valid[7];
IAR_XDATA_A u8 COM_7P7S;

//有效位置1
IAR_CONST u8 tbl_ledseg_valid[7] = {
#if (THEME_SELECT == THEME_LEDSEG_7PIN)
    PIN1 | PIN2 | PIN3 | PIN4 | PIN5 | PIN6,
    PIN0 | PIN2 | PIN3 | PIN5 | PIN6,
    PIN0 | PIN1 | PIN3 | PIN4 | PIN5 | PIN6,
    PIN0 | PIN1 | PIN2 | PIN4 | PIN5 | PIN6,
    PIN0 | PIN1 | PIN2 | PIN3,
    PIN0 | PIN1 | PIN2 | PIN3,
    PIN0 | PIN1 | PIN2 | PIN3,
#else
    PIN1 | PIN2 | PIN3 | PIN4 | PIN5,
    PIN0 | PIN2 | PIN3 | PIN4 | PIN5,
    PIN0 | PIN1 | PIN3 | PIN4 | PIN5 | PIN6,
    PIN0 | PIN1 | PIN2 | PIN4 | PIN5,
    PIN0 | PIN1 | PIN2 | PIN3 | PIN5 | PIN6,
    PIN0 | PIN1 | PIN2 | PIN3 | PIN4 | PIN6,
    PIN2 | PIN4 | PIN5,
#endif
};

//led_7p7s初始化函数
#pragma location="DISP_LED_7P7S_SEG"
void led_7p7s_init(void)
{
    P2DIR |= 0x7f;                  //所有用到的引脚都设为输入
    P1DIR |= BIT(6);

    COM_7P7S = 0;

    my_memset((u8*)disp_buf,0x00,5);
    my_memset((u8 *)pin_disp_buf, 0x00, 7);
}

//根据7脚LED的真值表进行映射（每段输出高的IO记为COM端 7*7）COM:0~6  SEG:0~6
//#pragma location="DISP_LED_7P7S_SEG"
void led_7p7s_value_set(void)
{
    u8 ie0, ie1;
    bool ie_ea = IE_EA;
    IE_EA = 0;          //关总中断，保护好IE0/IE1后再打开
    ie0 = IE0;          //保存IE0
    ie1 = IE1;          //保存IE1
    IE0 = 0;            //关掉IE0
    IE1 &= BIT(6);      //关掉IE1，除了UART中断(因为这段处理较长，不能一直关IE_EA，否则会阻塞蓝牙UART中断)
    IE_EA = ie_ea;      //恢复总中断

    my_memset((u8 *)pin_disp_buf, 0x00, 7);

/*********** SEG ****************** COM ******** SEG(out)  *******/
#if (THEME_SELECT == THEME_LEDSEG_7PIN)

    if(disp_buf[0] & LED_BIT_A)     pin_disp_buf[1] |= PIN0; //设为1，扫描时对应此SEG位设为输出(FM)
    if(disp_buf[0] & LED_BIT_B)     pin_disp_buf[2] |= PIN0;
    if(disp_buf[0] & LED_BIT_C)     pin_disp_buf[3] |= PIN0;
    if(disp_buf[0] & LED_BIT_D)     pin_disp_buf[4] |= PIN0;
    if(disp_buf[0] & LED_BIT_E)     pin_disp_buf[5] |= PIN0;
    if(disp_buf[0] & LED_BIT_F)     pin_disp_buf[6] |= PIN0;
    if(disp_buf[0] & LED_BIT_G)     pin_disp_buf[2] |= PIN1;

    if(disp_buf[1] & LED_BIT_A)     pin_disp_buf[0] |= PIN1;
    if(disp_buf[1] & LED_BIT_B)     pin_disp_buf[0] |= PIN2;
    if(disp_buf[1] & LED_BIT_C)     pin_disp_buf[0] |= PIN3;
    if(disp_buf[1] & LED_BIT_D)     pin_disp_buf[0] |= PIN4;
    if(disp_buf[1] & LED_BIT_E)     pin_disp_buf[0] |= PIN5;
    if(disp_buf[1] & LED_BIT_F)     pin_disp_buf[0] |= PIN6;
    if(disp_buf[1] & LED_BIT_G)     pin_disp_buf[1] |= PIN2;

    if(disp_buf[2] & LED_BIT_A)     pin_disp_buf[3] |= PIN2;
    if(disp_buf[2] & LED_BIT_B)     pin_disp_buf[4] |= PIN2;
    if(disp_buf[2] & LED_BIT_C)     pin_disp_buf[5] |= PIN2;
    if(disp_buf[2] & LED_BIT_D)     pin_disp_buf[6] |= PIN2;
    if(disp_buf[2] & LED_BIT_E)     pin_disp_buf[4] |= PIN3;
    if(disp_buf[2] & LED_BIT_F)     pin_disp_buf[5] |= PIN3;
    if(disp_buf[2] & LED_BIT_G)     pin_disp_buf[6] |= PIN3;

    if(disp_buf[3] & LED_BIT_A)     pin_disp_buf[2] |= PIN3;
    if(disp_buf[3] & LED_BIT_B)     pin_disp_buf[2] |= PIN4;
    if(disp_buf[3] & LED_BIT_C)     pin_disp_buf[2] |= PIN5;
    if(disp_buf[3] & LED_BIT_D)     pin_disp_buf[2] |= PIN6;
    if(disp_buf[3] & LED_BIT_E)     pin_disp_buf[3] |= PIN4;
    if(disp_buf[3] & LED_BIT_F)     pin_disp_buf[3] |= PIN5;
    if(disp_buf[3] & LED_BIT_G)     pin_disp_buf[3] |= PIN6;
    if(disp_buf[4] & ICON_PLAY)     pin_disp_buf[3] |= PIN1;
    if(disp_buf[4] & ICON_PAUSE)    pin_disp_buf[4] |= PIN1;
    if(disp_buf[4] & ICON_USB)      pin_disp_buf[5] |= PIN1;
    if(disp_buf[4] & ICON_SD)       pin_disp_buf[6] |= PIN1;
    if(disp_buf[4] & ICON_DOT2)     pin_disp_buf[1] |= PIN3;
    if(disp_buf[4] & ICON_FM)       pin_disp_buf[1] |= PIN5;
    if(disp_buf[4] & ICON_MP3)      pin_disp_buf[1] |= PIN6;

#elif (THEME_SELECT == THEME_LEDSEG_7PIN_MHZ)

    if(disp_buf[0] & LED_BIT_A)     pin_disp_buf[0] |= PIN1; //设为1，扫描时对应此SEG位设为输出(MHZ)
    if(disp_buf[0] & LED_BIT_B)     pin_disp_buf[0] |= PIN2;
    if(disp_buf[0] & LED_BIT_C)     pin_disp_buf[3] |= PIN0;
    if(disp_buf[0] & LED_BIT_D)     pin_disp_buf[4] |= PIN0;
    if(disp_buf[0] & LED_BIT_E)     pin_disp_buf[0] |= PIN3;
    if(disp_buf[0] & LED_BIT_F)     pin_disp_buf[1] |= PIN0;
    if(disp_buf[0] & LED_BIT_G)     pin_disp_buf[2] |= PIN0;

    if(disp_buf[1] & LED_BIT_A)     pin_disp_buf[1] |= PIN2;
    if(disp_buf[1] & LED_BIT_B)     pin_disp_buf[1] |= PIN3;
    if(disp_buf[1] & LED_BIT_C)     pin_disp_buf[4] |= PIN1;
    if(disp_buf[1] & LED_BIT_D)     pin_disp_buf[1] |= PIN5;
    if(disp_buf[1] & LED_BIT_E)     pin_disp_buf[1] |= PIN4;
    if(disp_buf[1] & LED_BIT_F)     pin_disp_buf[2] |= PIN1;
    if(disp_buf[1] & LED_BIT_G)     pin_disp_buf[3] |= PIN1;

    if(disp_buf[2] & LED_BIT_A)     pin_disp_buf[4] |= PIN3;
    if(disp_buf[2] & LED_BIT_B)     pin_disp_buf[2] |= PIN4;
    if(disp_buf[2] & LED_BIT_C)     pin_disp_buf[3] |= PIN4;
    if(disp_buf[2] & LED_BIT_D)     pin_disp_buf[5] |= PIN0;
    if(disp_buf[2] & LED_BIT_E)     pin_disp_buf[5] |= PIN2;
    if(disp_buf[2] & LED_BIT_F)     pin_disp_buf[3] |= PIN2;
    if(disp_buf[2] & LED_BIT_G)     pin_disp_buf[4] |= PIN2;

    if(disp_buf[3] & LED_BIT_A)     pin_disp_buf[6] |= PIN5;
    if(disp_buf[3] & LED_BIT_B)     pin_disp_buf[5] |= PIN6;
    if(disp_buf[3] & LED_BIT_C)     pin_disp_buf[4] |= PIN5;
    if(disp_buf[3] & LED_BIT_D)     pin_disp_buf[5] |= PIN3;
    if(disp_buf[3] & LED_BIT_E)     pin_disp_buf[3] |= PIN5;
    if(disp_buf[3] & LED_BIT_F)     pin_disp_buf[5] |= PIN4;
    if(disp_buf[3] & LED_BIT_G)     pin_disp_buf[4] |= PIN6;

    if(disp_buf[4] & ICON_PLAY)     pin_disp_buf[0] |= PIN5;
    if(disp_buf[4] & ICON_PAUSE)    pin_disp_buf[2] |= PIN5;
    if(disp_buf[4] & ICON_USB)      pin_disp_buf[5] |= PIN1;
    if(disp_buf[4] & ICON_SD)       pin_disp_buf[0] |= PIN4;
    if(disp_buf[4] & ICON_DOT2)     pin_disp_buf[2] |= PIN3;
    if(disp_buf[4] & ICON_FM) {
        pin_disp_buf[2] |= PIN6;
        pin_disp_buf[6] |= PIN4;
    }
    if(disp_buf[4] & ICON_MP3)    pin_disp_buf[6] |= PIN2;
#endif

    IE0 = ie0;          //先恢复IE0，此时会关IE_EA
    IE1 = ie1;          //再恢复IE1
    IE_EA = ie_ea;      //恢复总中断
}


#if 0

//LED扫描函数(1COM 6 SEG 以COM为单位扫描)
#pragma location="DISP_LEDSEG_SCAN"
__near_func void led_7p7s_scan(void)
{
    u8 dis_seg = 0,dir_temp,out_temp,dir_temp2,out_temp2;//,dir_temp3,out_temp3;
    out_temp = P2 & 0x90;      //把所用到的脚全部置0 (并保存没用到的P2脚原来的电平)
    out_temp2 = P1 & 0xbf;
    dir_temp = P2DIR | 0x7f;   //把所用到的脚全部设为输入 (并保存没用到的P2脚原来的方向)
    dir_temp2 = P1DIR | 0x40;
    if(COM_7P7S > 6) {
        COM_7P7S = 0;
#if (LINEIN_DETECT_EN && LINEIN_SEG_REUSE)
        LINEIN_SEG_ENTER_DETECT();
        delay(20);  //SYSCLK_24M时,20约为20 uS
        linein_detect();
        LINEIN_SEG_EXIT_DETECT();
        return;
#endif
    }
    dis_seg = pin_disp_buf[COM_7P7S];
    dir_temp &= ~((dis_seg & 0x0f) | ((dis_seg & 0x30)<<1));  //把要显示的段设为输出 (前面已经把所有脚置0)
    dir_temp2 &= ~(dis_seg & 0x40);         //p16

    if(COM_7P7S == 0)
    {
        dir_temp2 &= ~BIT(6);
        out_temp2 |= BIT(6);
    }
    else if(COM_7P7S < 3)
    {
        dir_temp &= ~BIT(7-COM_7P7S);
        out_temp |= BIT(7-COM_7P7S);
    }
    else
    {
        dir_temp &= ~BIT(6-COM_7P7S);
        out_temp |= BIT(6-COM_7P7S);
    }
    P2 = out_temp;
    P2DIR = dir_temp;
    P1 = out_temp2;
    P1DIR = dir_temp2;

    COM_7P7S++;     //扫描下一COM
}

#else

//LED扫描函数(1COM 1 SEG 以SEG为单位扫描)
#pragma location="DISP_LEDSEG_SCAN"
__near_func void led_7p7s_scan(void)
{
    static u8 count = 0;
    u8 dis_seg = 0,dir_temp,out_temp,dir_temp2,out_temp2;//,dir_temp3,out_temp3;
    out_temp = P2 & 0x90;      //把所用到的脚全部置0 (并保存没用到的P2脚原来的电平)
    out_temp2 = P1 & 0xbf;
    dir_temp = P2DIR | 0x7f;   //把所用到的脚全部设为输入 (并保存没用到的P2脚原来的方向)
    dir_temp2 = P1DIR | 0x40;

    while (1) {
        if (count > 6) {
            count = 0;
            COM_7P7S++;
        }
        if(COM_7P7S > 6) {
            COM_7P7S = 0;
#if (LINEIN_DETECT_EN && LINEIN_SEG_REUSE)
            LINEIN_SEG_ENTER_DETECT();
#endif
#if (EAR_DETECT_EN && EAR_SEG_REUSE)
            EAR_SEG_ENTER_DETECT();
#endif			
            delay(20);  //SYSCLK_24M时,20约为20 uS
#if (LINEIN_DETECT_EN && LINEIN_SEG_REUSE)
            linein_detect();
#endif
#if (EAR_DETECT_EN && EAR_SEG_REUSE)
            earphone_detect();
#endif
#if (LINEIN_DETECT_EN && LINEIN_SEG_REUSE)
            LINEIN_SEG_EXIT_DETECT();
#endif
#if (EAR_DETECT_EN && EAR_SEG_REUSE)
            EAR_SEG_EXIT_DETECT();
#endif		
#if ((LINEIN_DETECT_EN && LINEIN_SEG_REUSE) || (EAR_DETECT_EN && EAR_SEG_REUSE))
            return;
#endif		
        }
        if (tbl_ledseg_valid[COM_7P7S] & BIT(count)) {         //节约CPU，只扫描有效的SEG段
            break;
        }
        count++;
    }

    dis_seg = pin_disp_buf[COM_7P7S] & BIT(count);

    dir_temp &= ~((dis_seg & 0x0f) | ((dis_seg & 0x30)<<1));  //把要显示的段设为输出 (前面已经把所有脚置0)
    dir_temp2 &= ~(dis_seg & 0x40);         //p16

    if(COM_7P7S == 0)
    {
        dir_temp2 &= ~BIT(6);
        out_temp2 |= BIT(6);
    }
    else if(COM_7P7S < 3)
    {
        dir_temp &= ~BIT(7-COM_7P7S);
        out_temp |= BIT(7-COM_7P7S);
    }
    else
    {
        dir_temp &= ~BIT(6-COM_7P7S);
        out_temp |= BIT(6-COM_7P7S);
    }
    P2 = out_temp;
    P2DIR = dir_temp;
    P1 = out_temp2;
    P1DIR = dir_temp2;

    count++;        //扫描下一SEG
}
#endif

#endif
