Using Alternative Storage Media
2025-12-10
Written by: xiaobin
Remember, a data object is a COM object that implements the IDataObject interface.

MFC’s OLE clipboard support is concentrated in two classes.
The first, COleDataSource, models the provider side of clipboard operations.
The second, COleDataObject, models the consumer side.
Add the following to the InitInstance() in <ProjName.cpp>:
// Initialize OLE libraries
if (!AfxOleInit())
{
AfxMessageBox(_T("OLE initialization failed. Make sure that the OLE libraries are the correct version.")); // IDP_OLE_INIT_FAILED
return FALSE;
}
Resolving the “CoInitialize has not been called”.
Two structures play key roles in the operation of SetData and GetData:
CFile provider:
USES_CONVERSION; // A2W usage
char szText[] = "Hello, world";
TCHAR szPath[MAX_PATH], szFileName[MAX_PATH];
::GetTempPath(sizeof(szPath) / sizeof(TCHAR), szPath);
::GetTempFileName(szPath, _T("tmp"), 0, szFileName);
CFile file;
if (file.Open(szFileName, CFile::modeCreate | CFile::modeWrite)) {
file.Write(szText, ::lstrlen(A2W(szText)) + 1);
file.Close();
LPWSTR pwszFileName = (LPWSTR) ::CoTaskMemAlloc(MAX_PATH * sizeof(WCHAR));
#ifdef UNICODE
::lstrcpy(pwszFileName, szFileName);
#else
::MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, szFileName, -1, pwszFileName, MAX_PATH);
#endif
FORMATETC fe = {
CF_TEXT, NULL, DVASPECT_CONTENT, -1, TYMED_FILE
};
STGMEDIUM stgm;
stgm.tymed = TYMED_FILE;
stgm.lpszFileName = pwszFileName;
stgm.pUnkForRelease = NULL;
COleDataSource* pods = new COleDataSource;
pods->CacheData(CF_TEXT, &stgm, &fe);
pods->SetClipboard();
}
char szText[BUFLEN];
STGMEDIUM stgm;
FORMATETC fe = {
CF_TEXT, NULL, DVASPECT_CONTENT, -1, TYMED_FILE
};
COleDataObject odo;
odo.AttachClipboard();
if (odo.GetData(CF_TEXT, &stgm, &fe) && stgm.tymed == TYMED_FILE) {
TCHAR szFileName[MAX_PATH];
#ifdef UNICODE
::lstrcpy(szFileName, stgm.lpszFileName);
#else
::WideCharToMultiByte(CP_ACP, 0, stgm.lpszFileName,
-1, szFileName, sizeof(szFileName) / sizeof(TCHAR), NULL, NULL);
#endif
CFile file;
if (file.Open(szFileName, CFile::modeRead)) {
ULONGLONG ulSize = file.GetLength();
if (ulSize < BUFLEN)
file.Read(szText, (UINT)ulSize);
file.Close();
}
::ReleaseStgMedium(&stgm);
}
Macro define:
#define BUFLEN 4096