Skip to content

Instantly share code, notes, and snippets.

@mokapyo
Created June 24, 2017 15:17
Show Gist options
  • Save mokapyo/c99f4f431a624f26a01521fb96f1b57a to your computer and use it in GitHub Desktop.
Save mokapyo/c99f4f431a624f26a01521fb96f1b57a to your computer and use it in GitHub Desktop.
#include <Ole2.h>
#include <atlstr.h>
#include "CExcelEdit.h"
class CExcelEdit {
public:
CExcelEdit(CString FilePath, CString SheetName);
~CExcelEdit();
CString ReadStr(CString cell);
DOUBLE ReadNum(CString cell);
bool WriteStr(CString cell, CString input);
bool WriteNum(CString cell, DOUBLE input);
private:
IDispatch *m_pXlApp;
IDispatch *m_pXlBooks;
IDispatch *m_pXlBook;
IDispatch *m_pXlSheets;
IDispatch *m_pXlSheet;
};
// AutoWrap() - Automation helper function...
HRESULT AutoWrap(int autoType, VARIANT *pvResult, IDispatch *pDisp, LPOLESTR ptName, int cArgs...) {
// Begin variable-argument list...
va_list marker;
va_start(marker, cArgs);
if (!pDisp) {
MessageBox(NULL, _T("NULL IDispatch passed to AutoWrap()"), _T("Error"), 0x10010);
_exit(0);
}
// Variables used...
DISPPARAMS dp = { NULL, NULL, 0, 0 };
DISPID dispidNamed = DISPID_PROPERTYPUT;
DISPID dispID;
HRESULT hr;
TCHAR buf[200];
char szName[200];
// Convert down to ANSI
WideCharToMultiByte(CP_ACP, 0, ptName, -1, szName, 256, NULL, NULL);
// Get DISPID for name passed...
hr = pDisp->GetIDsOfNames(IID_NULL, &ptName, 1, LOCALE_USER_DEFAULT, &dispID);
if (FAILED(hr)) {
MessageBox(NULL, _T("Dispatch::GetIDsOfNames failed"), _T("AutoWrap()"), 0x10010);
_exit(0);
return hr;
}
// Allocate memory for arguments...
VARIANT *pArgs = new VARIANT[cArgs + 1];
// Extract arguments...
for (int i = 0; i<cArgs; i++) {
pArgs[i] = va_arg(marker, VARIANT);
}
// Build DISPPARAMS
dp.cArgs = cArgs;
dp.rgvarg = pArgs;
// Handle special-case for property-puts!
if (autoType & DISPATCH_PROPERTYPUT) {
dp.cNamedArgs = 1;
dp.rgdispidNamedArgs = &dispidNamed;
}
// Make the call!
hr = pDisp->Invoke(dispID, IID_NULL, LOCALE_SYSTEM_DEFAULT, autoType, &dp, pvResult, NULL, NULL);
if (FAILED(hr)) {
MessageBox(NULL, buf, _T("IDispatch::Invoke failed"), 0x10010);
_exit(0);
return hr;
}
// End variable-argument section...
va_end(marker);
delete[] pArgs;
return hr;
}
CExcelEdit::CExcelEdit(CString FilePath, CString SheetName) {
// COMの初期化
CoInitialize(NULL);
// CLSID取得
CLSID clsid;
HRESULT hr = CLSIDFromProgID(L"Excel.Application", &clsid);
if (FAILED(hr)) {
MessageBox(NULL, _T("CLSIDFromProgID() failed"), _T("Error"), MB_OK);
return;
}
// IDispatch取得
*m_pXlApp;
hr = CoCreateInstance(clsid, NULL, CLSCTX_LOCAL_SERVER, IID_IDispatch, (void**)&m_pXlApp);
if (FAILED(hr)) {
MessageBox(NULL, _T("CoCreateInstance() failed"), _T("Error"), MB_OK);
return;
}
// Excel画面を表示(デバッグ用('ω')ノ) ---------------------------------
/*
VARIANT x;
x.vt = VT_I4;
x.lVal = 1;
AutoWrap(DISPATCH_PROPERTYPUT, NULL, m_pXlApp, L"Visible", 1, x);
*/
// ----------------------------------------------------------------------------------------------------
// Get Workbooks collection
{
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlApp, L"Workbooks", 0);
m_pXlBooks = result.pdispVal;
}
// 指定ファイルオープン
{
VARIANT parm;
VARIANT result;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(FilePath);
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlBooks, L"Open", 1, parm);
m_pXlBook = result.pdispVal;
}
// シートの設定
{
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlBook, L"WorkSheets", 0);
m_pXlSheets = result.pdispVal;
}
// シート変更
{
VARIANT result;
VariantInit(&result);
VARIANT parm;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(SheetName);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlSheets, L"Item", 1, parm);
m_pXlSheet = result.pdispVal;
}
}
CExcelEdit::~CExcelEdit() {
// Tell Excel to quit (i.e. App.Quit)
AutoWrap(DISPATCH_METHOD, NULL, m_pXlApp, L"Quit", 0);
// Release references...
m_pXlBook->Release();
m_pXlBooks->Release();
m_pXlApp->Release();
// Uninitialize COM for this thread...
CoUninitialize();
}
CString CExcelEdit::ReadStr(CString cell) {
// 取得するセルの指定
IDispatch *pXlRange;
{
VARIANT parm;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(cell);
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlSheet, L"Range", 1, parm);
VariantClear(&parm);
pXlRange = result.pdispVal;
}
// 値の取得
VARIANT result2;
VariantInit(&result2);
AutoWrap(DISPATCH_PROPERTYGET, &result2, pXlRange, L"Value2", 0);
CString RetStr = result2.bstrVal;
return RetStr;
}
DOUBLE CExcelEdit::ReadNum(CString cell) {
// 取得するセルの指定
IDispatch *pXlRange;
{
VARIANT parm;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(cell);
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlSheet, L"Range", 1, parm);
VariantClear(&parm);
pXlRange = result.pdispVal;
}
// 値の取得
VARIANT result2;
VariantInit(&result2);
AutoWrap(DISPATCH_PROPERTYGET, &result2, pXlRange, L"Value2", 0);
DOUBLE RetStr = result2.dblVal;
return RetStr;
}
bool CExcelEdit::WriteStr(CString cell, CString input) {
IDispatch *pXlRange;
{
VARIANT parm;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(cell);
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlSheet, L"Range", 1, parm);
VariantClear(&parm);
pXlRange = result.pdispVal;
}
VARIANT arr;
arr.vt = VT_BSTR;
arr.bstrVal = ::SysAllocString(input);
// 作成した値を代入
AutoWrap(DISPATCH_PROPERTYPUT, NULL, pXlRange, L"Value", 1, arr);
// ファイルを上書き保存
AutoWrap(DISPATCH_PROPERTYGET, NULL, m_pXlBook, L"Save", 0);
// RangeのDispatchを解放
pXlRange->Release();
return true;
}
bool CExcelEdit::WriteNum(CString cell, DOUBLE input) {
IDispatch *pXlRange;
{
VARIANT parm;
parm.vt = VT_BSTR;
parm.bstrVal = ::SysAllocString(cell);
VARIANT result;
VariantInit(&result);
AutoWrap(DISPATCH_PROPERTYGET, &result, m_pXlSheet, L"Range", 1, parm);
VariantClear(&parm);
pXlRange = result.pdispVal;
}
VARIANT arr;
arr.vt = VT_R8;
arr.dblVal = input;
// 作成した値を代入
AutoWrap(DISPATCH_PROPERTYPUT, NULL, pXlRange, L"Value", 1, arr);
// ファイルを上書き保存
AutoWrap(DISPATCH_PROPERTYGET, NULL, m_pXlBook, L"Save", 0);
// RangeのDispatchを解放
pXlRange->Release();
return true;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment