Importing Barcode Xpress as a COM Object
Barcode Xpress can be used as an ActiveX control in development environments that provide container support like Visual Basic or Visual C++. In this case, the Barcode Xpress control is placed on a form or dialog box.
You can also import Barcode Xpress as a COM object in development environments like Visual C++. In this case, Barcode Xpress is not restricted to a dialog box and it does not require container support. The following discussion assumes that your development environment is Visual C++.
Starting with version 5 of Visual C++, Microsoft has provided support for a new #import compiler directive that enables developers to import components directly as native COM objects, by-passing the ActiveX trappings. The following is a quote from a brief section of the Fourth Edition of Inside Visual C++ (Microsoft Press): "The #import directive is the future of COM programming. With each new version of Visual C++, you’ll see COM features moving into the compiler…"
How to use Barcode Xpress as an Imported COM Object in Visual C++.
References made to files in the Visual C++ sample, ReadBarcodeFromDIB, and pertinent statements are shown in boldface.
1. #importing a control into Visual C++
Importing a control via the #import directive is a simple process. The #import directive line can be added to the Stdafx.h file to provide the appropriate functionality to all source files in the project. The following example shows the #import directive used in the Stdafx.h file from the ReadBarcodeFromDIB project:
C++ ReadBarcodeFromDIB Sample Project |
Copy Code
|
// stdafx.h : include file for standard system include files,
// or project specific include files that are used frequently, but
// are changed infrequently
#if !defined(AFX_STDAFX_H__73AF9569_D12A_49D1_82D7_9662053EE69A__INCLUDED_)
#define AFX_STDAFX_H__73AF9569_D12A_49D1_82D7_9662053EE69A__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers
#include <afxwin.h> // MFC core and standard components
#include <afxext.h> // MFC extensions
#include <afxdisp.h> // MFC Automation classes
#include <afxdtctl.h> // MFC support for Internet Explorer 4 Common Controls
#ifndef _AFX_NO_AFXCMN_SUPPORT
#include <afxcmn.h> // MFC support for Windows Common Controls
#endif // _AFX_NO_AFXCMN_SUPPORT
#import "Accusoft.ImagXpress13.ActiveX.dll"
#import "Accusoft.BarcodeXpress13.ActiveX.dll"
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_STDAFX_H__73AF9569_D12A_49D1_82D7_9662053EE69A__INCLUDED_)
|
The #import directive simply points to the Barcode Xpress control. When the Barcode IDL-defined interfaces. To use this COM object, you simply create an instance of the interface you want and then call methods directly by using this instance pointer.
2. Define a pointer to the COM object
After the #import directive is added, a pointer to the Barcode Xpress COM object must be defined. In the ReadBarcodeFromDIB project, the pointer is called and it is implemented in the ReadBarcodeFromDIBDlg.h file as follows:
C++ example to define a pointer to the COM object |
Copy Code
|
using namespace AccusoftBarcodeXpress13;
#include "..\Include\BarcodeXpress13_Events.h"
...
class CReadBarcodeFromDIBDlg : public CDialog
{
private:
...
//ImagXpress pointers
CImagXpress* m_ppCImagXpress;
IImagXpressPtr m_pImagXpress;
CBarcodeXpress* m_ppIBarcodeXpress;
IBarcodeXpressPtr m_pBarcodeXpress;
...
|
3. Initialize COM
The COM library must be initialized before COM functions can be called and it must be closed before the program exits. This is illustrated in the ReadBarcodeFromDIB.cpp file as follows:
C++ example to initialize and close COM library |
Copy Code
|
/////////////////////////////////////////////////////////////////////////////
// CReadBarcodeFromDIBApp initialization
BOOL CReadBarcodeFromDIBApp::InitInstance()
{
// Initialize the COM library on the current apartment and identify
// the currency model as single-thread apartment (STA). Applications
// must initialize the COM
// library before they can call COM library functions other than
// CoGetMalloc and memory allocation functions.
HRESULT hRes = CoInitialize(NULL);
AfxEnableControlContainer();
// Standard initialization
// If you are not using these features and wish to reduce the size
// of your final executable, you should remove from the following
// the specific initialization routines you do not need.
#ifdef _AFXDLL
Enable3dControls(); // Call this when using MFC in a shared DLL
#else
Enable3dControlsStatic(); // Call this when linking to MFC statically
#endif
CReadBarcodeFromDIBDlg dlg;
m_pMainWnd = &dlg;
int nResponse = dlg.DoModal();
if (nResponse == IDOK)
{
// TODO: Place code here to handle when the dialog is
// dismissed with OK
}
else if (nResponse == IDCANCEL)
{
// TODO: Place code here to handle when the dialog is
// dismissed with Cancel
}
// Closes the COM library on the current apartment,
// unloads all DLLs loaded by apartment,
// frees any other resources that the apartment maintains, and
// forces all RPC connections on the apartment to close.
CoUninitialize();
// Since the dialog has been closed, return FALSE so that we exit the
// application, rather than start the application's message pump.
return FALSE;
}
|
4. Create the Barcode Xpress COM Object
To use Barcode Xpress, an instance of the Barcode Xpress COM object must be created. After the object is created, the object’s properties and methods can be used to create your scanning application. In the ReadBarcodeFromDIB project, the COM object is created in the ReadBarcodeFromDIBDlg.cpp file as follows:
Before you distribute applications that use the Barcode Xpress COM object, you need to edit the BarcodeXpress12_Open.cpp file and change the values passed to SetSolutionName, SetSolutionKey, and (if applicable) SetOEMLicenseKey. Obtain distribution codes from Accusoft.
Example to create the Barcode Xpress object |
Copy Code
|
/////////////////////////////////////////////////////////////////////////////
// CReadBarcodeFromDIBDlg message handlers
BOOL CReadBarcodeFromDIBDlg::OnInitDialog()
{
CDialog::OnInitDialog();
// 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
// TODO: Add extra initialization here
CWnd* pControl = NULL;
pControl = GetDlgItem(Description);
if (pControl)
{
pControl->SetWindowText(lpctstrDescription);
}
CRect oIXArea;
oIXArea.left = 25;
oIXArea.top = 215;
oIXArea.right = 725;
oIXArea.bottom = 636;
// Create an ImagXpress Object
m_ppCImagXpress = new CImagXpress(this, 1, (long) m_hWnd,
oIXArea.left, oIXArea.top, oIXArea.Width(), oIXArea.Height());
m_pImagXpress = m_ppCImagXpress->pImagXpress;
m_pImagXpress->PutCtlVisible(true);
m_pImagXpress->AutoSize = ISIZE_BestFit;
m_pImagXpress->ScrollBars = SB_Both;
m_pImagXpress->MenuSetEnabled(Menu_Context,TOOL_None, true);
// **Initialize Barcode. You must call BC_Open before
// **creating the first Barcode Xpress COM object. You cannot distribute applications using
// **Barcode Xpress COM objects without valid unlock codes.
// Create a Barcode Xpress class object. The Barcode Xpress
// class object automatically creates a Barcode Xpress
// COM object.
m_ppIBarcodeXpress = new CBarcodeXpress(this, 1);
// The SetSolutionName, SetSolutionKey and possibly the SetOEMLicenseKey method must be
// called to distribute the runtime. Note that the SolutionName, SolutionKey and
// OEMLicenseKey values shown below are only examples.
//
//m_pBarcodeXpress->SetSolutionName("YourSolutionName");
//m_pBarcodeXpress->SetSolutionKey(12345, 12345, 12345, 12345);
//m_pBarcodeXpress->SetOEMLicenseKey("1.0.AStringForOEMLicensingContactAccusoftSalesForMoreInformation...");
//
//m_pImagXpress->SetSolutionName("YourSolutionName");
//m_pImagXpress->SetSolutionKey(12345, 12345, 12345, 12345);
//m_pImagXpress->SetOEMLicenseKey("1.0.AStringForOEMLicensingContactAccusoftSalesForMoreInformation...");
// Get the pointer to the created Barcode Xpress Barcode COM object.
// This is the pointer that you will use to access Barcode Xpress
// Barcode properties and methods.
m_pBarcodeXpress = m_ppIBarcodeXpress->pBarcodeXpress;
// Close the Barcode Xpress Barcode initialization.
// You must call this AFTER creating the first Barcode Xpress Barcode
// COM object
m_1D.SetCheck(BST_CHECKED);
m_selection = 0;
m_pImagXpress->FileName = "..\\..\\..\\..\\..\\..\\Common\\Images\\Barcode All Supported Types.tif";
return TRUE; // return TRUE unless you set the focus to a control
}
|
The arguments for the CBarcodeXpress constructor are ignored as the Barcode Xpress control does not implement any user interface interaction mechanics.
5. Use the Barcode Xpress COM Object to Set Properties and Call Methods
After an instance of the Barcode Xpress COM object is created, the object can be used to set Barcode Xpress properties and call Barcode Xpress methods. In the ReadBarcodeFromDIB project, this is illustrated in the OnDetectButton function shown below. This function is called when the user clicks the Recognized Barcode button.
C++ example to set Barcode Xpress properties and call methods |
Copy Code
|
void CReadBarcodeFromDIBDlg::OnDetectButton()
{
// TODO: Add your control notification handler code here
// Set barcode classification type based on selected radio button
switch(m_selection)
{
case 0:
{
barcodetype = BC_StyleUnknown; //all 1D barcodes
break;
}
case 1:
{
barcodetype = BC_StylePatchCode; //Patch Code
break;
}
case 2:
{
barcodetype = BC_StyleIntelligentMail; //Intelligent Mail
break;
}
case 3:
{
barcodetype = BC_StylePDF417; //PDF417
break;
}
case 4:
{
barcodetype = BC_StyleDataMatrix; //DataMatrix
break;
}
case 5:
{
barcodetype = BC_StyleRoyalPost4State; //Royal Post
break;
}
case 6:
{
barcodetype = BC_StylePostNet; //Post net
break;
}
case 7:
{
barcodetype = BC_StyleQRCode; //QR
break;
}
case 8:
{
barcodetype = BC_StyleAustralian4State; //Australian Post
break;
}
}
m_pBarcodeXpress->SetBarcodeReaderType(barcodetype);
m_pBarcodeXpress->ImageSource = BC_ImageSourceDIB;
m_pBarcodeXpress->hDIB = m_pImagXpress->CopyDIB();
m_pBarcodeXpress->AnalyzeBC(0,0,0,0);
int numBC = m_pBarcodeXpress->NumBarcodes;
CString bcName;
CString bcResult;
CString result;
CString strBarcodeInformation;
if ((m_pBarcodeXpress->SSError == 0) & (m_pBarcodeXpress->NumBarcodes > 0))
{
int i;
for (i = 0 ; i < numBC ; i++)
{
m_pBarcodeXpress->GetBarcode(i);
bcName = (BSTR) m_pBarcodeXpress->BarcodeCodeName;
bcResult = (BSTR) m_pBarcodeXpress->BarcodeResult;
strBarcodeInformation.FormatMessage(szBarcodeInfoFormat, i, bcResult, bcName);
result += strBarcodeInformation;
}
MessageBox(result,"Barcode Result", MB_OK);
}
else
{
if (m_pBarcodeXpress->SSError != 0)
{
MessageBox("Error #" + m_pBarcodeXpress->SSError,"Error",MB_OK);
}
else
{
MessageBox("No barcodes found","Barcode Result", MB_OK);
}
}
//Must Free the DIB passed into the Analyze method to avoid memory issues
GlobalFree((HGLOBAL)m_pBarcodeXpress->hDIB);
}
|
6. Delete the Barcode Xpress COM Object
The Barcode Xpress COM object must be deleted when it is no longer needed. The object is usually deleted before the application exits. In the ReadBarcodeFromDIB project, the COM object is deleted as follows:
C++ example to delete the COM object |
Copy Code
|
BOOL CReadBarcodeFromDIBDlg::DestroyWindow()
{
// TODO: Add your specialized code here and/or call the base class
CDialog::OnDestroy();
if (m_pImagXpress)
{
m_pImagXpress = NULL;
if (m_ppCImagXpress)
{
delete m_ppCImagXpress;
}
}
if (m_pBarcodeXpress)
{
m_pBarcodeXpress = NULL;
if (m_ppIBarcodeXpress)
{
delete m_ppIBarcodeXpress;
}
}
return CDialog::DestroyWindow();
}
|