⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 calldisplayitem.cpp

📁 一个WinCE6。0下的IP phone的源代码
💻 CPP
📖 第 1 页 / 共 3 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this sample source code is subject to the terms of the Microsoft
// license agreement under which you licensed this sample source code. If
// you did not accept the terms of the license agreement, you are not
// authorized to use this sample source code. For the terms of the license,
// please see the license agreement between you and Microsoft or, if applicable,
// see the LICENSE.RTF on your install media or the root of your tools installation.
// THE SAMPLE SOURCE CODE IS PROVIDED "AS IS", WITH NO WARRANTIES.
//
#include <windows.h>

#define INITGUID
#include <initguid.h>
#include "DisplayItem.hpp"
#undef INITGUID

#include "CallDisplayItem.h"
#include "Common.hpp"
#include "UIManager.hpp"
#include "NewResource.hpp"
#include "auto_xxx.hxx"
#include "Debug.hpp"

#include "CallBase.hpp"
#include <winuserm.h>
#include "LayoutColor.hpp"
#include "VoIPApp.hpp"

/*------------------------------------------------------------------------------
    FormatRectForLabeledControl
    
    helper function to format the rect for call control
    
------------------------------------------------------------------------------*/
HRESULT 
FormatRectForLabeledControl(
    RECT *prcOriginal,
    RECT *prcAdjust,
    UINT  idLabel,
    short AfterLabelMargin, 
    short RightMargin, 
    short TopMargin, 
    short BottomMargin
    )
{
    HDC hdc = CreateCompatibleDC(NULL);
    if (hdc == NULL)
    {
        return E_FAIL;         
    }
    
    HRESULT hr = CommonUtilities_t::ToHR(::DrawText(
                    hdc,
                    CommonUtilities_t::LoadString(GlobalData_t::s_ModuleInstance, idLabel),
                    -1,
                    prcAdjust,
                    DT_LEFT | DT_WORDBREAK | DT_CALCRECT | DT_NOPREFIX
                    ));
    if (FAILED(hr))
    {
        goto exit; 
    }

    prcAdjust->left   = prcAdjust->right    + AfterLabelMargin;
    prcAdjust->right  = prcOriginal->right  - RightMargin;
    prcAdjust->top    = prcOriginal->top    + TopMargin;
    prcAdjust->bottom = prcOriginal->bottom - BottomMargin;


exit: 

    DeleteDC(hdc);
    return hr;
}


/*------------------------------------------------------------------------------
    FormatDurationString
    
    Helper function used to format the duration of a call
    
    Parameters:
        : pstDuration - the systemtime struct containing the duration
        : wszBuf - the buffer to copy the string into
        : cchBuf - the size of wszBuf in wide-characters
    
    Returns (HRESULT): indicating success or failure
------------------------------------------------------------------------------*/
HRESULT 
FormatDurationString(
    const SYSTEMTIME * pstDuration, 
    WCHAR * wszBuf, 
    INT cchBuf
    )
{
    HRESULT hr = S_OK;

    hr = CommonUtilities_t::ToHR(GetTimeFormat(
        LOCALE_USER_DEFAULT,
        TIME_FORCE24HOURFORMAT,
        pstDuration,
        CommonUtilities_t::LoadString(GlobalData_t::s_ModuleInstance, IDS_TIME_FMT_DURATION),  // GetTimeFormat will fail if this call fails
        wszBuf,
        cchBuf
        ));

    return hr;
}



//Internal constants

//If the item is not dialing or transferring, the state defers to the
//state of the currentcall inside the item, this #define represents
//that deferring state
#define e_csDeferToCallStatus  (CallDisplayItemState)-3

// Speed of the animation, in milliseconds / frame
const INT c_cmsAnimateSpeed = 500;

//Subitem text indicies

//Mapping between a callstatus and the glyphs to be used for animating
//the call in the corresponding state
struct CallAnimationEntry
{
    RTC_SESSION_STATE   CallStatus;         // Call status
    INT                 idxGlyphOffset;     // Offset from the top of the glyph BMP, in "glyph units"
    INT                 cGlyphFrames;       // Number of frames in the glyph animation
};

const UINT c_idxGlyphInvalid            = 0; const UINT c_cFramesInvalid          = 1;
const UINT c_idxGlyphConnected          = 1; const UINT c_cFramesConnected        = 1;
const UINT c_idxGlyphInConference       = 2; const UINT c_cFramesInConference     = 1;
const UINT c_idxGlyphInProgress         = 3; const UINT c_cFramesInProgress       = 4;
const UINT c_idxGlyphHolding            = 4; const UINT c_cFramesHolding          = 2;
const UINT c_idxGlyphDisconnected       = 5; const UINT c_cFramesDisconnected     = 1;
const UINT c_idxGlyphSentToConference   = 6; const UINT c_cFramesSentToConference = 1;
const UINT c_idxGlyphReferring          = 7; const UINT c_cFramesReferring        = 1;
const UINT c_idxGlyphIncoming           = 8; const UINT c_cFramesIncoming         = 1;
const UINT c_idxGlyphAnswerring         = 8; const UINT c_cFramesAnswerring       = 1;

//Table for the entire mapping
CallAnimationEntry sc_AnimationEntryLookup[] =
{
    { RTCSS_IDLE,                     c_idxGlyphInvalid,          c_cFramesInvalid          },
    { RTCSS_INCOMING,                 c_idxGlyphIncoming,         c_cFramesIncoming         },
    { RTCSS_INPROGRESS,               c_idxGlyphInProgress,       c_cFramesInProgress       },
    { RTCSS_ANSWERING,                c_idxGlyphAnswerring,       c_cFramesAnswerring       },
    { RTCSS_REFER,                    c_idxGlyphReferring,        c_cFramesReferring        },
    { RTCSS_CONNECTED,                c_idxGlyphConnected,        c_cFramesConnected        },
    { RTCSS_DISCONNECTED,             c_idxGlyphDisconnected,     c_cFramesDisconnected     },
    { RTCSS_HOLD,                     c_idxGlyphHolding,          c_cFramesHolding          },
};

/*------------------------------------------------------------------------------
    FindAnimationStatusEntry
    
    Finds a animation entry by callstatus by iterating over the
    lookup table.
    
    Parameters:
        CallStatus: Call status whose entry is requested.
    
    Returns (CallAnimationEntry): A pointer to the animation entry,
        or NULL if the call status was not found.
------------------------------------------------------------------------------*/
inline const CallAnimationEntry* FindAnimationStatusEntry(RTC_SESSION_STATE status)
{
    for (INT i = 0; i < ARRAYSIZE(sc_AnimationEntryLookup); i++)
    {
        if (sc_AnimationEntryLookup[i].CallStatus == status)
        {
            return &sc_AnimationEntryLookup[i];
        }
    }

    return NULL;
}

/*------------------------------------------------------------------------------
    CallDisplayItem_t::CallDisplayItem_t
    
    Constructor for a channel item.
    
    Parameters:
        pCall: Current call to associate with this item.
------------------------------------------------------------------------------*/
CallDisplayItem_t::CallDisplayItem_t(
    Call_t *pCall /* = NULL */
    ) 
{
    TRACE(ZONE_PHONEAPP_FUNCTION); 
    m_State                 = (pCall == NULL) ? e_csDialing : e_csDeferToCallStatus;
    m_cpCall                = pCall;
    m_tk                    = 0;
    m_RemovingEditControl   = false; 
}

CallDisplayItem_t::~CallDisplayItem_t()
{
    ; 
}


HRESULT
CallDisplayItem_t::QueryInterface(
    REFIID riid,
    void** ppvObject
    )
{
    if (!ppvObject)
    {
        return E_INVALIDARG;
    }

    HRESULT hr = S_OK;

    if (riid == IID_IVoIPDisplayControl)
    {
        *ppvObject = (IVoIPDisplayControl*)this;
    }
    else
    {
        *ppvObject = NULL;
        hr = E_NOTIMPL;
    }

    return hr;
}

BOOL 
CallDisplayItem_t::GetHeight(
    UINT* pHeight
    )
{
    PREFAST_ASSERT(pHeight);
    *pHeight = Layout_t::CallItemHeight();   
    return TRUE;
}

HRESULT 
CallDisplayItem_t::ShowControls(
    BOOL IsVisible
    )
{
    if (!(HWND)m_EditControl || m_RemovingEditControl)
    {
        return S_FALSE;
    }

    if (!IsVisible || m_State == e_csDeferToCallStatus)
    {
        ShowWindow(m_EditControl, SW_HIDE); 
    }
    else
    {
        ShowWindow(m_EditControl, SW_SHOW); 
    }
    
    return S_OK;
}

/*------------------------------------------------------------------------------
    CallDisplayItem_t::Position
    
    Positions the commcontrols on the display item
    
    Parameters:
        hwndLV: HWND of the parent for the controls
        pRECT:    RECT of the display item
        fVisible: TRUE if this control is on-screen
    
    Returns (HRESULT): 
------------------------------------------------------------------------------*/
HRESULT 
CallDisplayItem_t::PositionControls(
    HWND  VirtualListBox, 
    RECT* pRECT
    )
{
    if (pRECT == NULL)    
    {
        return E_INVALIDARG; 
    }

    //if we are not visible or just NOT showing the control, hide the control
    if (m_State == e_csDeferToCallStatus)
    {
        if ((HWND)m_EditControl)
        {
            ShowWindow(
                m_EditControl, 
                SW_HIDE
                );
        }
        
        return S_OK;
    }

    //Otherwise we need to show/create the control

    //Move/Size the rectangle where we are placing the control
    //based on our state
    RECT rcControl = *pRECT;
            
    if (m_State == e_csDialing)
    {
        FormatRectForLabeledControl(
            pRECT, 
            &rcControl, 
            IDS_LABEL_DIAL,
            Layout_t::DialingStateAfterLabelMargin(),
            Layout_t::DialingStateRightMargin(), 
            Layout_t::DialingStateTopMargin(), 
            Layout_t::DialingStateBottomMargin()            
            );
    }

    if (m_State == e_csTransferring)
    {
        FormatRectForLabeledControl(
            pRECT, 
            &rcControl, 
            IDS_LABEL_DIAL,
            Layout_t::TransferringStateAfterLabelMargin(), 
            Layout_t::TransferringStateRightMargin(), 
            Layout_t::TransferringStateTopMargin(), 
            Layout_t::TransferringStateBottomMargin()
            );
    }

    HRESULT hr = S_OK; 
    
    //Create the control if necessary
    if (!(HWND)m_EditControl)
    {
        hr = m_EditControl.Create(
                        WNDCLASS_EDIT,
                        NULL,
                        WS_VISIBLE | WS_CHILD | ES_AUTOHSCROLL | WS_BORDER,
                        0,
                        VirtualListBox,
                        rcControl.left,
                        rcControl.top,
                        rcControl.right - rcControl.left,
                        rcControl.bottom - rcControl.top
                        );

        if (FAILED(hr))
        {
            ASSERT(FALSE); 
            return hr; 
        }

        m_EditControl.SetCallbackPointer((INT_PTR)this);

        m_rcControl = rcControl;

        ///TODO: need to hook up with the input button
        SendMessage(
            m_EditControl, 
            EM_SETINPUTMODE, 
            0, 
            (LPARAM)EIM_NUMBERS
            ); 

        WCHAR AlreadyDialedString[MAX_PATH] = L""; 
        GetApp()->GetUIManager().GetAlreadyDialedString(
                                    AlreadyDialedString, 
                                    ARRAYSIZE(AlreadyDialedString)
                                    ); 
        if (AlreadyDialedString[0] != L'\0')
        {
            SendMessage(
                m_EditControl, 
                WM_SETTEXT, 
                0, 
                reinterpret_cast<LPARAM>(AlreadyDialedString)
                ); 

            GetApp()->GetUIManager().UpdateMenuBar(); 
        }
        
        return S_OK;
    }

    //only move the control, if the window pos has changed since last time we placed
    //the control
    if (memcmp(&m_rcControl, &rcControl, sizeof(RECT)) != 0)
    {
        m_rcControl = rcControl;
        
        hr = MoveWindow(
                m_EditControl, 
                rcControl.left, 
                rcControl.top, 
                rcControl.right - rcControl.left, 
                rcControl.bottom - rcControl.top, 
                TRUE
                );
    }
    
    return S_OK;
}

/*------------------------------------------------------------------------------

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -