[reply]class DownLoadFile
{
#define LOULONG(l) ((ULONG)(((ULONGLONG)(l)) & 0xffffffff))
#define HIULONG(l) ((ULONG)((((ULONGLONG)(l)) >> 32) & 0xffffffff))
#define WM_USER_ENDDOWNLOAD (WM_USER + 1)
#define WM_USER_DISPLAYSTATUS (WM_USER + 2)
#pragma pack(1)
struct DOWNLOADSTATUS
{
ULONG ulProgress;
ULONG ulProgressMax;
ULONG ulStatusCode;
LPCWSTR szStatusText;
};
#pragma pack()
class CBindStatusCallbackImpl : public IBindStatusCallback
{
enum
{
UF_BINDSTATUS_FIRST = BINDSTATUS_FINDINGRESOURCE,
UF_BINDSTATUS_LAST = BINDSTATUS_ACCEPTRANGES
};
public:
CBindStatusCallbackImpl(BackGroundWall* pThiz)
{
m_pThiz = pThiz;
m_ulObjRefCount = 1;
}
// IUnknown methods
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject)
{
TRACE(_T("IUnknown::QueryInterface\n"));
*ppvObject = NULL;
// IUnknown
if (::IsEqualIID(riid, __uuidof(IUnknown)))
{
TRACE(_T("IUnknown::QueryInterface(IUnknown)\n"));
*ppvObject = this;
}
// IBindStatusCallback
else if (::IsEqualIID(riid, __uuidof(IBindStatusCallback)))
{
TRACE(_T("IUnknown::QueryInterface(IBindStatusCallback)\n"));
*ppvObject = static_cast<IBindStatusCallback*>(this);
}
if (*ppvObject)
{
(*reinterpret_cast<LPUNKNOWN*>(ppvObject))->AddRef();
return S_OK;
}
return E_NOINTERFACE;
}
STDMETHOD_(ULONG, AddRef)()
{
TRACE(_T("IUnknown::AddRef\n"));
return ++m_ulObjRefCount;
}
STDMETHOD_(ULONG, Release)()
{
TRACE(_T("IUnknown::Release\n"));
return --m_ulObjRefCount;
}
// IBindStatusCallback methods
STDMETHOD(OnStartBinding)(DWORD, IBinding*)
{
TRACE(_T("IBindStatusCallback::OnStartBinding\n"));
int nRet = m_fileView.Init(m_pThiz->m_strFileName, { 32 * 1024 * 1024UL, 0UL, });
if (nRet != 0)
{
TRACE(_T("Init failure!\n"));
return E_ABORT;
}
return S_OK;
}
STDMETHOD(GetPriority)(LONG*)
{
TRACE(_T("IBindStatusCallback::GetPriority\n"));
return E_NOTIMPL;
}
STDMETHOD(OnLowResource)(DWORD)
{
TRACE(_T("IBindStatusCallback::OnLowResource\n"));
return S_OK;
}
STDMETHOD(OnProgress)(ULONG ulProgress,
ULONG ulProgressMax,
ULONG ulStatusCode,
LPCWSTR szStatusText)
{
#ifdef _DEBUG
static const LPCTSTR plpszStatus[] =
{
_T("BINDSTATUS_FINDINGRESOURCE"), // 1
_T("BINDSTATUS_CONNECTING"),
_T("BINDSTATUS_REDIRECTING"),
_T("BINDSTATUS_BEGINDOWNLOADDATA"),
_T("BINDSTATUS_DOWNLOADINGDATA"),
_T("BINDSTATUS_ENDDOWNLOADDATA"),
_T("BINDSTATUS_BEGINDOWNLOADCOMPONENTS"),
_T("BINDSTATUS_INSTALLINGCOMPONENTS"),
_T("BINDSTATUS_ENDDOWNLOADCOMPONENTS"),
_T("BINDSTATUS_USINGCACHEDCOPY"),
_T("BINDSTATUS_SENDINGREQUEST"),
_T("BINDSTATUS_CLASSIDAVAILABLE"),
_T("BINDSTATUS_MIMETYPEAVAILABLE"),
_T("BINDSTATUS_CACHEFILENAMEAVAILABLE"),
_T("BINDSTATUS_BEGINSYNCOPERATION"),
_T("BINDSTATUS_ENDSYNCOPERATION"),
_T("BINDSTATUS_BEGINUPLOADDATA"),
_T("BINDSTATUS_UPLOADINGDATA"),
_T("BINDSTATUS_ENDUPLOADINGDATA"),
_T("BINDSTATUS_PROTOCOLCLASSID"),
_T("BINDSTATUS_ENCODING"),
_T("BINDSTATUS_VERFIEDMIMETYPEAVAILABLE"),
_T("BINDSTATUS_CLASSINSTALLLOCATION"),
_T("BINDSTATUS_DECODING"),
_T("BINDSTATUS_LOADINGMIMEHANDLER"),
_T("BINDSTATUS_CONTENTDISPOSITIONATTACH"),
_T("BINDSTATUS_FILTERREPORTMIMETYPE"),
_T("BINDSTATUS_CLSIDCANINSTANTIATE"),
_T("BINDSTATUS_IUNKNOWNAVAILABLE"),
_T("BINDSTATUS_DIRECTBIND"),
_T("BINDSTATUS_RAWMIMETYPE"),
_T("BINDSTATUS_PROXYDETECTING"),
_T("BINDSTATUS_ACCEPTRANGES"),
_T("???") // unknown
};
#endif
TRACE(_T("IBindStatusCallback::OnProgress\n"));
TRACE(_T("ulProgress: %lu, ulProgressMax: %lu\n"), ulProgress, ulProgressMax);
TRACE(_T("ulStatusCode: %lu "), ulStatusCode);
if (ulStatusCode < UF_BINDSTATUS_FIRST || ulStatusCode > UF_BINDSTATUS_LAST)
{
ulStatusCode = UF_BINDSTATUS_LAST + 1;
}
#ifdef _DEBUG
TRACE(_T("(%s), szStatusText: %ls\n"), plpszStatus[ulStatusCode - UF_BINDSTATUS_FIRST], szStatusText);
#endif
printf("ulProgress: %lu, ulProgressMax: %lu\n", ulProgress, ulProgressMax);
//if (m_hWnd != NULL)
//{
// // inform the dialog box to display current status, don't use PostMessage
// DOWNLOADSTATUS downloadStatus = { ulProgress, ulProgressMax, ulStatusCode, szStatusText };
// ::PostMessageW(m_hWnd, WM_USER_DISPLAYSTATUS, 0, reinterpret_cast<LPARAM>(&downloadStatus));
//}
//if (m_hEventStop != NULL)
//{
// if (::WaitForSingleObject(m_hEventStop, 0) == WAIT_OBJECT_0)
// {
// TRACE(_T("Canceled.\n"));
// ::PostMessageW(m_hWnd, WM_USER_DISPLAYSTATUS, 0, NULL);
// return E_ABORT; // canceled by the user
// }
//}
return S_OK;
}
STDMETHOD(OnStopBinding)(HRESULT, LPCWSTR)
{
TRACE(_T("IBindStatusCallback::OnStopBinding\n"));
const ULARGE_INTEGER& uiSize = { LOULONG(m_ullSize), HIULONG(m_ullSize), };
m_fileView.Exit(uiSize);
return S_OK;
}
//---
STDMETHOD(GetBindInfo)(DWORD*, BINDINFO*)
{
TRACE(_T("IBindStatusCallback::GetBindInfo\n"));
return S_OK;
}
STDMETHOD(OnDataAvailable)(DWORD grfBSCF, DWORD dwSize, FORMATETC* pformatetc, STGMEDIUM* pstgmed)
{
TRACE(_T("IBindStatusCallback::OnDataAvailable\n"));
//BSCF_FIRSTDATANOTIFICATION = 0x00000001,
//BSCF_INTERMEDIATEDATANOTIFICATION = 0x00000002,
//BSCF_LASTDATANOTIFICATION = 0x00000004,
//有可能为BSCF_FIRSTDATANOTIFICATION, BSCF_FIRSTDATANOTIFICATION & BSCF_LASTDATANOTIFICATION, BSCF_INTERMEDIATEDATANOTIFICATION, BSCF_LASTDATANOTIFICATION
//即可能为一个包、两个包或多个包
ULONG ulReadSize = 0;
if ((grfBSCF & BSCF_FIRSTDATANOTIFICATION) == BSCF_FIRSTDATANOTIFICATION)
{
m_ullSize = 0;
}
//char* pData = new char[dwSize];
//if (pData == NULL)
//{
// return E_ABORT;
//}
if ((m_ullSize + dwSize) > m_fileView.m_uiMapViewSize.QuadPart)
{
return E_ABORT;
}
pstgmed->pstm->Read((LPBYTE)m_fileView.m_lpMapAddress + m_ullSize, dwSize, &ulReadSize);
m_ullSize += ulReadSize;
//delete[]pData;
return S_OK;
}
STDMETHOD(OnObjectAvailable)(REFIID, IUnknown*)
{
TRACE(_T("IBindStatusCallback::OnObjectAvailable\n"));
return S_OK;
}
protected:
ULONG m_ulObjRefCount = 0UL;
private:
FileView m_fileView = {};
BackGroundWall* m_pThiz = NULL;
HANDLE m_hEventStop = NULL;
public:
ULONGLONG m_ullSize = 0ULL;
};
public:
HWND m_hWnd = NULL;
int m_nIndex = 0;
int m_nCount = 0;
__time64_t m_tTimeSec = 0LL;
const LONGLONG T_20MIN = 1200LL;
bool m_bLocal = false;
std::vector<std::wstring> m_files = {};
std::wstring m_strUrl = std::wstring();
std::wstring m_strFileName = std::wstring();
int DownLoad()
{
CBindStatusCallbackImpl bsci(this);
::DeleteUrlCacheEntryW(m_strUrl.c_str());
HRESULT hr = ::URLOpenStreamW(NULL, m_strUrl.c_str(), 0UL, &bsci);
return(0);
}
int SetDeskWallPaper()
{
::SystemParametersInfoW(SPI_SETDESKWALLPAPER, 0, (PVOID)m_strFileName.c_str(), SPIF_SENDCHANGE);
::Sleep(16);
::SystemParametersInfoW(SPI_SETDESKWALLPAPER, 0, (PVOID)m_strFileName.c_str(), SPIF_SENDCHANGE);
return(0);
}
int LoadNewBg(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(0) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\") + std::to_wstring(_time64(nullptr) % 86400) + L".png";
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
}
}
}
}
return(0);
}
bool DoSwitchNextOne()
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && ::wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
m_tTimeSec = _time64(nullptr);
return(true);
}
if ((LONGLONG)(_time64(nullptr) - m_tTimeSec) > T_20MIN)
{
m_tTimeSec = _time64(nullptr);
return(true);
}
return(false);
}
int RunWithNetwork(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_nCount = 8;
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(m_nIndex % m_nCount) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.png");
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
}
}
}
}
return(0);
}
int RunLoopWithNetwork(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_nIndex = 0;
m_nCount = 8;
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
while (true)
{
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(m_nIndex) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.png");
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
}
}
}
}
//20分钟切换一次
for (int i = 0; i < 1200; i++)
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
break;
}
::Sleep(1000);
}
}
return(0);
}
int RunWithLocal(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_files.clear();
enum_file(m_files, lpcwFilePath, { L".png",L".jpg", });
m_nCount = m_files.size();
if (m_nCount > 1)
{
m_strFileName = m_files[m_nIndex % m_nCount];
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
return(0);
}
return(-1);
}
int RunLoopWithLocal(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
enum_file(m_files, lpcwFilePath, { L".png",L".jpg", });
m_nIndex = 0;
m_nCount = m_files.size();
if (m_nCount > 1)
{
while (true)
{
m_strFileName = m_files[m_nIndex];
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
//20分钟切换一次
for (int i = 0; i < 1200; i++)
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
break;
}
::Sleep(1000);
}
}
return(0);
}
return(-1);
}
int RunTask(LPCWSTR lpcwFilePath)
{
bool bOk = DoSwitchNextOne();
if (bOk == true)
{
if (RunWithLocal(lpcwFilePath) != 0)
{
RunWithNetwork(lpcwFilePath);
}
}
return(0);
}
public:
int my_test(void)
{
HANDLE hMapFile; // handle for the file's memory-mapped region
HANDLE hFile; // the file handle
ULARGE_INTEGER uiFileMapping = { 1000UL,0UL, };
ULARGE_INTEGER uiFileOffset = { 0UL,0UL, };
ULARGE_INTEGER uiMapViewSize = { 1000UL,0UL, };
BOOL bFlag; // a result holder
SYSTEM_INFO SysInfo; // system information; used to get granularity
LPVOID lpMapAddress; // pointer to the base address of the
// Create the test file. Open it "Create Always" to overwrite any
// existing file. The data is re-created below
hFile = ::CreateFileW(L"test.txt",
GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
CREATE_ALWAYS,
FILE_FLAG_SEQUENTIAL_SCAN,
NULL);
if (hFile == INVALID_HANDLE_VALUE)
{
_tprintf(TEXT("hFile is NULL\n"));
_tprintf(TEXT("Target file is %s\n"),
L"test.txt");
return 4;
}
// Get the system allocation granularity.
::GetSystemInfo(&SysInfo);
// Create a file mapping object for the file
// Note that it is a good idea to ensure the file size is not zero
hMapFile = ::CreateFileMappingW(hFile, // current file handle
NULL, // default security
PAGE_READWRITE, // read/write permission
uiFileMapping.HighPart, // size of mapping object, high
uiFileMapping.LowPart, // size of mapping object, low
L"MAPPING"); // name of mapping object
if (hMapFile == NULL)
{
_tprintf(TEXT("hMapFile is NULL: last error: %d\n"), GetLastError());
return (2);
}
// Map the view and test the results.
lpMapAddress = ::MapViewOfFile(hMapFile, // handle to
// mapping object
FILE_MAP_ALL_ACCESS, // read/write
uiFileOffset.HighPart, // high-order 32
// bits of file
// offset
uiFileOffset.LowPart, // low-order 32
// bits of file
// offset
uiMapViewSize.QuadPart); // number of bytes
// to map
if (lpMapAddress == NULL)
{
_tprintf(TEXT("lpMapAddress is NULL: last error: %d\n"), GetLastError());
return 3;
}
::memcpy(lpMapAddress, "asdfjaklsdjfkljasdlkjfajsdflk", strlen("asdfjaklsdjfkljasdlkjfajsdflk"));
// Close the file mapping object and the open file
bFlag = ::UnmapViewOfFile(lpMapAddress);
bFlag = ::CloseHandle(hMapFile); // close the file mapping object
if (!bFlag)
{
_tprintf(TEXT("\nError %ld occurred closing the mapping object!"),
GetLastError());
}
bFlag = ::CloseHandle(hFile); // close the file itself
if (!bFlag)
{
_tprintf(TEXT("\nError %ld occurred closing the file!"),
GetLastError());
}
return 0;
}
};
[/reply]
class DownLoadFile
{
#define LOULONG(l) ((ULONG)(((ULONGLONG)(l)) & 0xffffffff))
#define HIULONG(l) ((ULONG)((((ULONGLONG)(l)) >> 32) & 0xffffffff))
#define WM_USER_ENDDOWNLOAD (WM_USER + 1)
#define WM_USER_DISPLAYSTATUS (WM_USER + 2)
#pragma pack(1)
struct DOWNLOADSTATUS
{
ULONG ulProgress;
ULONG ulProgressMax;
ULONG ulStatusCode;
LPCWSTR szStatusText;
};
#pragma pack()
class CBindStatusCallbackImpl : public IBindStatusCallback
{
enum
{
UF_BINDSTATUS_FIRST = BINDSTATUS_FINDINGRESOURCE,
UF_BINDSTATUS_LAST = BINDSTATUS_ACCEPTRANGES
};
public:
CBindStatusCallbackImpl(BackGroundWall* pThiz)
{
m_pThiz = pThiz;
m_ulObjRefCount = 1;
}
// IUnknown methods
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject)
{
TRACE(_T("IUnknown::QueryInterface\n"));
*ppvObject = NULL;
// IUnknown
if (::IsEqualIID(riid, __uuidof(IUnknown)))
{
TRACE(_T("IUnknown::QueryInterface(IUnknown)\n"));
*ppvObject = this;
}
// IBindStatusCallback
else if (::IsEqualIID(riid, __uuidof(IBindStatusCallback)))
{
TRACE(_T("IUnknown::QueryInterface(IBindStatusCallback)\n"));
*ppvObject = static_cast<IBindStatusCallback*>(this);
}
if (*ppvObject)
{
(*reinterpret_cast<LPUNKNOWN*>(ppvObject))->AddRef();
return S_OK;
}
return E_NOINTERFACE;
}
STDMETHOD_(ULONG, AddRef)()
{
TRACE(_T("IUnknown::AddRef\n"));
return ++m_ulObjRefCount;
}
STDMETHOD_(ULONG, Release)()
{
TRACE(_T("IUnknown::Release\n"));
return --m_ulObjRefCount;
}
// IBindStatusCallback methods
STDMETHOD(OnStartBinding)(DWORD, IBinding*)
{
TRACE(_T("IBindStatusCallback::OnStartBinding\n"));
int nRet = m_fileView.Init(m_pThiz->m_strFileName, { 32 * 1024 * 1024UL, 0UL, });
if (nRet != 0)
{
TRACE(_T("Init failure!\n"));
return E_ABORT;
}
return S_OK;
}
STDMETHOD(GetPriority)(LONG*)
{
TRACE(_T("IBindStatusCallback::GetPriority\n"));
return E_NOTIMPL;
}
STDMETHOD(OnLowResource)(DWORD)
{
TRACE(_T("IBindStatusCallback::OnLowResource\n"));
return S_OK;
}
STDMETHOD(OnProgress)(ULONG ulProgress,
ULONG ulProgressMax,
ULONG ulStatusCode,
LPCWSTR szStatusText)
{
#ifdef _DEBUG
static const LPCTSTR plpszStatus[] =
{
_T("BINDSTATUS_FINDINGRESOURCE"), // 1
_T("BINDSTATUS_CONNECTING"),
_T("BINDSTATUS_REDIRECTING"),
_T("BINDSTATUS_BEGINDOWNLOADDATA"),
_T("BINDSTATUS_DOWNLOADINGDATA"),
_T("BINDSTATUS_ENDDOWNLOADDATA"),
_T("BINDSTATUS_BEGINDOWNLOADCOMPONENTS"),
_T("BINDSTATUS_INSTALLINGCOMPONENTS"),
_T("BINDSTATUS_ENDDOWNLOADCOMPONENTS"),
_T("BINDSTATUS_USINGCACHEDCOPY"),
_T("BINDSTATUS_SENDINGREQUEST"),
_T("BINDSTATUS_CLASSIDAVAILABLE"),
_T("BINDSTATUS_MIMETYPEAVAILABLE"),
_T("BINDSTATUS_CACHEFILENAMEAVAILABLE"),
_T("BINDSTATUS_BEGINSYNCOPERATION"),
_T("BINDSTATUS_ENDSYNCOPERATION"),
_T("BINDSTATUS_BEGINUPLOADDATA"),
_T("BINDSTATUS_UPLOADINGDATA"),
_T("BINDSTATUS_ENDUPLOADINGDATA"),
_T("BINDSTATUS_PROTOCOLCLASSID"),
_T("BINDSTATUS_ENCODING"),
_T("BINDSTATUS_VERFIEDMIMETYPEAVAILABLE"),
_T("BINDSTATUS_CLASSINSTALLLOCATION"),
_T("BINDSTATUS_DECODING"),
_T("BINDSTATUS_LOADINGMIMEHANDLER"),
_T("BINDSTATUS_CONTENTDISPOSITIONATTACH"),
_T("BINDSTATUS_FILTERREPORTMIMETYPE"),
_T("BINDSTATUS_CLSIDCANINSTANTIATE"),
_T("BINDSTATUS_IUNKNOWNAVAILABLE"),
_T("BINDSTATUS_DIRECTBIND"),
_T("BINDSTATUS_RAWMIMETYPE"),
_T("BINDSTATUS_PROXYDETECTING"),
_T("BINDSTATUS_ACCEPTRANGES"),
_T("???") // unknown
};
#endif
TRACE(_T("IBindStatusCallback::OnProgress\n"));
TRACE(_T("ulProgress: %lu, ulProgressMax: %lu\n"), ulProgress, ulProgressMax);
TRACE(_T("ulStatusCode: %lu "), ulStatusCode);
if (ulStatusCode < UF_BINDSTATUS_FIRST || ulStatusCode > UF_BINDSTATUS_LAST)
{
ulStatusCode = UF_BINDSTATUS_LAST + 1;
}
#ifdef _DEBUG
TRACE(_T("(%s), szStatusText: %ls\n"), plpszStatus[ulStatusCode - UF_BINDSTATUS_FIRST], szStatusText);
#endif
printf("ulProgress: %lu, ulProgressMax: %lu\n", ulProgress, ulProgressMax);
//if (m_hWnd != NULL)
//{
// // inform the dialog box to display current status, don't use PostMessage
// DOWNLOADSTATUS downloadStatus = { ulProgress, ulProgressMax, ulStatusCode, szStatusText };
// ::PostMessageW(m_hWnd, WM_USER_DISPLAYSTATUS, 0, reinterpret_cast<LPARAM>(&downloadStatus));
//}
//if (m_hEventStop != NULL)
//{
// if (::WaitForSingleObject(m_hEventStop, 0) == WAIT_OBJECT_0)
// {
// TRACE(_T("Canceled.\n"));
// ::PostMessageW(m_hWnd, WM_USER_DISPLAYSTATUS, 0, NULL);
// return E_ABORT; // canceled by the user
// }
//}
return S_OK;
}
STDMETHOD(OnStopBinding)(HRESULT, LPCWSTR)
{
TRACE(_T("IBindStatusCallback::OnStopBinding\n"));
const ULARGE_INTEGER& uiSize = { LOULONG(m_ullSize), HIULONG(m_ullSize), };
m_fileView.Exit(uiSize);
return S_OK;
}
//---
STDMETHOD(GetBindInfo)(DWORD*, BINDINFO*)
{
TRACE(_T("IBindStatusCallback::GetBindInfo\n"));
return S_OK;
}
STDMETHOD(OnDataAvailable)(DWORD grfBSCF, DWORD dwSize, FORMATETC* pformatetc, STGMEDIUM* pstgmed)
{
TRACE(_T("IBindStatusCallback::OnDataAvailable\n"));
//BSCF_FIRSTDATANOTIFICATION = 0x00000001,
//BSCF_INTERMEDIATEDATANOTIFICATION = 0x00000002,
//BSCF_LASTDATANOTIFICATION = 0x00000004,
//有可能为BSCF_FIRSTDATANOTIFICATION, BSCF_FIRSTDATANOTIFICATION & BSCF_LASTDATANOTIFICATION, BSCF_INTERMEDIATEDATANOTIFICATION, BSCF_LASTDATANOTIFICATION
//即可能为一个包、两个包或多个包
ULONG ulReadSize = 0;
if ((grfBSCF & BSCF_FIRSTDATANOTIFICATION) == BSCF_FIRSTDATANOTIFICATION)
{
m_ullSize = 0;
}
//char* pData = new char[dwSize];
//if (pData == NULL)
//{
// return E_ABORT;
//}
if ((m_ullSize + dwSize) > m_fileView.m_uiMapViewSize.QuadPart)
{
return E_ABORT;
}
pstgmed->pstm->Read((LPBYTE)m_fileView.m_lpMapAddress + m_ullSize, dwSize, &ulReadSize);
m_ullSize += ulReadSize;
//delete[]pData;
return S_OK;
}
STDMETHOD(OnObjectAvailable)(REFIID, IUnknown*)
{
TRACE(_T("IBindStatusCallback::OnObjectAvailable\n"));
return S_OK;
}
protected:
ULONG m_ulObjRefCount = 0UL;
private:
FileView m_fileView = {};
BackGroundWall* m_pThiz = NULL;
HANDLE m_hEventStop = NULL;
public:
ULONGLONG m_ullSize = 0ULL;
};
public:
HWND m_hWnd = NULL;
int m_nIndex = 0;
int m_nCount = 0;
__time64_t m_tTimeSec = 0LL;
const LONGLONG T_20MIN = 1200LL;
bool m_bLocal = false;
std::vector<std::wstring> m_files = {};
std::wstring m_strUrl = std::wstring();
std::wstring m_strFileName = std::wstring();
int DownLoad()
{
CBindStatusCallbackImpl bsci(this);
::DeleteUrlCacheEntryW(m_strUrl.c_str());
HRESULT hr = ::URLOpenStreamW(NULL, m_strUrl.c_str(), 0UL, &bsci);
return(0);
}
int SetDeskWallPaper()
{
::SystemParametersInfoW(SPI_SETDESKWALLPAPER, 0, (PVOID)m_strFileName.c_str(), SPIF_SENDCHANGE);
::Sleep(16);
::SystemParametersInfoW(SPI_SETDESKWALLPAPER, 0, (PVOID)m_strFileName.c_str(), SPIF_SENDCHANGE);
return(0);
}
int LoadNewBg(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(0) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\") + std::to_wstring(_time64(nullptr) % 86400) + L".png";
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
}
}
}
}
return(0);
}
bool DoSwitchNextOne()
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && ::wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
m_tTimeSec = _time64(nullptr);
return(true);
}
if ((LONGLONG)(_time64(nullptr) - m_tTimeSec) > T_20MIN)
{
m_tTimeSec = _time64(nullptr);
return(true);
}
return(false);
}
int RunWithNetwork(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_nCount = 8;
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(m_nIndex % m_nCount) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.png");
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
}
}
}
}
return(0);
}
int RunLoopWithNetwork(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_nIndex = 0;
m_nCount = 8;
const std::string& sL = "\"url\":\"";
const std::string& sR = "&";
while (true)
{
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.json");
m_strUrl = L"https://cn.bing.com/HPImageArchive.aspx?format=js&idx=" + std::to_wstring(m_nIndex) + L"&n=1&mkt=zh-CN";// L"https://cn.bing.com/th?id=OHR.QuebecDuck_ZH-CN0588954873_1920x1080.jpg";
DownLoad();
FILE* fp = _wfopen(m_strFileName.c_str(), L"r");
if (fp != NULL)
{
_fseeki64(fp, 0LL, SEEK_END);
LONGLONG len = _ftelli64(fp);
_fseeki64(fp, 0LL, SEEK_SET);
std::string sData(len, '\0');
fread(sData.data(), 1, sData.size(), fp);
fclose(fp);
if (sData.empty() == false)
{
auto itL = sData.find(sL, 0);
if (itL != std::string::npos)
{
itL += sL.length();
auto itR = sData.find(sR, itL);
if (itL != std::string::npos)
{
std::string sUrl = "https://cn.bing.com/" + sData.substr(itL, itR - itL);
m_strFileName = lpcwFilePath + std::wstring(L"\\cnbing.png");
m_strUrl = UTF8ToWIDE(sUrl).c_str();
DownLoad();
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
}
}
}
}
//20分钟切换一次
for (int i = 0; i < 1200; i++)
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
break;
}
::Sleep(1000);
}
}
return(0);
}
int RunWithLocal(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
m_files.clear();
enum_file(m_files, lpcwFilePath, { L".png",L".jpg", });
m_nCount = m_files.size();
if (m_nCount > 1)
{
m_strFileName = m_files[m_nIndex % m_nCount];
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
return(0);
}
return(-1);
}
int RunLoopWithLocal(LPCWSTR lpcwFilePath)
{
::CreateDirectoryW(lpcwFilePath, NULL);
enum_file(m_files, lpcwFilePath, { L".png",L".jpg", });
m_nIndex = 0;
m_nCount = m_files.size();
if (m_nCount > 1)
{
while (true)
{
m_strFileName = m_files[m_nIndex];
SetDeskWallPaper();
m_nIndex = (m_nIndex + 1) % m_nCount;
//20分钟切换一次
for (int i = 0; i < 1200; i++)
{
WCHAR wValueData[MAXIMUM_REPARSE_DATA_BUFFER_SIZE] = { 0 };
if (GetAppSettingWithRegistry(wValueData, L"NEXTFLAG", L"XingYun86BGT") == TRUE && wcsicmp(wValueData, L"1") == 0)
{
SetAppSettingWithRegistry(L"0", L"NEXTFLAG", L"XingYun86BGT");
break;
}
::Sleep(1000);
}
}
return(0);
}
return(-1);
}
int RunTask(LPCWSTR lpcwFilePath)
{
bool bOk = DoSwitchNextOne();
if (bOk == true)
{
if (RunWithLocal(lpcwFilePath) != 0)
{
RunWithNetwork(lpcwFilePath);
}
}
return(0);
}
public:
int my_test(void)
{
HANDLE hMapFile; // handle for the file's memory-mapped region
HANDLE hFile; // the file handle
ULARGE_INTEGER uiFileMapping = { 1000UL,0UL, };
ULARGE_INTEGER uiFileOffset = { 0UL,0UL, };
ULARGE_INTEGER uiMapViewSize = { 1000UL,0UL, };
BOOL bFlag; // a result holder
SYSTEM_INFO SysInfo; // system information; used to get granularity
LPVOID lpMapAddress; // pointer to the base address of the
// Create the test file. Open it "Create Always" to overwrite any
// existing file. The data is re-created below
hFile = ::CreateFileW(L"test.txt",
GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
CREATE_ALWAYS,
FILE_FLAG_SEQUENTIAL_SCAN,
NULL);
if (hFile == INVALID_HANDLE_VALUE)
{
_tprintf(TEXT("hFile is NULL\n"));
_tprintf(TEXT("Target file is %s\n"),
L"test.txt");
return 4;
}
// Get the system allocation granularity.
::GetSystemInfo(&SysInfo);
// Create a file mapping object for the file
// Note that it is a good idea to ensure the file size is not zero
hMapFile = ::CreateFileMappingW(hFile, // current file handle
NULL, // default security
PAGE_READWRITE, // read/write permission
uiFileMapping.HighPart, // size of mapping object, high
uiFileMapping.LowPart, // size of mapping object, low
L"MAPPING"); // name of mapping object
if (hMapFile == NULL)
{
_tprintf(TEXT("hMapFile is NULL: last error: %d\n"), GetLastError());
return (2);
}
// Map the view and test the results.
lpMapAddress = ::MapViewOfFile(hMapFile, // handle to
// mapping object
FILE_MAP_ALL_ACCESS, // read/write
uiFileOffset.HighPart, // high-order 32
// bits of file
// offset
uiFileOffset.LowPart, // low-order 32
// bits of file
// offset
uiMapViewSize.QuadPart); // number of bytes
// to map
if (lpMapAddress == NULL)
{
_tprintf(TEXT("lpMapAddress is NULL: last error: %d\n"), GetLastError());
return 3;
}
::memcpy(lpMapAddress, "asdfjaklsdjfkljasdlkjfajsdflk", strlen("asdfjaklsdjfkljasdlkjfajsdflk"));
// Close the file mapping object and the open file
bFlag = ::UnmapViewOfFile(lpMapAddress);
bFlag = ::CloseHandle(hMapFile); // close the file mapping object
if (!bFlag)
{
_tprintf(TEXT("\nError %ld occurred closing the mapping object!"),
GetLastError());
}
bFlag = ::CloseHandle(hFile); // close the file itself
if (!bFlag)
{
_tprintf(TEXT("\nError %ld occurred closing the file!"),
GetLastError());
}
return 0;
}
};