Introduction
The Eye4Software GPS toolkit allows software developers to add GPS functionality to their own programs without the need to have any knowledge on serial communications and GPS protocols like RS-232 and NMEA0183.
The product can be used in many programming environments, such as Visual Basic, Visual C++, Visual Studio.Net, Borland C++ Builder, Borland Delphi and VBA, but also web oriented applications such as ASP, ASP.NET and PHP, and all other programming environments that support ActiveX.
Prerequisites
First you must have Visual C++ and the Eye4Software GPS Component installed on your computer.
We will use Visual C++ 6.0 in this document, but all versions from 6.0 and up can be used.
You can download the Eye4Software GPS Component
here.
Creating the project
Start the Visual C++ IDE, and select the "New" option from the "File" menu.
The "New Project" dialog now appears, you can use the dialog to enter the name of your product. Select "Win32 Console Application" if you wish to create a console application, or select the "MFC AppWizard" option to create a project with a GUI.
Copy the include files
In order to declare and create the objects from your Visual C++ application, you need to include the include files of the ActiveX control. You can create an include folder in your project folder where you store these files. These files can be found in the "Samples\Visual C++\Include" folder from the installation directory.
Declare and create the object(s)
Once you copied the include files, you have to declare these files in your source code like this:
#include "include\GpsCtrl.h"
#include "include\GpsConstantsX.h"
#include "include\GpsCtrl_i.c"
You can also include the ".c" file in your project instead of using the #include directive for this file.
The objects can be declared in your code like this:
IGps * m_pGps;
You can create the m_pGps instance of the object like this:
CoCreateInstance ( CLSID_Gps, NULL, CLSCTX_INPROC_SERVER, IID_IGps, (void**) &m_pGps );
The m_pGps pointer should not be zero, if this is the case, creation of the instance has failed. In this case please check the following:
- Is the GpsCtrl.dll component copieed and registered on this computer;
- Did you call CoInitialize () or AfxOleInit () in your project;
- Did you install the correct DLL for the OS used (X86/x64/PocketPC).
The source code
Below you can find the sourcecode from the Visual C++ demo as shipped with the project.
#include "stdafx.h"
/////////////////////////////////////////////////////////////////////////////
#include "..\include\GpsConstantsX.h"
#include "..\include\GpsCtrl.h"
/////////////////////////////////////////////////////////////////////////////
#include "Demo.h"
#include "DemoDlg.h"
/////////////////////////////////////////////////////////////////////////////
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
CDemoDlg::CDemoDlg(CWnd* pParent) : CDialog(CDemoDlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CDemoDlg)
m_bCheckCRC = FALSE;
m_bCheckLogData = FALSE;
m_strAltitude = _T("");
m_strCourse = _T("");
m_strGpsFix = _T("");
m_strLatitude = _T("");
m_strLongitude = _T("");
m_strLogfile = _T("");
m_strResult = _T("");
m_strGpsSats = _T("");
m_strSpeed = _T("");
m_strTime = _T("");
//}}AFX_DATA_INIT
HRESULT hr = CoCreateInstance ( CLSID_Gps, NULL, CLSCTX_INPROC_SERVER, IID_IGps, (void**) &m_pGps );
m_bStarted = FALSE;
if( ! SUCCEEDED ( hr ) )
{
m_pGps = NULL;
return;
}
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
/////////////////////////////////////////////////////////////////////////////
CDemoDlg::~CDemoDlg ()
{
if ( m_pGps )
{
m_pGps->Close ();
m_pGps->Release ();
}
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CDemoDlg)
DDX_Control(pDX, IDC_LIST_SATS, m_listSats);
DDX_Control(pDX, IDC_COMBO_PORT, m_comboPort);
DDX_Control(pDX, IDC_COMBO_BAUDRATE, m_comboBaudrate);
DDX_Check(pDX, IDC_CHECK_CRC, m_bCheckCRC);
DDX_Check(pDX, IDC_CHECK_LOGDATA, m_bCheckLogData);
DDX_Text(pDX, IDC_EDIT_ALTITUDE, m_strAltitude);
DDX_Text(pDX, IDC_EDIT_COURSE, m_strCourse);
DDX_Text(pDX, IDC_EDIT_FIX, m_strGpsFix);
DDX_Text(pDX, IDC_EDIT_LATITUDE, m_strLatitude);
DDX_Text(pDX, IDC_EDIT_LONGITUDE, m_strLongitude);
DDX_Text(pDX, IDC_EDIT_LOGFILE, m_strLogfile);
DDX_Text(pDX, IDC_EDIT_RESULT, m_strResult);
DDX_Text(pDX, IDC_EDIT_SATS, m_strGpsSats);
DDX_Text(pDX, IDC_EDIT_SPEED, m_strSpeed);
DDX_Text(pDX, IDC_EDIT_TIME, m_strTime);
//}}AFX_DATA_MAP
}
/////////////////////////////////////////////////////////////////////////////
BEGIN_MESSAGE_MAP(CDemoDlg, CDialog)
//{{AFX_MSG_MAP(CDemoDlg)
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_BUTTON_START, OnButtonStart)
ON_BN_CLICKED(IDC_BUTTON_STOP, OnButtonStop)
ON_BN_CLICKED(IDC_BUTTON_BROWSE, OnButtonBrowse)
ON_BN_CLICKED(IDC_BUTTON_VIEW, OnButtonView)
ON_WM_TIMER()
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
LONG CDemoDlg::GetLastResult ()
{
LONG lResult = 0L;
BSTR bstrResult = NULL;
if ( m_pGps )
{
m_pGps->get_LastError ( &lResult );
m_pGps->get_LastErrorDescription ( &bstrResult );
if ( bstrResult )
{
m_strResult.Format ( _T("%ld (%ls)"), lResult, bstrResult );
SysFreeString ( bstrResult );
}
}
UpdateData ( FALSE );
return lResult;
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::SetLogFile ()
{
TCHAR tszTempPath [ MAX_PATH + 1 ];
// Get Temp Folder
GetTempPath ( MAX_PATH, tszTempPath );
// Add trailing backslash
if( tszTempPath [ 0 ] == '\0' || tszTempPath [ _tcslen ( tszTempPath ) - 1 ] != '\\' )
{
_tcscat( tszTempPath, _T("\\") );
}
// Set logfile
m_strLogfile = tszTempPath;
m_strLogfile += _T("GpsLog.txt");
UpdateData ( FALSE );
}
/////////////////////////////////////////////////////////////////////////////
BOOL CDemoDlg::OnInitDialog()
{
LONG lPort = 0L;
CString strPort = _T("");
CDialog::OnInitDialog();
SetIcon(m_hIcon, TRUE);
SetIcon(m_hIcon, FALSE);
for ( lPort = 1 ; lPort <= 16 ; lPort++ )
{
strPort.Format ( _T("COM%ld"), lPort );
m_comboPort.AddString ( strPort );
}
m_comboPort.SetCurSel ( 0 );
m_comboBaudrate.AddString ( _T("1200" ) );
m_comboBaudrate.AddString ( _T("2400" ) );
m_comboBaudrate.AddString ( _T("4800" ) );
m_comboBaudrate.AddString ( _T("9600" ) );
m_comboBaudrate.AddString ( _T("19200" ) );
m_comboBaudrate.AddString ( _T("38400" ) );
m_comboBaudrate.AddString ( _T("57600" ) );
m_comboBaudrate.AddString ( _T("115200") );
m_comboBaudrate.SetCurSel ( 2 );
SetupListCtrl ();
EnableControls ();
SetTimer ( 1, 1000L, NULL );
SetLogFile ();
return TRUE;
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this);
SendMessage ( WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
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;
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}
/////////////////////////////////////////////////////////////////////////////
HCURSOR CDemoDlg::OnQueryDragIcon()
{
return (HCURSOR) m_hIcon;
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::SetupListCtrl ()
{
m_listSats.SetExtendedStyle ( LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT );
LVCOLUMN lvCol;
ZeroMemory (&lvCol,sizeof(LVCOLUMN));
lvCol.mask = LVCF_TEXT|LVCF_WIDTH;
lvCol.cx = 90;
lvCol.pszText = _T("PRN#");
m_listSats.InsertColumn ( 0,&lvCol);
lvCol.mask = LVCF_TEXT|LVCF_WIDTH;
lvCol.cx = 90;
lvCol.pszText = _T("Elevation");
m_listSats.InsertColumn ( 1,&lvCol);
lvCol.mask = LVCF_TEXT|LVCF_WIDTH;
lvCol.cx = 90;
lvCol.pszText = _T("Azimuth");
m_listSats.InsertColumn ( 2,&lvCol);
lvCol.mask = LVCF_TEXT|LVCF_WIDTH;
lvCol.cx = 90;
lvCol.pszText = _T("SNR (db)");
m_listSats.InsertColumn ( 3,&lvCol);
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnButtonStart()
{
BSTR bstrTemp = NULL;
CString strTemp = _T("");
if ( m_pGps == NULL )
{
AfxMessageBox ( _T("GpsCtrl.dll failed to load.\nCheck if the file is
present on this computer\nand reregister it using REGSVR32" ) );
}
UpdateData ( TRUE );
// Set Serial Port
m_pGps->put_DeviceSerialPort ( m_comboPort.GetCurSel () + 1L );
// Set Serial Baudrate
m_comboBaudrate.GetLBText ( m_comboBaudrate.GetCurSel (), strTemp );
m_pGps->put_DeviceBaudrate ( _tcstol ( strTemp, NULL, 10 ) );
// Set Logfile
bstrTemp = m_strLogfile.AllocSysString ();
m_pGps->put_LogFile ( bstrTemp );
SysFreeString ( bstrTemp );
// Set CRC Checking
m_pGps->put_EnableChecksum ( m_bCheckCRC );
// Set NMEA logging
m_pGps->put_LogGpsData ( m_bCheckLogData );
// Set Units
m_pGps->put_UnitsSpeed ( GPS_SPEED_KNOTS );
m_pGps->put_UnitsAltitude ( GPS_ALTITUDE_FEET );
// Set Lat-Lon format
m_pGps->put_LatLonStringFormat ( GPS_LATLONFORMAT_DM );
// Start !
m_pGps->Open ();
// Get Result and set controls
if ( GetLastResult () == 0L )
{
m_bStarted = TRUE;
EnableControls ();
}
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnButtonStop()
{
if ( m_pGps == NULL )
{
AfxMessageBox ( _T("GpsCtrl.dll failed to load.\nCheck if the file is
present on this computer\nand reregister it using REGSVR32" ) );
}
m_bStarted = FALSE;
m_pGps->Close ();
EnableControls ();
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::EnableControls ()
{
GetDlgItem ( IDC_BUTTON_START )->EnableWindow ( !m_bStarted );
GetDlgItem ( IDC_BUTTON_STOP )->EnableWindow ( m_bStarted );
GetDlgItem ( IDC_CHECK_CRC )->EnableWindow ( !m_bStarted );
GetDlgItem ( IDC_CHECK_LOGDATA )->EnableWindow ( !m_bStarted );
GetDlgItem ( IDC_COMBO_PORT )->EnableWindow ( !m_bStarted );
GetDlgItem ( IDC_COMBO_BAUDRATE )->EnableWindow ( !m_bStarted );
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnButtonBrowse()
{
CFileDialog cfd ( FALSE, NULL, 0, NULL, _T("All Files (*.*)|*.*||\0\0") );
UpdateData ( TRUE );
cfd.m_ofn.lpstrInitialDir = m_strLogfile;
if ( cfd.DoModal () == IDOK )
{
m_strLogfile = cfd.GetPathName ();
}
UpdateData ( FALSE );
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnButtonView()
{
UpdateData();
if ( m_strLogfile.GetLength () )
{
if ( ShellExecute ( NULL, _T("open"), m_strLogfile, NULL, NULL, SW_SHOWDEFAULT ) == INVALID_HANDLE_VALUE )
{
AfxMessageBox ( _T("Failed to display logfile"), MB_OK );
}
}
}
/////////////////////////////////////////////////////////////////////////////
void CDemoDlg::OnTimer(UINT nIDEvent)
{
BSTR bstrValue = NULL;
LONG lValue = 0L;
LONG lResult = 0L;
DOUBLE dblValue = 0L;
INT nIndex = 0L;
BOOL bUsed = FALSE;
CString strTemp = _T("");
VARIANT vtValue;
VariantInit ( &vtValue );
IGpsSatelliteInfo * pSat = NULL;
if ( nIDEvent == 1 )
{
if ( m_bStarted )
{
UpdateData ( TRUE );
LockWindowUpdate ();
m_pGps->get_gpsLatitudeString ( &bstrValue );
m_strLatitude = bstrValue;
SysFreeString ( bstrValue );
m_pGps->get_gpsLongitudeString ( &bstrValue );
m_strLongitude = bstrValue;
SysFreeString ( bstrValue );
m_pGps->get_gpsSpeed ( &dblValue );
m_strSpeed.Format ( _T("%3.1f knots"), dblValue );
m_pGps->get_gpsCourse ( &dblValue );
m_strCourse.Format ( _T("%3.0f degrees"), dblValue );
m_pGps->get_gpsAltitude ( &dblValue );
m_strAltitude.Format ( _T("%3.0f feet"), dblValue );
m_pGps->get_gpsTimeString ( &bstrValue );
m_strTime = bstrValue;
SysFreeString ( bstrValue );
m_pGps->get_gpsQuality ( &lValue );
m_strGpsFix.Format ( _T("%ld"), lValue );
m_pGps->get_gpsSatellites ( &lValue );
m_strGpsSats.Format ( _T("%ld"), lValue );
// Display information about satellites used for fix
m_listSats.DeleteAllItems ();
m_pGps->GetFirstSatellite ( &vtValue );
m_pGps->get_LastError ( &lResult );
while ( lResult == 0L )
{
pSat = ( vtValue.vt == VT_DISPATCH ) ? ( IGpsSatelliteInfo * ) vtValue.pdispVal : NULL;
if ( pSat )
{
pSat->get_UsedForFix ( &bUsed );
if ( bUsed )
{
// Insert item with satellite PRN number
pSat->get_ID ( &lValue );
strTemp.Format ( _T("%ld"), lValue );
m_listSats.InsertItem ( nIndex, strTemp, 0 );
// Set Elevation
pSat->get_Elevation ( &lValue );
strTemp.Format ( _T("%ld"), lValue );
m_listSats.SetItemText ( nIndex, 1, strTemp );
// Set Azimuth
pSat->get_Azimuth ( &lValue );
strTemp.Format ( _T("%ld"), lValue );
m_listSats.SetItemText ( nIndex, 2, strTemp );
// Set SignalNoise ratio
pSat->get_SignalNoiseRatio ( &lValue );
strTemp.Format ( _T("%ld"), lValue );
m_listSats.SetItemText ( nIndex, 3, strTemp );
nIndex++;
}
VariantClear ( &vtValue );
}
// Get Next Satellite
m_pGps->GetNextSatellite ( &vtValue );
m_pGps->get_LastError ( &lResult );
}
UnlockWindowUpdate ();
UpdateData ( FALSE );
}
}
CDialog::OnTimer(nIDEvent);
}
/////////////////////////////////////////////////////////////////////////////