www.pudn.com > lightlamp.rar > lightlampDlg.cpp
/*
** ============================================================================
**
** FILE
** lightlampDlg.cpp
**
** DESCRIPTION
** Lighting Lamp Implementation File
**
** CREATED
** I.A.Marsden Integration UK Ltd
**
** COPYRIGHT
** Copyright 2005 Integration Associates Inc. All rights reserved.
**
** LIMITED USE LICENSE. By using this software, the user agrees to the terms of the
** following license. If the user does not agree to these terms,
** then this software should be returned within 30 days and a full
** refund of the purchase price or license fee will provided.
** Integration Associates hereby grants a license to the user on the
** following terms and conditions: The user may use, copy, modify,
** revise, translate, abridge, condense, expand, collect, compile,
** link, recast, distribute, transform or adapt this software solely
** in connection with the development of products incorporating
** integrated circuits sold by Integration Associates. Any other use
** for any other purpose is expressly prohibited with the prior written
** consent of Integration Associates.
**
** Any copy or modification made must satisfy the following conditions:
**
** 1. Both the copyright notice and this permission notice appear in all copies of the software,
** derivative works or modified versions, and any portions thereof, and that both notices
** appear in supporting documentation.
**
** 2. All copies of the software shall contain the following acknowledgement: "Portions of this
** software are used under license from Integration Associates Inc. and are copyrighted."
**
** 3 Neither the name of Integration Associates Inc. nor any of its subsidiaries may be used
** to endorse or promote products derived from this software without specific prior written
** permission.
**
** THIS SOFTWARE IS PROVIDED BY "AS IS" AND ALL WARRANTIES OF ANY KIND, INCLUDING THE IMPLIED
** WARRANTIES OF MERCHANTABILITY AND FITNESS FOR USE, ARE EXPRESSLY DISCLAIMED. THE DEVELOPER
** SHALL NOT BE LIABLE FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
** THIS SOFTWARE MAY NOT BE USED IN PRODUCTS INTENDED FOR USE IN IMPLANTATION OR OTHER DIRECT
** LIFE SUPPORT APPLICATIONS WHERE MALFUNCTION MAY RESULT IN THE DIRECT PHYSICAL HARM OR INJURY
** TO PERSONS. ALL SUCH IS USE IS EXPRESSLY PROHIBITED.
** ============================================================================
*/
#include "stdafx.h"
#include "lightlamp.h"
#include "lightlampDlg.h"
#include "ConfigureDlg.h"
#include "ZBDLLApi.h"
#include "ZigBeeIf.h"
#include "bisync_tokens.h"
#include "ZigBeeStructures.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
/*
** ============================================================================
** Function Prototypes
** ============================================================================
*/
ClightlampDlg* m_lightlampDlg = NULL;
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialog
{
public:
CAboutDlg();
// Dialog Data
enum { IDD = IDD_ABOUTBOX };
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
// Implementation
protected:
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
{
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
END_MESSAGE_MAP()
/*
** ============================================================================
**
** FUNCTION NAME:
** ClightlampDlg
**
** DESCRIPTION
** Constructor
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
ClightlampDlg::ClightlampDlg(CWnd* pParent /*=NULL*/)
: CDialog(ClightlampDlg::IDD, pParent)
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
m_lightlampDlg = this; // The single instantiation
}
/*
** ============================================================================
**
** FUNCTION NAME:
** DoDataExchange
**
** DESCRIPTION
** Load / Unload the controls
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
void ClightlampDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
DDX_Control(pDX, IDC_STATIC_STATUS, m_Status);
DDX_Control(pDX, IDC_STATIC_LAMP, m_Lamp);
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ClightlampDlg MESSAGE MAP
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
BEGIN_MESSAGE_MAP(ClightlampDlg, CDialog)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_DESTROY()
ON_WM_QUERYDRAGICON()
//}}AFX_MSG_MAP
ON_BN_CLICKED(IDC_BUTTON_BIND, OnBnClickedButtonBind)
ON_MESSAGE(WM_USER+ZDO_SET_CONFIRM, ZDO_SET_confirm )
ON_MESSAGE(WM_USER+ZDO_RESET_CONFIRM, ZDO_RESET_confirm )
ON_MESSAGE(WM_USER+ZDO_START_CONFIRM, ZDO_START_confirm )
ON_MESSAGE(WM_USER+ZDO_END_DEVICE_BIND_CONFIRM, ZDO_END_DEVICE_BIND_confirm )
ON_MESSAGE(WM_USER+AF_INDIRECT_INDICATION, AF_INDIRECT_indication )
ON_MESSAGE(WM_USER+ZDO_NLME_SYNC_CONFIRM, ZDO_NLME_SYNC_confirm )
END_MESSAGE_MAP()
/*
** ============================================================================
**
** FUNCTION NAME:
** OnInitDialog
**
** DESCRIPTION
** Initialise the dialog
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
BOOL ClightlampDlg::OnInitDialog()
{
int retval;
CDialog::OnInitDialog();
// Add "About..." menu item to system menu.
// IDM_ABOUTBOX must be in the system command range.
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
CString strAboutMenu;
strAboutMenu.LoadString(IDS_ABOUTBOX);
if (!strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
nBitmapOff.LoadBitmap( IDB_BITMAP_BULBOFF ); // Load bitmaps
nBitmapOn.LoadBitmap( IDB_BITMAP_BULBON );
m_Lamp.SetBitmap( nBitmapOff.operator HBITMAP() ); // Set the starting picture to be off
m_lightlampDlg->m_Status.SetWindowText( "Lamp Off" ); // Set the text too
hZigBee = new CZigBeeIf(); // The ZigBee If
if ( hZigBee == NULL )
{
// Error creating the ZigBee interface
::MessageBox( m_hWnd, "Error Creating ZigBee Interface", "ZigBee Light Lamp", MB_ICONSTOP | MB_OK );
return FALSE;
}
retval = hZigBee->ZBIFConnect( m_hWnd ); // Find some hardware
if (retval != STK_SUCCESS)
{
// Error
::MessageBox( m_hWnd, "Error Opening ZigBee Interface", "ZigBee Light Lamp", MB_ICONSTOP | MB_OK );
return FALSE;
}
CConfigureDlg hConfigureDlg; // The Config Dialog
hConfigureDlg.s_Channel = "00020000"; // Initial dialog settings
hConfigureDlg.s_PANId = "1AAA";
hConfigureDlg.b_ZC = 1;
hConfigureDlg.b_ZR = 0;
hConfigureDlg.b_ZED = 0;
INT_PTR nResponse = hConfigureDlg.DoModal(); // Display the dialog
if (nResponse == IDCANCEL)
{
return FALSE; // Cancelled Config so just leave
}
// get the device type
if ( hConfigureDlg.b_ZC != 0 ) DevType = 0;
else if ( hConfigureDlg.b_ZR != 0 ) DevType = 1;
else DevType = 2;
CHAR scanbuf[6];
scanbuf[2] = '\0';
// Get the channel mask
int i = hConfigureDlg.s_Channel.Find( 'x' );
if ( i != -1 )
{
hConfigureDlg.s_Channel.Delete( 0, i+1 ); // Strip off the 0x
}
i = hConfigureDlg.s_Channel.GetLength();
if ( i < 8 )
{
hConfigureDlg.s_Channel = "FFFFFFFF"; // Too few digits, so overwrite
}
for ( i = 4 ; i > 0 ; i-- )
{
scanbuf[0] = hConfigureDlg.s_Channel[0];
scanbuf[1] = hConfigureDlg.s_Channel[1];
hConfigureDlg.s_Channel.Delete( 0, 2 );
sscanf( scanbuf, "%02x", &scanbuf[0] );
ScanChannels[i-1] = scanbuf[0];
}
// Get the PANId
i = hConfigureDlg.s_PANId.Find( 'x' );
if ( i != -1 )
{
hConfigureDlg.s_PANId.Delete( 0, i+1 ); // Strip off the 0x
}
i = hConfigureDlg.s_PANId.GetLength();
if ( i < 4 )
{
hConfigureDlg.s_PANId = "1AAA"; // Too few digits, so overwrite
}
for ( i = 2 ; i > 0 ; i-- )
{
scanbuf[0] = hConfigureDlg.s_PANId[0];
scanbuf[1] = hConfigureDlg.s_PANId[1];
hConfigureDlg.s_PANId.Delete( 0, 2 );
sscanf( scanbuf, "%02x", &scanbuf[0] );
PANId[i-1] = scanbuf[0];
}
// Subscribe to relevant Callbacks
hZigBee->ZBIFSubscribe( ZDO_SET_CONFIRM );
hZigBee->ZBIFSubscribe( ZDO_RESET_CONFIRM );
hZigBee->ZBIFSubscribe( ZDO_START_CONFIRM );
hZigBee->ZBIFSubscribe( ZDO_END_DEVICE_BIND_CONFIRM );
hZigBee->ZBIFSubscribe( AF_INDIRECT_INDICATION );
hZigBee->ZBIFSubscribe( ZDO_NLME_SYNC_CONFIRM );
Sleep( 1000 ); // Let the stack start and the world sort itself out
hZigBee->ZDO_RESET_request( 0 ); // Send a reset into the stack
OperatingState = STATE_START; // We are now starting up the device
m_Status.SetWindowText( "Resetting Stack" ); // Tell the user
return TRUE; // return TRUE unless you set the focus to a control
}
/*
** ============================================================================
**
** FUNCTION NAME:
** OnSysCommand
**
** DESCRIPTION
** System Command Menu
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
void ClightlampDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialog::OnSysCommand(nID, lParam);
}
}
/*
** ============================================================================
**
** FUNCTION NAME:
** OnPaint
**
** DESCRIPTION
** Handle the paint request
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
void ClightlampDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, reinterpret_cast(dc.GetSafeHdc()), 0);
// Center icon in client rectangle
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}
/*
** ============================================================================
**
** FUNCTION NAME:
** OnQueryDragIcon
**
** DESCRIPTION
** The system calls this function to obtain the cursor to display while the user drags
** the minimized window.
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
HCURSOR ClightlampDlg::OnQueryDragIcon()
{
return static_cast(m_hIcon);
}
/*
** ============================================================================
**
** FUNCTION NAME:
** OnDestroy
**
** DESCRIPTION
** Close the ZigBee Stack and device
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
void ClightlampDlg::OnDestroy()
{
if ( hZigBee == NULL ) return; // If no stack operational just return
hZigBee->ZBIFDisconnect(); // Disconnect
}
/*
** ============================================================================
**
** FUNCTION NAME:
** OnBnClickedButtonBind
**
** DESCRIPTION
** Action the Bind Button
**
** AUTHOR
** Ian Marsden
**
** ============================================================================
*/
void ClightlampDlg::OnBnClickedButtonBind()
{
UCHAR cl1[2] = { 0, 1 }; // Output Cluster List
UCHAR cl2[1] = { 0 }; // Input Cluster List
if ( hZigBee == NULL ) return; // If no stack operational just return
m_Status.SetWindowText( "Bind in progress" ); // Tell the user
// Send Bind Request
hZigBee->ZDO_END_DEVICE_BIND_request (
0, // LocalCoordinator,
1, // DEP,
0x104, // ProfileID,
1, // NumInClusters,
cl2, // InClusterList,
2, // NumOutClusters,
cl1 // OutClusterList
);
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee ZDO_SET_Confirm Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::ZDO_SET_confirm( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char Status = msg[2];
unsigned char Attribute = msg[3];
/* ============== Created Parameters ============== */
UCHAR buffer[11];
if ( Status != 0 )
{
// SET Error
m_lightlampDlg->OperatingState = STATE_FAIL;
m_lightlampDlg->m_Status.SetWindowText( "Set Failed" ); // Tell the user
}
else
{
switch ( Attribute )
{
case ZIB_CONFIG_PANID:
// Have successfully Set the PANId.
// Build the node descriptor
buffer[0] = m_lightlampDlg->DevType; // Device Type
buffer[1] = 0x40; // Frequency Band
buffer[2] = 0x4F; // MAC Capabilities
buffer[3] = 0; // Manufacturers Code
buffer[4] = 0; // Manufacturers Code
buffer[5] = 0x7F; // Max Buffer
buffer[6] = 0; // Max Transfer
buffer[7] = 0; // Max Transfer
m_lightlampDlg->hZigBee->ZDO_SET_request( ZIB_CONFIG_NODE_DESCRIPTOR, 8, buffer );
m_lightlampDlg->m_Status.SetWindowText( "Setting the Node Descriptor" ); // Tell the user
break;
case ZIB_CONFIG_NODE_DESCRIPTOR:
// Have successfully Set the Node Descriptor.
// Build the mode & params descriptor
buffer[0] = m_lightlampDlg->ScanChannels[0]; // Scan Channels
buffer[1] = m_lightlampDlg->ScanChannels[1]; // Scan Channels
buffer[2] = m_lightlampDlg->ScanChannels[2]; // Scan Channels
buffer[3] = m_lightlampDlg->ScanChannels[3]; // Scan Channels
buffer[4] = 5; // Scan Duration
buffer[5] = 1; // Protocol Version
buffer[6] = 1; // Stack Profile
buffer[7] = 0xF; // Beacon Order
buffer[8] = 0xF; // Superframe Order
buffer[9] = 0; // Battery Life Extension
buffer[10] = 0; // Security Level
m_lightlampDlg->hZigBee->ZDO_SET_request( ZIB_CONFIG_NWK_MODE_AND_PARAMS, 11, buffer );
m_lightlampDlg->m_Status.SetWindowText( "Setting the Mode Descriptor" ); // Tell the user
break;
case ZIB_CONFIG_NWK_MODE_AND_PARAMS:
// Have successfully Set the Mode & Params Descriptor.
// Build the simple descriptor
buffer[0] = 1; // gives 1 for endpoint
buffer[1] = 4; // app profileid = 0x0104
buffer[2] = 1; // app profileid = 0x0104
buffer[3] = 2; // device id light = 0x0002
buffer[4] = 0; // device id light = 0x0002
buffer[5] = 0; // version flags
buffer[6] = 2; // light input cluster count
buffer[7] = 0; // cluster 0 is input
buffer[8] = 1; // cluster 1 is input
buffer[9] = 1; // light output cluster count
buffer[10] = 0; // cluster 0 is output
m_lightlampDlg->hZigBee->ZDO_SET_request( ZIB_CONFIG_SIMPLE_DESCRIPTOR, 11, buffer );
m_lightlampDlg->m_Status.SetWindowText( "Setting the Simple Descriptor" ); // Tell the user
break;
case ZIB_CONFIG_SIMPLE_DESCRIPTOR:
// Have successfully Set the Simple Descriptor.
// Now start the stack
m_lightlampDlg->hZigBee->ZDO_START_request( );
m_lightlampDlg->OperatingState = STATE_START;
if (m_lightlampDlg->DevType == 0) m_lightlampDlg->m_Status.SetWindowText( "Starting a Network" );
else m_lightlampDlg->m_Status.SetWindowText( "Joining a Network" ); // Tell the user
break;
default:
break;
}
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee ZDO_RESET_Confirm Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::ZDO_RESET_confirm( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char Status = msg[2];
/* ============== Created Parameters ============== */
if ( Status != 0 )
{
// Reset Error
m_lightlampDlg->OperatingState = STATE_FAIL;
m_lightlampDlg->m_Status.SetWindowText( "Reset Failed" ); // Tell the user
}
else
{
// Next Set the PANId
m_lightlampDlg->m_Status.SetWindowText( "Setting the PANID" ); // Tell the user
m_lightlampDlg->hZigBee->ZDO_SET_request( ZIB_CONFIG_PANID, 2, m_lightlampDlg->PANId );
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee ZDO_START_Confirm Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::ZDO_START_confirm( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char Status = msg[2];
unsigned short ShortAddr = (msg[4]<<8) & msg[3];
/* ============== Created Parameters ============== */
if ( Status != 0 )
{
// Start Error
m_lightlampDlg->OperatingState = STATE_FAIL;
CString strError;
strError.Format( "Start Failed %02x", Status );
m_lightlampDlg->m_Status.SetWindowText( strError ); // Tell the user
}
else
{
// We are operational
m_lightlampDlg->OperatingState = STATE_RUNNING;
m_lightlampDlg->m_Status.SetWindowText( "Device Started" );
if (m_lightlampDlg->DevType == 2)
{
// End device so poll for data
m_lightlampDlg->hZigBee->ZDO_NLME_SYNC_request( 1 ); // Sync & Track
}
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee AF_INDIRECT_indication Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::AF_INDIRECT_indication( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char DstEndpoint = msg[2];
unsigned char ClusterId = msg[3];
unsigned char AfduLength = msg[4];
unsigned char* Afdu = &msg[5];
unsigned char WasBroadcast = msg[5+AfduLength];
unsigned char SecurityStatus = msg[6+AfduLength];
/* ============== Created Parameters ============== */
if ( ( Afdu[0] == 0x21 ) &&
( Afdu[2] == 4 ) &&
( Afdu[3] == 1 ) &&
( Afdu[4] == 0 ) &&
( Afdu[5] == 0 ))
{
// Lighting Move to Level Command
if ( Afdu[6] == 0 )
{
// Switch Off
m_lightlampDlg->m_Lamp.SetBitmap( nBitmapOff.operator HBITMAP() );
m_lightlampDlg->m_Status.SetWindowText( "Lamp Off" ); // Tell user
}
else
{
// Switch On
m_lightlampDlg->m_Lamp.SetBitmap( nBitmapOn.operator HBITMAP() );
m_lightlampDlg->m_Status.SetWindowText( "Lamp On" ); // Tell user
}
}
else
{
m_lightlampDlg->m_Status.SetWindowText( "Indirect Data Mismatch" ); // Tell user
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee ZDO_END_DEVICE_BIND_confirm Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::ZDO_END_DEVICE_BIND_confirm( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char Status = msg[2];
/* ============== Created Parameters ============== */
if ( Status != 0 )
{
// Bind Error
m_lightlampDlg->m_Status.SetWindowText( "Bind Failed" ); // Tell user
}
else
{
// BIND OK
m_lightlampDlg->m_Status.SetWindowText( "Bind Succeeded" ); // Tell user
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}
/*
** ============================================================================
**
** FUNCTION NAME:
** ZigBee ZDO_NLME_SYNC_confirm Callback
**
** ============================================================================
*/
LRESULT ClightlampDlg::ZDO_NLME_SYNC_confirm( WPARAM wParam, LPARAM lParam)
{
unsigned char* msg;
unsigned char msglength = (unsigned char) wParam;
msg = (unsigned char*) lParam;
/* ============== Create Parameters ============== */
unsigned char Status = msg[2];
/* ============== Created Parameters ============== */
if ( Status != 0 )
{
// Sync Error
m_lightlampDlg->m_Status.SetWindowText( "Sync Failed" ); // Tell user
}
delete [] msg; // Tidy up the memory associated with this message
return 0;
}