/**********************************************************************************************************
 * Copyright(C) 2017, Heilongjiang TYW Co.,Ltd.
 *
 * @Filename:     	Popup_Scheduler.c
 *
 * @Description:  	��������
 *
 * @Functions List:
 *
 *
 * @History:       	Version: 			V0.0.1
										Date:      		2018?1?29? 16?13?
                    Author: 			myliu
                    Modification: creat
 **********************************************************************************************************/

/**********************************************************************************************************
 * Include
*/
#include "include.h"
#include "Popup_Lib.h"   
#include "Popup_List.h"
//#include "Sound_List.h"
//#include "DisplaySch.h"
//#include "Common_Interface.h"
#include "Popup_Message_List.h"
#include "Popup_Scheduler.h"
//#include "Sound_Scheduler.h"

/**********************************************************************************************************
 * Constants and defines
 */
#define MAX_MEM_NUM				64u      /*512bytes*/

/**********************************************************************************************************
 * Local variables
 */
static CommMemBuf_t CommBuf[MAX_MEM_NUM];
static struct PopupList *FatalListHead = POPUPLIB_NULL;
static struct PopupList *HintListHead = POPUPLIB_NULL;
static struct PopupList *WarningListHead = POPUPLIB_NULL;
static struct PopupList *ExceptionListHead = POPUPLIB_NULL;
static PopupSchedulingStruct s_PopupScheduling;
PopupList_Opt_t PopupListOpt = {0};

/**********************************************************************************************************
 * Local functions
 */
static struct PopupList *Popup_Polling_Next ( struct PopupList *CurPopup );
static void Popup_Update_Status ( uint16_t PopupID );
static void Popup_Fatal_Request ( uint16_t PopupID );
static void Popup_Hint_Request ( uint16_t PopupID );
static void Popup_Warning_Request ( uint16_t PopupID );
static void Popup_Exception_Request ( uint16_t PopupID );
static struct PopupList *Popup_Select ( uint16_t PopupID );
static void Popup_Delete_Request ( uint16_t PopupID );
static void Popup_Cal_CutGrade ( uint16_t NewPopupID );
static void Popup_Cal_CutGrade_loc ( uint16_t NewPopupID );
static uint8_t Popup_Compare_Priority ( uint16_t PopupID1, uint16_t PopupID2 );
static uint16_t Popup_Get_Last_Masked_Warning ( void );
static uint16_t Popup_Get_Previous_Masked_Warning ( uint16_t PopupID );
static uint16_t Popup_Get_Next_Masked_Warning ( uint16_t PopupID );
static void Popup_IRQ_Enable(void);
static void Popup_IRQ_Disable(void);

/**********************************************************************************************************
 * Global variables
 */

/**********************************************************************************************************
 * Global functions
 */
/**********************************************************************************************************
 *@Function:  		Popup_Scheduler_Init
 *@Description: 	��ʼ��������Ϣ������
 *@Input:			MY_MemInit / CommMemInit
 *@Output:			none.
 *@Calls:  			none.
 *@Return:  		none.
 *@Note:    		�����ڴ����������Ҫ�������Ӳ����ʼ��֮��Ӧ�ÿ�ʼ֮ǰ�����г�ʼ����������ֻ���ϵ��ʼ��һ��
 **********************************************************************************************************/
void Popup_Scheduler_Init ( void )
{
    
    
    PopupListOpt.CommMemBuf = CommBuf;
    PopupListOpt.MaxCommMenSize = MAX_MEM_NUM;
    PopupListOpt.pPopupAttributeTable = PopupAttributeTable;
    PopupListOpt.IRQ_Disable = Popup_IRQ_Disable;
    PopupListOpt.IRQ_Enable = Popup_IRQ_Enable;
    PopupList_Init(&PopupListOpt);    
    /*��ʼ������ֵ*/
    s_PopupScheduling.Timer 	   = 0u;
    s_PopupScheduling.NewPopupID   = POPUP_NONE;
    s_PopupScheduling.CurPopupID   = POPUP_NONE;
    s_PopupScheduling.PollPopupID  = POPUP_NONE;
    s_PopupScheduling.CurStatus    = POPUP_STATUS_OFF;
    s_PopupScheduling.CutGrade     = POPUP_CUT_NOT;
    s_PopupScheduling.SndReqCode   = 1u;
    s_PopupScheduling.CurMaskedID  = POPUP_NONE;
    s_PopupScheduling.WarningExist = FALSE;
}

/**********************************************************************************************************
 *@Function:  		Popup_Scheduler_OFF
 *@Description: 	PopupList_Destroy
 *@Input:			MY_MemInit / CommMemInit
 *@Output:			none.
 *@Calls:  			none.
 *@Return:  		none.
 *@Note:    		��������״̬��ʱ��Ҫ�رյ�������������д�������Ϣ
 **********************************************************************************************************/
void Popup_Scheduler_OFF ( void )
{
    uint8_t i = 0u;

    /*1��ɾ��ȫ����Ҫ����Ϣ*/
    /*FatalListHead = PopupList_Destroy ( FatalListHead );*/
    /*2��ɾ��ȫ����ʾ����Ϣ*/
    /*HintListHead = PopupList_Destroy ( HintListHead );*/
    /*3��ɾ��ȫ����������Ϣ*/
    /*WarningListHead = PopupList_Destroy ( WarningListHead );*/
    /*4��ɾ��ȫ����������Ϣ*/
    /*ExceptionListHead = PopupList_Destroy ( ExceptionListHead );*/

    /*5����ʼ������ֵ*/
    /*s_PopupScheduling.Timer 	   = 0u;
    s_PopupScheduling.NewPopupID   = POPUP_NONE;
    s_PopupScheduling.CurPopupID   = POPUP_NONE;
    s_PopupScheduling.PollPopupID  = POPUP_NONE;
    s_PopupScheduling.CurStatus    = POPUP_STATUS_OFF;
    s_PopupScheduling.CutGrade     = POPUP_CUT_NOT;
    s_PopupScheduling.SndReqCode   = 1u;
    s_PopupScheduling.CurMaskedID  = POPUP_NONE;
    s_PopupScheduling.WarningExist = FALSE;*/

    Popup_Del_Masked_Request();
}

/**********************************************************************************************************
 *@Function:  		Popup_Scheduling_Service
 *@Description:   ���ȵ�����Ϣ�����µ�ǰ��ʾ����Ϣ����,�ӿں���
 *					      ���ܷ����л���������
 *					      1����ǰ��ʾ��Ϣ��ɾ��/����
 *					      2���������ȼ��ߵ�����Ϣ
 *					      3����ʾʱ�䵽
 *@Input:			    CommMemInit
 *@Output:			  none.
 *@Calls:  			  none
 *@Return:  		  none
 *@Note:    		  �÷���������ÿ100ms������һ��
 **********************************************************************************************************/
void Popup_Scheduling_Service ( void )
{
    struct PopupList *CurPopup = POPUPLIB_NULL;
    struct PopupList *NextPopup = POPUPLIB_NULL;
    uint8_t IsReturn = 0u;
    struct PopupList *p1 = POPUPLIB_NULL;

    /*2����ǰ����ʾ����������Ϣ��ֱ�ӷ���,������ʾʱ���ۼ�*/
    if ( s_PopupScheduling.CurPopupID >= POPUP_MAX )
    {
        if ( s_PopupScheduling.NewPopupID < POPUP_MAX )
        {
            s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
        }
        else
        {
            return;
        }
    }
    else
    {
        CurPopup = Popup_Select ( s_PopupScheduling.CurPopupID );
        if ( s_PopupScheduling.Timer < 0xFFFEu )
        {
            s_PopupScheduling.Timer++;

            if ( CurPopup != POPUPLIB_NULL )
            {
                if ( CurPopup->Timer < 0xFFFE )
                {
                    CurPopup->Timer++;
                }
            }
            else
            {
                s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
            }
        }
    }

    /*3�������л��ȼ�������Ӧ�Ĵ���*/
    switch ( s_PopupScheduling.CutGrade )
    {
        case POPUP_CUT_IMMEDIATELY:
            break;

        case POPUP_CUT_WAIT_TIME_MIN:
#if POPUP_DEFINE_FIRST_DISPLAY
            if ( s_PopupScheduling.CurStatus == POPUP_STATUS_FIRST )
            {
                if ( s_PopupScheduling.Timer < POPUP_DISP_TIME_MIN )
                {
                    IsReturn = 1u;
                }
            }
#else
            if ( s_PopupScheduling.Timer < PopupAttributeTable[s_PopupScheduling.CurPopupID].MinDispTime )
            {
                IsReturn = 1u;
            }   
#endif
            break;

        case POPUP_CUT_WAIT_TIME_NORMAL:
#if POPUP_DEFINE_FIRST_DISPLAY
            if ( s_PopupScheduling.CurStatus == POPUP_STATUS_FIRST )
            {
                if ( s_PopupScheduling.Timer < POPUP_DISP_TIME_NORMAL )
                {
                    IsReturn = 1u;
                }
                s_PopupScheduling.NewPopupID = POPUP_NONE;
            }
#else
        /*    if ( s_PopupScheduling.Timer < POPUP_DISP_TIME_MIN )
            {
                IsReturn = 1u;
            }   */
            if(s_PopupScheduling.Timer < PopupAttributeTable[s_PopupScheduling.CurPopupID].MaxDispTime )
            {
            	IsReturn = 1u;	
            }

#endif
            break;

        case POPUP_CUT_NOT:
          /*  if ( s_PopupScheduling.Timer < POPUP_DISP_TIME_NORMAL )
            {
                IsReturn = 1u;
            }   */
            if(s_PopupScheduling.Timer < PopupAttributeTable[s_PopupScheduling.CurPopupID].MaxDispTime )
            {
            	IsReturn = 1u;	
            }
            break;

        default:
            break;
    }

    if(IsReturn == 0u)
    {
     	// if ( CurPopup != POPUPLIB_NULL )
     	// {
     	// 	CurPopup -> Timer =  s_PopupScheduling.Timer;
     	// }
        /*4 ����л��ȼ�*/
        s_PopupScheduling.CutGrade = POPUP_CUT_NOT;

        /*5 �л�������Ϣ*/
         if ( s_PopupScheduling.NewPopupID < POPUP_MAX )
         {
             NextPopup = Popup_Select ( s_PopupScheduling.NewPopupID );
             if ( NextPopup == POPUPLIB_NULL )
             {
                 NextPopup = Popup_Polling_Next ( CurPopup );
             }
             s_PopupScheduling.NewPopupID = POPUP_NONE;
             s_PopupScheduling.Timer = 0u;
         }
         else
        {
            NextPopup = Popup_Polling_Next ( CurPopup );
        }

        /*6�����µ�ǰ��ʾ����Ϣ*/
        if ( NextPopup != POPUPLIB_NULL )
        {
            if ( NextPopup->PopupID != s_PopupScheduling.CurPopupID )
            {
                if ( s_PopupScheduling.CurPopupID >= POPUP_MAX )
                {
                    s_PopupScheduling.Timer = 0u;
                }
                else
                {
                    if ( PopupAttributeTable [ NextPopup->PopupID ].Class != PopupAttributeTable [ s_PopupScheduling.CurPopupID ].Class )
                    {
                        s_PopupScheduling.Timer = 0u;
                    }
                }
                s_PopupScheduling.CurStatus  = NextPopup->Status;
                s_PopupScheduling.CurPopupID = NextPopup->PopupID;
            }
        }
        else
        {
            s_PopupScheduling.CurPopupID = POPUP_NONE;
            s_PopupScheduling.Timer = 0u;
        }

        /*7. ������һ��������״̬*/
        if ( CurPopup != POPUPLIB_NULL )
        {
            Popup_Update_Status ( CurPopup->PopupID );
        }
    }
    
    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Request
 *@Description:   	��Ϣ�������󣬰���ȫ�����ͣ��ӿں���
 *@Input:			uint8_t PopupID -- ������Ϣ��ID.
 *@Output:			none.
 *@Calls:  			none.
 *@Return:  		none.
 *@Note:    		none.
 **********************************************************************************************************/
void Popup_Request ( uint16_t PopupID )
{
    switch ( PopupAttributeTable[PopupID].Type )
    {
        case POPUP_TYPE_FATAL:
            Popup_Fatal_Request ( PopupID );
            break;

        case POPUP_TYPE_HINT:
            Popup_Hint_Request ( PopupID );
            break;

        case POPUP_TYPE_WARNING:
            Popup_Warning_Request ( PopupID );
            break;

        case POPUP_TYPE_EXCEPTION:
            Popup_Exception_Request ( PopupID );
            break;

        default:
            break;
    }

    return;
}

/**********************************************************************************************************
 *@Function:  	Popup_Mask_Request
 *@Description: ���ε����ࣨ�����ࣩ��Ϣ��ֻ����ʾ���Ĳſ��Ա�����
 *              ***********����ȫ����ʾ����***************
 *@Input:		none.
 *@Output:		none.
 *@Calls:  		none.
 *@Return:  	none.
 *@Note:    	none.
 **********************************************************************************************************/
void Popup_Mask_Request ( void )
{
    uint8_t i = 0;
    uint8_t PopupClass = 0u;
    struct PopupList *p1 = POPUPLIB_NULL;

    if ( PopupAttributeTable[s_PopupScheduling.CurPopupID].Type == POPUP_TYPE_WARNING )
    {
        s_PopupScheduling.CurMaskedID = s_PopupScheduling.CurPopupID;
        
        PopupClass = PopupAttributeTable[s_PopupScheduling.CurPopupID].Class;
        if(PopupAttributeTable[PopupClass].pMbrList != NULL)
        {
            for(i=0; i < PopupAttributeTable[PopupClass].MbrCnt; i++)
            {
                p1 = Popup_Select(PopupAttributeTable[PopupClass].pMbrList[i]);
                if(p1 != POPUPLIB_NULL)
                {
                    p1->Status = POPUP_STATUS_MASKED;
                    s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;                    
                }
            }
        }
        else
        {
            p1 = Popup_Select(s_PopupScheduling.CurPopupID);
            if(p1 != POPUPLIB_NULL)
            {
                p1->Status = POPUP_STATUS_MASKED;
                s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
            }
        }
        /*p1 = WarningListHead;
        while ( p1 != POPUPLIB_NULL )
        {
            if ( p1->Status == POPUP_STATUS_LOOP )
            {
                p1->Status = POPUP_STATUS_MASKED;
            }
            p1 = p1->next;
        }*/
    }

    return;
}

uint8_t Popup_WarningRequested ( void );
uint8_t Popup_WarningRequested ( void )
{
    struct PopupList *p1 = POPUPLIB_NULL;
    uint8_t retVal = 0u;

    p1 = FatalListHead;
    if ( p1 == POPUPLIB_NULL )
    {
        p1 = HintListHead;
        while ( p1 != POPUPLIB_NULL )
        {
            if ( ( p1->Status == POPUP_STATUS_NEW ) || ( p1->Status == POPUP_STATUS_FIRST ) || ( p1->Status == POPUP_STATUS_LOOP ) )
            {
                retVal = 1u;
            }
            p1 = p1->next;
        }

        p1 = WarningListHead;
        while ( p1 != POPUPLIB_NULL )
        {
            if ( ( p1->Status == POPUP_STATUS_NEW ) || ( p1->Status == POPUP_STATUS_FIRST ) || ( p1->Status == POPUP_STATUS_LOOP ) )
            {
                retVal = 1u;
            }
            p1 = p1->next;
        }
    }
    else
    {
        retVal = 1u;
    }

    return retVal;
}

/**********************************************************************************************************
 *@Function:  	Popup_Del_Masked_Request
 *@Description: ��IGN_OFFʱ����Ҫ�����ι��ı�����Ϣ��ʾ���������������ٴ���ʾ��������
 *@Input:		none.
 *@Output:		none.
 *@Calls:  		none.
 *@Return:  	none.
 *@Note:    	Ŀǰ��������Ϣ��״̬�л�Ϊѭ����ʾ״̬.
 **********************************************************************************************************/
void Popup_Del_Masked_Request ( void )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = WarningListHead;
    while ( p1 != POPUPLIB_NULL )
    {
        if ( p1->Status == POPUP_STATUS_MASKED )
        {
            //p1->Status = POPUP_STATUS_LOOP;
            p1->Status = POPUP_STATUS_FIRST;
            Popup_Cal_CutGrade ( p1->PopupID );
        }
        p1 = p1->next;
    }
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Status
 *@Description:   ��ȡ��ѯ��Ϣ��״̬
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  none.
 *@Calls:  			  PopupList_Select
 *@Return:  		  POPUP_STATUS_OFF -- ����Ϣ������Ҫ��ʾ
 *                POPUP_STATUS_FIRST -- ����Ϣ��һ����ʾ
 *                POPUP_STATUS_LOOP -- ����Ϣ������ѯ��ʾ��
 *                POPUP_STATUS_MASKED -- ����Ϣ������
 *                POPUP_STATUS_DELETE -- ����Ϣ�ȴ���ɾ��
 *                POPUP_STATUS_CLEAR -- ����Ϣ���ϱ�ɾ��
 *@Note:    		  none.
 **********************************************************************************************************/
uint8_t Popup_Get_Status ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;
    uint8_t retStatus = POPUP_STATUS_OFF;

    switch ( PopupAttributeTable[PopupID].Type )
    {
        case POPUP_TYPE_FATAL:
            p1 = PopupList_Select ( FatalListHead, &PopupID );
            break;

        case POPUP_TYPE_HINT:
            p1 = PopupList_Select ( HintListHead, &PopupID );
            break;

        case POPUP_TYPE_WARNING:
            p1 = PopupList_Select ( WarningListHead, &PopupID );
            break;

        case POPUP_TYPE_EXCEPTION:
            p1 = PopupList_Select ( ExceptionListHead, &PopupID );
            break;

        default:
            break;
    }

    if ( p1 != POPUPLIB_NULL )
    {
        retStatus = p1->Status;
    }

    return retStatus;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Current_Message
 *@Description:   ��ȡ��ǰ��Ϣ�����ֱ��
 *@Input:			    none.
 *@Output:			  none.
 *@Calls:  			  none.
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
uint16_t Popup_Get_Current_Message ( void )
{
    uint16_t retPopupMsgID = POPUP_MSG_NONE;

    if ( s_PopupScheduling.CurPopupID < POPUP_MAX )
    {
        retPopupMsgID = PopupAttributeTable[s_PopupScheduling.CurPopupID].Message;
    }

    return retPopupMsgID;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Current_Sound
 *@Description:   ��ȡ��ǰ��Ϣ���������
 *@Input:			    none.
 *@Output:			  none.
 *@Calls:  			  none.
 *@Return:  		  none.
 *@Note:    		  ����������Ӱ�������ĳ����Լ��Ƿ���
 **********************************************************************************************************/
static uint8_t Popup_Get_Current_Sound1 ( void )
{
/*    uint8_t retSndID = SND_NONE;

    if ( s_PopupScheduling.CurPopupID < POPUP_MAX )
    {
        retSndID = PopupAttributeTable[s_PopupScheduling.CurPopupID].Snd;
    }
    
    return retSndID;
    */
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Current_Sound_Req_Code
 *@Description:   ��ȡ��ǰ��Ϣ������������
 *@Input:			    none.
 *@Output:			  none.
 *@Calls:  			  none.
 *@Return:  		  none.
 *@Note:    		  ����������Ӱ�������ĳ����Լ��Ƿ���
 **********************************************************************************************************/
uint8_t Popup_Get_Current_Sound_Req_Code ( void )
{
   /* struct PopupList *p1 = POPUPLIB_NULL;
    uint8_t retReqCode = 0u;

    if ( s_PopupScheduling.CurPopupID < POPUP_MAX )
    {
        if ( PopupAttributeTable[s_PopupScheduling.CurPopupID].SndMode == POPUP_MODE_MULTI )
        {
            if ( s_PopupScheduling.SndReqCode == 0xFFu )
            {
                s_PopupScheduling.SndReqCode = 0x01u;
            }
            else
            {
                s_PopupScheduling.SndReqCode++;
            }
            retReqCode = s_PopupScheduling.SndReqCode;
        }
        else
        {
            p1 = Popup_Select ( s_PopupScheduling.CurPopupID );
            if ( p1 != POPUPLIB_NULL )
            {
                if ( p1->Status == POPUP_STATUS_FIRST )
                {
                    retReqCode = s_PopupScheduling.SndReqCode;
                }
            }
        }
    }

    return retReqCode;
    */
}

/**********************************************************************************************************
 *@Function:  		Popup_Delete
 *@Description:   �����ǰ��ʾ��Ϣ������ǵ�һ����ʾ��Ҫ�ȴ�Tmin���ڶ�����Ϣ����ʾ�ࣩ���⣩
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  FatalListHead/HintListHead/WarningListHead/ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Delete
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
void Popup_Delete ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = Popup_Select ( PopupID );
    if ( p1 != POPUPLIB_NULL )
    {   
	    //Sound_Delete(PopupAttributeTable[PopupID].Snd); 
        if ( p1->PopupID == s_PopupScheduling.CurPopupID )
        {
            p1->Status = POPUP_STATUS_DELETE;
            if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_HINT )
            {
                s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
            }
            else
            {
                s_PopupScheduling.CutGrade = POPUP_CUT_WAIT_TIME_MIN;
            }
        }
        else
        {
            Popup_Delete_Request ( PopupID );  
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Clear
 *@Description:   �����ǰ��ʾ��Ϣ������Ҫ�ȴ�Tmin
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  FatalListHead/HintListHead/WarningListHead/ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Delete
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
void Popup_Clear ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = Popup_Select ( PopupID );
    if ( p1 != POPUPLIB_NULL )
    {
      //Sound_Delete(PopupAttributeTable[PopupID].Snd);   
	  if ( p1->PopupID == s_PopupScheduling.CurPopupID )
        {
            p1->Status = POPUP_STATUS_CLEAR;
            s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
        }
        else
        {
            Popup_Delete_Request ( PopupID );
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Warning_Status
 *@Description:   ��ѯ�Ƿ���ڱ�������Ϣ/�����ǻ�ȡ��ʾ������Ϣ�£��Ƿ���ڱ�������Ϣ
 *@Input:			    none
 *@Output:			  none
 *@Calls:  			  none
 *@Return:  		  TRUE --���ڱ�������Ϣ
 *                FALSE -- �����ڱ�������Ϣ
 *@Note:    		  none.
 **********************************************************************************************************/
uint8_t Popup_Get_Warning_Status ( void )
{
    uint8_t retVal = 0u;

    if ( WarningListHead != POPUPLIB_NULL )
    {
        retVal = 1u;
    }

    return retVal;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Masked_Warning_Msg
 *@Description:   ��ȡ��ǰ��ʾ��������Ϣ������/ͼƬ���
 *@Input:			    none
 *@Output:			  none
 *@Calls:  			  none
 *@Return:  		  ����/ͼƬ���
 *@Note:    		  none.
 **********************************************************************************************************/
uint16_t Popup_Get_Masked_Warning_Msg ( void )
{
    uint16_t retMaskedID = POPUP_MSG_NONE;

    if ( s_PopupScheduling.CurMaskedID < POPUP_MAX )
    {
        retMaskedID = s_PopupScheduling.CurMaskedID;
    }
    return retMaskedID;
}

/**********************************************************************************************************
 *@Function:  		Popup_Masked_Warning_Polling_Reset
 *@Description:   ��λ������Ϣ��ǰ��ʾ��ָ�룬��ǰ����ָ�����һ���������ָ���һ��
 *@Input:			    none.
 *@Output:			  none.
 *@Calls:  			  none.
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
void Popup_Masked_Warning_Polling_Reset ( uint8_t Mode )
{
    uint16_t PopupID;

    if ( Mode == POPUP_POLLING_FORWARD )
    {
        PopupID = Popup_Get_First_Masked_Warning();
    }
    else
    {
        PopupID = Popup_Get_Last_Masked_Warning();
    }

    s_PopupScheduling.CurMaskedID = PopupID;

    return;
}

/**********************************************************************************************************
��������Popup_Masked_Warning_Polling
��  �ܣ���ѯ�����εı���

        ÿ����һ�δ˺���,�����α���ָ��ᰴָ�������ƶ�һλ,��ָ������ָ������
        �ϵ����һ��������Ϣʱ,�ٴ���ͬһ�����ѯ,��ǰ�������α�����Ϣ���Ϊ
        POPUP_NONE ��ʾ������ѯ�ѽ���

        ����:��ǰ�������α��� A��B��C��D,����Popup_Masked_Warning_Polling_Reset
        ����,�趨����Ϊ POPUP_POLLING_FORWARD ʱ,�����α���ָ���ָ�򱨾�A,����,
        ���øú����趨����Ϊ POPUP_POLLING_FORWARD ʱ�����α���ָ�뼴ָ�򱨾�B.
        �ظ����ô˺����ҷ��򲻱��������α���ָ��ָ�򱨾�D��,������ͬ������ô˺�
        ���򷵻� POPUP_NONE,��ʾ��ѯ�ѽ���

        ͨ������Popup_Get_Masked_Warning�ɶ�����ǰ�����α���ָ��ָ��ı���

��  ����Mode����ѯģʽ POPUP_POLLING_FORWARD - �������ģʽ
                       POPUP_POLLING_REVERSE - �������ģʽ
����ֵ����
 **********************************************************************************************************/
void Popup_Masked_Warning_Polling ( uint8_t Mode )
{
    uint16_t PopupEnd;
    uint16_t PopupID;

    PopupID  = s_PopupScheduling.CurMaskedID;

    if ( PopupID != POPUP_NONE )
    {
        if ( Mode == POPUP_POLLING_FORWARD )
        {
            PopupEnd = Popup_Get_Last_Masked_Warning();
            if ( PopupEnd != POPUP_NONE )
            {
                if ( PopupID == PopupEnd )
                {
                    s_PopupScheduling.CurMaskedID = POPUP_NONE;
                }
                else
                {
                    s_PopupScheduling.CurMaskedID = Popup_Get_Next_Masked_Warning ( PopupID );
                }
            }
        }
        else
        {
            PopupEnd = Popup_Get_First_Masked_Warning();
            if ( PopupEnd != POPUP_NONE )
            {
                if ( PopupID == PopupEnd )
                {
                    s_PopupScheduling.CurMaskedID = POPUP_NONE;
                }
                else
                {
                    s_PopupScheduling.CurMaskedID = Popup_Get_Previous_Masked_Warning ( PopupID );
                }
            }
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Update_Status
 *@Description:   ����ָ��������Ϣ��״̬
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  none
 *@Calls:  			  PopupList_Select / PopupList_Delete
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static void Popup_Update_Status ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    /*1���������ͣ�����IDλ��*/
    p1 = Popup_Select ( PopupID );
    if ( p1 != POPUPLIB_NULL )
    {
        if ( ( p1->Status == POPUP_STATUS_CLEAR ) || ( p1->Status == POPUP_STATUS_DELETE ) )
        {
            Popup_Delete_Request ( p1->PopupID );
        }
        else if ( p1->Status != POPUP_STATUS_MASKED )
        {
            if ( PopupAttributeTable[p1->PopupID].DispMode == POPUP_MODE_SINGLE )
            {
                if(p1 ->Timer >= PopupAttributeTable[p1->PopupID].MaxDispTime)
                {
                    if( PopupAttributeTable[PopupID].Type == POPUP_TYPE_WARNING )
                    {
                        p1->Status = POPUP_STATUS_MASKED;	
                    }
                    else
                    {
                        p1->Status = POPUP_STATUS_OFF;	
                    }
                }
            }
            else
            {
                p1->Status = POPUP_STATUS_LOOP;
            }
        }
        else
        {

        }
    }
}

/**********************************************************************************************************
 *@Function:  		Popup_Polling_Next
 *@Description:   �л���ѯ���¸���ʾ
 *@Input:			    none
 *@Output:			  none
 *@Calls:  			  PopupList_Select / PopupList_Malloc / PopupList_Insert / Popup_Cal_CutGrade
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static struct PopupList *Popup_Polling_Next ( struct PopupList *CurPopup )
{
    struct PopupList *NextPopup = POPUPLIB_NULL;

    if ( CurPopup != POPUPLIB_NULL )
    {
        NextPopup = CurPopup->next;

#if POPUP_DEFINE_FIRST_DISPLAY
        while ( NextPopup != POPUPLIB_NULL )
        {
            if ( NextPopup->Status == POPUP_STATUS_FIRST )
            {
                break;
            }
            NextPopup = NextPopup->next;
        }
#endif
        while ( NextPopup != POPUPLIB_NULL )
        {
            if ( ( NextPopup->Status == POPUP_STATUS_LOOP ) || ( NextPopup->Status == POPUP_STATUS_FIRST ) )
            {
                break;
            }
            NextPopup = NextPopup->next;
        }
    }

    if ( NextPopup == POPUPLIB_NULL )
    {
        if ( FatalListHead != POPUPLIB_NULL )
        {
            NextPopup = FatalListHead;
            while ( NextPopup != POPUPLIB_NULL )
            {
                if ( ( NextPopup->Status == POPUP_STATUS_FIRST ) || ( NextPopup->Status == POPUP_STATUS_LOOP ) )
                {
                    break;
                }
                NextPopup = NextPopup->next;
            }
        }

        if ( ( HintListHead != POPUPLIB_NULL ) && ( NextPopup == POPUPLIB_NULL ) )
        {
            NextPopup = HintListHead;
            while ( NextPopup != POPUPLIB_NULL )
            {
                if ( ( NextPopup->Status == POPUP_STATUS_FIRST ) || ( NextPopup->Status == POPUP_STATUS_LOOP ) )
                {
                    break;
                }
                NextPopup = NextPopup->next;
            }
        }

        if ( ( WarningListHead != POPUPLIB_NULL ) && ( NextPopup == POPUPLIB_NULL ) )
        {
#if POPUP_CUT_RECOVER
            if ( s_PopupScheduling.PollPopupID < POPUP_MAX )
            {
                NextPopup = PopupList_Select ( WarningListHead, &s_PopupScheduling.PollPopupID );
                s_PopupScheduling.PollPopupID = POPUP_NONE;
            }
#endif
            if ( NextPopup == POPUPLIB_NULL )
            {
                NextPopup = WarningListHead;
                while ( NextPopup != POPUPLIB_NULL )
                {
                    if ( ( NextPopup->Status == POPUP_STATUS_FIRST ) || ( NextPopup->Status == POPUP_STATUS_LOOP ) )
                    {
                        break;
                    }
                    NextPopup = NextPopup->next;
                }
            }
        }

        if ( ( ExceptionListHead != POPUPLIB_NULL ) && ( NextPopup == POPUPLIB_NULL ) )
        {
            NextPopup = ExceptionListHead;
            while ( NextPopup != POPUPLIB_NULL )
            {
                if ( ( NextPopup->Status == POPUP_STATUS_FIRST ) || ( NextPopup->Status == POPUP_STATUS_LOOP ) )
                {
                    break;
                }
                NextPopup = NextPopup->next;
            }
        }
    }

    return NextPopup;
}

/**********************************************************************************************************
 *@Function:  		Popup_Fatal_Request
 *@Description:   �����һ����Ϣ����ȷ�����л��ȼ�
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Malloc / PopupList_Insert / Popup_Cal_CutGrade
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static void Popup_Fatal_Request ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = PopupList_Select ( FatalListHead, &PopupID );
    if ( p1 == POPUPLIB_NULL )
    {
        p1 = HintListHead;
        //while ( p1 != POPUPLIB_NULL )
        //{
        //    if ( p1->Status != POPUP_STATUS_OFF )
        //    {
        //        p1->Status = POPUP_STATUS_OFF;
        //    }
        //    p1 = p1->next;
        //}

        p1 = PopupList_Malloc();
        if ( p1 != POPUPLIB_NULL )
        {
            p1->PopupID = PopupID;
            p1->Status = POPUP_STATUS_FIRST;
            p1->Timer     = 0u;
            p1->next = POPUPLIB_NULL;
            FatalListHead = PopupList_Insert ( FatalListHead, p1 );
            Popup_Cal_CutGrade ( PopupID );
        }
    }
    else
    {
        if((p1->Status == POPUP_STATUS_DELETE) || (p1->Status == POPUP_STATUS_CLEAR))
        {
          p1->Status = POPUP_STATUS_FIRST;
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Hint_Request
 *@Description:   ����ڶ�����Ϣ����ȷ�����л��ȼ�
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Malloc / PopupList_Insert / Popup_Cal_CutGrade
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static void Popup_Hint_Request ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = PopupList_Select ( HintListHead, &PopupID );
    if ( p1 == POPUPLIB_NULL )
    {
        p1 = PopupList_Malloc();
        if ( p1 != POPUPLIB_NULL )
        {
            p1->PopupID = PopupID;
            //if ( FatalListHead == POPUPLIB_NULL )
            //{
            //    p1->Status = POPUP_STATUS_FIRST;
            //    s_PopupScheduling.NewPopupID = PopupID;
    //#if POPUP_HINT_CUT_HINT_IMMEDIATELY
    //            s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;   /*��ʾ��Ϣ���Դ����ʾ�ࡢ�����࣬�������������������Ϣ����ʾ�඼����������� */
    //#else
    //            s_PopupScheduling.CutGrade = POPUP_CUT_WAIT_TIME_MIN;   /*��ʾ��Ϣ���Դ����ʾ�ࡢ�����࣬�������������������Ϣ����ʾ�඼����������� */
    //#endif
            //    s_PopupScheduling.PollPopupID = s_PopupScheduling.CurPopupID;
            //    
            //}
            //else
            //{
            //    p1->Status = POPUP_STATUS_OFF;
            //}
            p1->Status = POPUP_STATUS_FIRST;
            p1->Timer    = 0u;
            p1->next = POPUPLIB_NULL;
            HintListHead = PopupList_Insert ( HintListHead, p1 );
            Popup_Cal_CutGrade ( PopupID );
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Warning_Request
 *@Description:   �����������Ϣ����ȷ�����л��ȼ�
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Malloc / PopupList_Insert / Popup_Cal_CutGrade
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static void Popup_Warning_Request ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = PopupList_Select ( WarningListHead, &PopupID );
    if ( p1 == POPUPLIB_NULL )
    {
        /*��ͨ�������Դ����ʾ����Ϣ����δ��ʾ����ʾ����Ϣ�����ٽ�����ʾ����ͬ�����ⱨ��*/
    #if POPUP_WARNING_CUT_HINT_MIN
        p1 = HintListHead;
        while ( p1 != POPUPLIB_NULL )
        {
            if ( p1->Status != POPUP_STATUS_OFF )
            {
                p1->Status = POPUP_STATUS_OFF;
            }
            p1 = p1->next;
        }
    #endif

        p1 = PopupList_Malloc();
        if ( p1 != POPUPLIB_NULL )
        {
            p1->PopupID = PopupID;
            p1->Status = POPUP_STATUS_FIRST;
            p1->Timer     = 0u;
            p1->next = POPUPLIB_NULL;
            WarningListHead = PopupList_Insert ( WarningListHead, p1 );
            /*����������ⱨ��������������Ϣ*/
            if ( FatalListHead == POPUPLIB_NULL )
            {
            #if POPUP_WARNING_CUT_HINT_MIN
                /*���������ʾ����Ϣ���ȴ���Сʱ��󣬴��*/
                if ( PopupAttributeTable[s_PopupScheduling.CurPopupID].Type == POPUP_TYPE_HINT )
                {
                    s_PopupScheduling.NewPopupID = PopupID;
                    s_PopupScheduling.CutGrade = POPUP_CUT_WAIT_TIME_MIN;
                }
                else
                {
                    Popup_Cal_CutGrade ( PopupID );
                }
            #else
                Popup_Cal_CutGrade ( PopupID );
            #endif
            }
        }
    }

    return;
}

/**********************************************************************************************************
 *@Function:  		Popup_Exception_Request
 *@Description:   �����������Ϣ����ȷ�����л��ȼ�
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  ExceptionListHead -- ������
 *@Calls:  			  PopupList_Select / PopupList_Malloc / PopupList_Insert / Popup_Cal_CutGrade
 *@Return:  		  none.
 *@Note:    		  none.
 **********************************************************************************************************/
static void Popup_Exception_Request ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;

    p1 = PopupList_Select ( ExceptionListHead, &PopupID );
    if ( p1 == POPUPLIB_NULL )
    {
        p1 = PopupList_Malloc();
        if ( p1 != POPUPLIB_NULL )
        {
            p1->PopupID = PopupID;
            p1->Status = POPUP_STATUS_FIRST;
            p1->Timer     = 0u;
            p1->next = POPUPLIB_NULL;
            ExceptionListHead = PopupList_Insert ( ExceptionListHead, p1 );

            if ( FatalListHead == POPUPLIB_NULL )
            {
                Popup_Cal_CutGrade ( PopupID );
            }
        }
    }
    
    return;
}


/**********************************************************************************************************
 *@Function:  		Popup_Select
 *@Description:   ��ȫ�������в���ָ��ID��λ��
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  struct PopupList *head -- ����ͷ
 *					      struct PopupList *p -- ָ��ID���ڵ�λ��
 *@Calls:  			  PopupList_Select
 *@Return:  		  struct PopupList *p -- ָ��ID���ڵ�λ��
 *@Note:    		  none
 **********************************************************************************************************/
static struct PopupList *Popup_Select ( uint16_t PopupID )
{
    struct PopupList *head = POPUPLIB_NULL;
    struct PopupList *p1 = POPUPLIB_NULL;

    /*1���������ͣ���ȡ����ͷ*/
    if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_FATAL )
    {
        head = FatalListHead;
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_HINT )
    {
        head = HintListHead;
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_WARNING )
    {
        head = WarningListHead;
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_EXCEPTION )
    {
        head = ExceptionListHead;
    }
    else
    {

    }

    /*2������IDλ��*/
    if ( head != POPUPLIB_NULL )
    {
        p1 = PopupList_Select ( head, &PopupID );
    }

    return p1;
}

/**********************************************************************************************************
 *@Function:  		Popup_Delete_Request
 *@Description:   ��ȫ�������в���ָ��ID��λ��
 *@Input:			    uint8_t PopupID -- ������Ϣ��ID
 *@Output:			  struct PopupList *head -- ����ͷ
 *					      struct PopupList *p -- ָ��ID���ڵ�λ��
 *@Calls:  			  PopupList_Select
 *@Return:  		  struct PopupList *p -- ָ��ID���ڵ�λ��
 *@Note:    		  none
 **********************************************************************************************************/
static void Popup_Delete_Request ( uint16_t PopupID )
{
    /*1���������ͣ���ȡ����ͷ*/
    if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_FATAL )
    {
        FatalListHead = PopupList_Delete ( FatalListHead, PopupID );
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_HINT )
    {
        HintListHead = PopupList_Delete ( HintListHead, PopupID );
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_WARNING )
    {
        WarningListHead = PopupList_Delete ( WarningListHead, PopupID );
    }
    else if ( PopupAttributeTable[PopupID].Type == POPUP_TYPE_EXCEPTION )
    {
        ExceptionListHead = PopupList_Delete ( ExceptionListHead, PopupID );
    }
    else
    {

    }

    return;
}

/**********************************************************************************************************
 *@Function:  	Popup_Cal_CutGrade
 *@Description: ��������Ϣ���л��ȼ�
 *@Input:			  uint8_t NewPopupID -- �µĵ�����ϢID
 *@Output:			none.
 *@Calls:  			Popup_Compare_Priority
 *@Return:  		Grade0 -- ���л�����
 *              Grade1 -- ���л��ȼ�����ǰ��ʾ��Ϣ������ǵ�һ����Ҫ����Tnormal(4s)�������������.
 *              Grade2 -- ���л��ȼ�����ǰ��ʾ��Ϣ������ǵ�һ����Ҫ����Tmin(2s)�������������.
 *              Grade3 -- ���л��ȼ���������ϵ�ǰ��ʾ��Ϣ.
 *@Note:    		none
 **********************************************************************************************************/
static void Popup_Cal_CutGrade ( uint16_t NewPopupID )     //15
{
    uint8_t ret = 0u;

    /*�Ѿ������л��ȼ����������Ϣ�����ȼ�����δ��ʾ����Ϣ�����л��ȼ�ά�ֲ���*/
    if ( s_PopupScheduling.NewPopupID < POPUP_MAX )
    {
        ret = Popup_Compare_Priority ( NewPopupID, s_PopupScheduling.NewPopupID );
        if ( ret != 0u )
        {
            s_PopupScheduling.NewPopupID = NewPopupID;
            Popup_Cal_CutGrade_loc(NewPopupID);
        }
    }
    else
    {
        s_PopupScheduling.NewPopupID = NewPopupID;
        Popup_Cal_CutGrade_loc(NewPopupID);
    }

    return;
}

static void Popup_Cal_CutGrade_loc ( uint16_t NewPopupID )
{
    uint8_t ret = 0u;

    if ( s_PopupScheduling.CurPopupID < POPUP_MAX )
    {
        ret = Popup_Compare_Priority ( NewPopupID, s_PopupScheduling.CurPopupID );
        switch ( ret )
        {
            case 0u: /*����Ϣ���ȼ�����/���ڵ�ǰ��ʾ����*/
                if ( PopupAttributeTable[NewPopupID].Class == PopupAttributeTable[s_PopupScheduling.CurPopupID].Class )
                {
#if POPUP_SAME_CLASS_CUT_IMMEDIATELY
                    s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;       /*������ͬ��������ϵ�ǰ*/
                    //Popup_Update_Status ( s_PopupScheduling.CurPopupID );
                    s_PopupScheduling.SndReqCode++;
#endif
                }
                else
                {
                    s_PopupScheduling.CutGrade = POPUP_CUT_WAIT_TIME_NORMAL;
                }
                break;

#if POPUP_HIGH_CUT_LOW_TYPE_IMMEDIATELY
            case 1u: /*����Ϣ�����͸�*/
                s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
                s_PopupScheduling.PollPopupID = s_PopupScheduling.CurPopupID;
                break;
#endif

            case 2u:
            case 3u: /*����Ϣ�����ȼ��ߣ��������������ȼ���*/
                s_PopupScheduling.CutGrade = POPUP_CUT_WAIT_TIME_MIN;
                break;

            default:
                s_PopupScheduling.CutGrade = POPUP_CUT_NOT;
                break;
        }
    }
    else
    {
        s_PopupScheduling.CutGrade = POPUP_CUT_IMMEDIATELY;
    }
}

/**********************************************************************************************************
 *@Function:  		Popup_Compare_Priority
 *@Description:   �Ƚ����ֵ�����Ϣ�����ȼ�
 *@Input:			    uint8_t PopupID1 -- ������Ϣ1
 *                uint8_t PopupID2 -- ������Ϣ2
 *@Output:		    none.
 *@Calls:  			  PopupAttributeTable -- ���Ա�
 *@Return:  		  0 -- �������ȼ���ͬ��PopupID1�����ȼ���
 *                1 -- PopupID1�����͸���PopupID2������
 *                2 -- PopupID1�������ȼ�����PopupID2�������ȼ�
 *                3 -- PopupID1�ĸ����ȼ�����PopupID2�ĸ����ȼ�
 *@Note:    		  none
 **********************************************************************************************************/
static uint8_t Popup_Compare_Priority ( uint16_t PopupID1, uint16_t PopupID2 )
{
    uint8_t ret = 0u;

    /*�Ƚ�����*/
    if ( PopupAttributeTable[PopupID1].Type < PopupAttributeTable[PopupID2].Type )
    {
        ret = 1u;
    }
    else if ( PopupAttributeTable[PopupID1].Type == PopupAttributeTable[PopupID2].Type )
    {
        /*������ͬ���Ƚ������ȼ�*/
        if ( PopupAttributeTable[PopupID1].Priority < PopupAttributeTable[PopupID2].Priority )
        {
            ret = 2u;
        }
        else if ( PopupAttributeTable[PopupID1].Priority == PopupAttributeTable[PopupID2].Priority )
        {
            /*������ͬ�������ȼ���ͬ���Ƚϸ����ȼ�*/
            if ( PopupAttributeTable[PopupID1].SubPriority < PopupAttributeTable[PopupID2].SubPriority )
            {
                ret = 3u;
            }
        }
        else
        {
        }
    }
    else
    {
    }

    return ret;
}


/**********************************************************************************************************
 *@Function:  		Popup_Get_First_Masked_Warning
 *@Description:   ��ȡ��һ��������Ϣ
 *@Input:			    none.
 *@Output:		    none.
 *@Calls:  			  none.
 *@Return:  		  ��һ��������Ϣ��ID�����û��������Ϣ������POPUP_NONE
 *@Note:    		  none
 **********************************************************************************************************/

uint16_t Popup_Get_First_Masked_Warning ( void )
{
    struct PopupList *p = POPUPLIB_NULL;
    uint16_t retVal = POPUP_NONE;
    
    p = WarningListHead;
    while ( p != POPUPLIB_NULL )
    {
        if ( p->Status == POPUP_STATUS_MASKED )
        {
            break;
        }
        p = p->next;
    }

    if ( p != POPUPLIB_NULL )
    {
        retVal = p->PopupID;
    }

    return retVal;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Last_Masked_Warning
 *@Description:   ��ȡ���һ��������Ϣ
 *@Input:			    none.
 *@Output:		    none.
 *@Calls:  			  none.
 *@Return:  		  ���һ��������Ϣ��ID�����û��������Ϣ������POPUP_NONE
 *@Note:    		  none
 **********************************************************************************************************/
static uint16_t Popup_Get_Last_Masked_Warning ( void )
{
    struct PopupList *p1 = POPUPLIB_NULL;
    struct PopupList *p2 = POPUPLIB_NULL;
    uint16_t retVal = POPUP_NONE;

    p1 = WarningListHead;
    while ( p1 != POPUPLIB_NULL )
    {
        if ( p1->Status == POPUP_STATUS_MASKED )
        {
            p2 = p1;
        }
        p1 = p1->next;
    }

    if ( p2 != POPUPLIB_NULL )
    {
        retVal = p2->PopupID;
    }

    return retVal;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Previous_Masked_Warning
 *@Description:   ��ȡ��ǰ��ʾ��������Ϣ����һ��������Ϣ
 *@Input:			    none.
 *@Output:		    none.
 *@Calls:  			  none.
 *@Return:  		  ��һ��������Ϣ��ID�������һ����ϢΪ�գ�����POPUP_NONE
 *@Note:    		  none
 **********************************************************************************************************/
static uint16_t Popup_Get_Previous_Masked_Warning ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;
    struct PopupList *p2 = POPUPLIB_NULL;
    uint16_t retVal = POPUP_NONE;

    p1 = WarningListHead;
    while ( p1 != POPUPLIB_NULL )
    {
        if ( p1->PopupID == PopupID )
        {
            break;
        }

        if ( ( p1->Status == POPUP_STATUS_MASKED ) && ( PopupAttributeTable[PopupID].Class != PopupAttributeTable[p1->PopupID].Class ) )
        {
            p2 = p1;
        }
        p1 = p1->next;
    }

    if ( p2 != POPUPLIB_NULL )
    {
        retVal = p2->PopupID;
    }

    return retVal;
}

/**********************************************************************************************************
 *@Function:  		Popup_Get_Previous_Masked_Warning
 *@Description:   ��ȡ��ǰ��ʾ��������Ϣ����һ��������Ϣ
 *@Input:			    none.
 *@Output:		    none.
 *@Calls:  			  none.
 *@Return:  		  ��һ��������Ϣ��ID�������һ����ϢΪ�գ�����POPUP_NONE
 *@Note:    		  none
 **********************************************************************************************************/
static uint16_t Popup_Get_Next_Masked_Warning ( uint16_t PopupID )
{
    struct PopupList *p1 = POPUPLIB_NULL;
    uint16_t retVal = POPUP_NONE;

    p1 = PopupList_Select ( WarningListHead, &PopupID );
    p1 = p1->next;

    while ( p1 != POPUPLIB_NULL )
    {
        if ( ( p1->Status == POPUP_STATUS_MASKED ) && ( PopupAttributeTable[PopupID].Class != PopupAttributeTable[p1->PopupID].Class ) )
        {
            break;
        }
        p1 = p1->next;
    }

    if ( p1 != POPUPLIB_NULL )
    {
        retVal = p1->PopupID;
    }

    return retVal;
}

static void Popup_IRQ_Enable(void)
{
    EnableInterrupts;
}

static void Popup_IRQ_Disable(void)
{
    DisableInterrupts;
}

/******************************************************************************
��������Popup_Mask_Request
��  �ܣ��������α�����Ϣ
        ����������ʱ�̷�����������,ֻ��������������ʱ,������Ϣ�Żᱻ����
��  ������
����ֵ����
******************************************************************************/
void Popup_Hint_Mask_Request ( uint16_t PopupID )
{

}

uint8_t Popup_Get_Hint_Msg(uint16_t *pList, uint16_t len)
{
	uint8_t           i        = 0u;
	uint8_t           jumpFlag = 0u;
	uint8_t           PopupNum = 0;
	uint8_t            PopupID  = 0u;
	struct PopupList *p1       = POPUPLIB_NULL;
//	Hint_MaskPopupNum = 0;

	p1 = HintListHead;

	while ( p1 != POPUPLIB_NULL )
	{
		jumpFlag = 0u;
		PopupID  = p1->PopupID;
		p1 = p1->next;

		if ( PopupAttributeTable [ PopupAttributeTable [ PopupID ].Class ].pMbrList != POPUPLIB_NULL )
		{
			for (  i = 0u; i < PopupNum; i++ )
			{
				if (PopupAttributeTable [ pList [ i ] ].Class == PopupAttributeTable [ PopupID ].Class  )
				{
					jumpFlag = 1u;
					break;
				}
			}
		}

		if ( jumpFlag == 0u )
		{
			pList [ PopupNum ] = PopupAttributeTable [ PopupID ].Message;
			PopupNum++;
			if ( PopupNum > len )
			{								   
				break;
			}
		}
	}
	return PopupNum;
}


uint8_t Popup_Get_Warring_Msg(uint16_t *pList, uint16_t len)
{
	uint8_t i = 0u;
	uint8_t startIndex = 0u;
	uint8_t endIndex = 0u;
	uint8_t jumpFlag = 0u;
	uint8_t PopupID = 0u;
	uint8_t PopupNum = 0u;
	uint8_t MaskPopupID = 0u;

	Popup_Masked_Warning_Polling_Reset(POPUP_POLLING_FORWARD);
	while (PopupID != 0xffu)
	{
		jumpFlag = 0u;
		PopupID = (uint8_t)Popup_Get_Masked_Warning_Msg();
		Popup_Masked_Warning_Polling(POPUP_POLLING_FORWARD);
		if (PopupID == 0xFF)
		{
			break;
		}
		if (PopupAttributeTable[PopupAttributeTable[PopupID].Class].pMbrList != NULL)
		{
			for (i = 0u; i < PopupNum; i++)
			{
				if (PopupAttributeTable[ pList[ i ] ].Class == PopupAttributeTable[PopupID].Class)
				{
					jumpFlag = 1u;
					break;
				}
			}
		}

		if (jumpFlag == 0u)
		{
			if (PopupID != 0xffu)
			{
				pList[PopupNum] = PopupAttributeTable [ PopupID ].Message;//PopupID;
				PopupNum++;
				if(PopupNum > len)
				{
					break;
				}
			}
		}
	}

	return PopupNum;

}

/**********************************************************************************************************
 **********************************************************************************************************/
