Overhaul repository structure to add config
I wish I didn't end up doing this all at once, but ah well. Quick rundown: - CommonCfg contains config/registry functions shared between Grabby and GrbyCfg. - GrbyCfg provides a dialog for configuring Grabby. git-svn-id: svn://vcs.sdm.2ki.xyz/Grabby/trunk@16 27729192-006e-004d-b9b5-06fbd0ef7001
This commit is contained in:
parent
be95698d10
commit
69476552e8
42 changed files with 2291 additions and 136 deletions
160
CommonCfg/CommonCfg.vcproj
Normal file
160
CommonCfg/CommonCfg.vcproj
Normal file
|
@ -0,0 +1,160 @@
|
|||
<?xml version="1.0" encoding="shift_jis"?>
|
||||
<VisualStudioProject
|
||||
ProjectType="Visual C++"
|
||||
Version="7.10"
|
||||
Name="CommonCfg"
|
||||
ProjectGUID="{61829180-05C1-4865-B9C3-FEB983AD6997}"
|
||||
RootNamespace="CommonCfg"
|
||||
Keyword="Win32Proj">
|
||||
<Platforms>
|
||||
<Platform
|
||||
Name="Win32"/>
|
||||
</Platforms>
|
||||
<Configurations>
|
||||
<Configuration
|
||||
Name="Debug|Win32"
|
||||
OutputDirectory="Debug"
|
||||
IntermediateDirectory="Debug"
|
||||
ConfigurationType="4"
|
||||
CharacterSet="2">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
PreprocessorDefinitions="_WIN32_WINNT=0x0400;_WIN32_WINDOWS=0x0400;_DEBUG"
|
||||
MinimalRebuild="TRUE"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="5"
|
||||
UsePrecompiledHeader="3"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="TRUE"
|
||||
DebugInformationFormat="4"
|
||||
CompileAs="1"/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
OutputFile="$(OutDir)/CommonCfg.lib"/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCManagedWrapperGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Release|Win32"
|
||||
OutputDirectory="Release"
|
||||
IntermediateDirectory="Release"
|
||||
ConfigurationType="4"
|
||||
CharacterSet="2">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
PreprocessorDefinitions="_WIN32_WINNT=0x0400;_WIN32_WINDOWS=0x0400"
|
||||
RuntimeLibrary="4"
|
||||
UsePrecompiledHeader="3"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="TRUE"
|
||||
DebugInformationFormat="3"
|
||||
CompileAs="1"/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
OutputFile="$(OutDir)/CommonCfg.lib"/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCManagedWrapperGeneratorTool"/>
|
||||
<Tool
|
||||
Name="VCAuxiliaryManagedWrapperGeneratorTool"/>
|
||||
</Configuration>
|
||||
</Configurations>
|
||||
<References>
|
||||
</References>
|
||||
<Files>
|
||||
<Filter
|
||||
Name="Source Files"
|
||||
Filter="cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx"
|
||||
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
|
||||
<File
|
||||
RelativePath=".\Config.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\MultiString.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\RegHelper.c">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\stdafx.c">
|
||||
<FileConfiguration
|
||||
Name="Debug|Win32">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
UsePrecompiledHeader="1"/>
|
||||
</FileConfiguration>
|
||||
<FileConfiguration
|
||||
Name="Release|Win32">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
UsePrecompiledHeader="1"/>
|
||||
</FileConfiguration>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\UploadConfig.c">
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Header Files"
|
||||
Filter="h;hpp;hxx;hm;inl;inc;xsd"
|
||||
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}">
|
||||
<File
|
||||
RelativePath=".\RegHelper.h">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\stdafx.h">
|
||||
</File>
|
||||
<Filter
|
||||
Name="Export"
|
||||
Filter="">
|
||||
<File
|
||||
RelativePath=".\Export\Config.h">
|
||||
</File>
|
||||
</Filter>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Resource Files"
|
||||
Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx"
|
||||
UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}">
|
||||
</Filter>
|
||||
<File
|
||||
RelativePath=".\ReadMe.txt">
|
||||
</File>
|
||||
</Files>
|
||||
<Globals>
|
||||
</Globals>
|
||||
</VisualStudioProject>
|
141
CommonCfg/Config.c
Normal file
141
CommonCfg/Config.c
Normal file
|
@ -0,0 +1,141 @@
|
|||
#include "stdafx.h"
|
||||
|
||||
const Config DEFAULT_CONFIG = {
|
||||
{0}, // Use default (My Documents/Screenshots)
|
||||
FALSE, // Don't upload screenshots
|
||||
TRUE, // Do keep screenshots
|
||||
FALSE, // Don't start helper on startup
|
||||
HSC_WIN10 // Emulate Win7+ "Snipping Tool" shortcut
|
||||
};
|
||||
|
||||
#define OpenRootKey(hkey,access) \
|
||||
RegCreateKeyEx(HKEY_CURRENT_USER, \
|
||||
_T(ROOT_KEYNAME), \
|
||||
0, \
|
||||
NULL, \
|
||||
REG_OPTION_NON_VOLATILE, \
|
||||
access, \
|
||||
NULL, \
|
||||
hkey, \
|
||||
NULL)
|
||||
|
||||
// Enumeration callback for GetConfig
|
||||
static BOOL
|
||||
ConfigCallback(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
DWORD dwValSize,
|
||||
DWORD dwValType,
|
||||
PVOID pData)
|
||||
{
|
||||
Config *cfg = pData;
|
||||
if (!cfg) return FALSE;
|
||||
|
||||
CopyIfMatch(hKey, cfg,
|
||||
ScreenshotDir, REG_PATH_SZ)
|
||||
else CopyIfMatch(hKey, cfg,
|
||||
Upload, REG_DWORD)
|
||||
else CopyIfMatch(hKey, cfg,
|
||||
KeepScreenshots, REG_DWORD)
|
||||
else CopyIfMatch(hKey, cfg,
|
||||
HelperStartup, REG_DWORD)
|
||||
else CopyIfMatch(hKey, cfg,
|
||||
HelperShortcut, REG_DWORD)
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
Config *
|
||||
GetConfig(void)
|
||||
{
|
||||
HKEY hkRootKey = NULL;
|
||||
BOOL bRes;
|
||||
DWORD dwErr;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
Config *cfg = HeapAlloc(hHeap, 0, sizeof(Config));
|
||||
|
||||
if (!cfg) return NULL;
|
||||
|
||||
// Copy in the default config
|
||||
CopyMemory(cfg, &DEFAULT_CONFIG, sizeof(Config));
|
||||
|
||||
if ((dwErr = OpenRootKey(&hkRootKey, KEY_READ))) {
|
||||
HeapFree(hHeap, 0, cfg);
|
||||
SetLastError(dwErr);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bRes = RegGetAllValues(hkRootKey, ConfigCallback, cfg);
|
||||
dwErr = GetLastError();
|
||||
RegCloseKey(hkRootKey);
|
||||
|
||||
if (!bRes) {
|
||||
FreeConfig(cfg);
|
||||
SetLastError(dwErr);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// If ScreenshotDir is NULL, set it to My Documents
|
||||
if (!strlen(cfg->ScreenshotDir)) {
|
||||
HRESULT hrRes;
|
||||
|
||||
// afaict, My Pictures isn't an easily accessible folder.
|
||||
// There's CSIDL_MYPICTURES, but that's XP-only (and also
|
||||
// points to a virtual folder???).
|
||||
hrRes = SHGetFolderPath(NULL,
|
||||
CSIDL_PERSONAL,
|
||||
NULL,
|
||||
SHGFP_TYPE_CURRENT,
|
||||
cfg->ScreenshotDir);
|
||||
|
||||
if (FAILED(hrRes)) {
|
||||
// TODO: error management
|
||||
// For now, just empty the string
|
||||
*cfg->ScreenshotDir = 0;
|
||||
} else {
|
||||
PathAppend(cfg->ScreenshotDir,
|
||||
_T("Screenshots"));
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Detect startup
|
||||
|
||||
return cfg;
|
||||
}
|
||||
|
||||
BOOL
|
||||
SaveConfig(Config *cfg)
|
||||
{
|
||||
HKEY hkRootKey;
|
||||
DWORD dwErr;
|
||||
|
||||
if (!cfg) return FALSE;
|
||||
|
||||
if ((dwErr = OpenRootKey(&hkRootKey, KEY_WRITE))) {
|
||||
SetLastError(dwErr);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
StoreConfig(hkRootKey, cfg,
|
||||
ScreenshotDir, REG_SZ)
|
||||
StoreConfig(hkRootKey, cfg,
|
||||
Upload, REG_DWORD)
|
||||
StoreConfig(hkRootKey, cfg,
|
||||
KeepScreenshots, REG_DWORD)
|
||||
StoreConfig(hkRootKey, cfg,
|
||||
HelperStartup, REG_DWORD)
|
||||
StoreConfig(hkRootKey, cfg,
|
||||
HelperShortcut, REG_DWORD)
|
||||
|
||||
RegCloseKey(hkRootKey);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
FreeConfig(Config *cfg)
|
||||
{
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
if (!cfg) return;
|
||||
|
||||
HeapFree(hHeap, 0, cfg);
|
||||
return;
|
||||
}
|
86
CommonCfg/Export/Config.h
Normal file
86
CommonCfg/Export/Config.h
Normal file
|
@ -0,0 +1,86 @@
|
|||
#pragma once
|
||||
|
||||
typedef struct _MultiString {
|
||||
LPTSTR * Values; // Array of string values
|
||||
size_t Count; // Length of Values
|
||||
size_t TotalLength; // Used by registry helpers.
|
||||
// NOTE: This length includes the NULL
|
||||
// terminator characters of each string
|
||||
DWORD Reserved[2]; // Used internally
|
||||
} MultiString;
|
||||
|
||||
// Initializes an existing MultiString array, with the given length.
|
||||
// If dwInitLen is 0, no entries are pre-allocated.
|
||||
BOOL
|
||||
MultiString_Init(MultiString *ms,
|
||||
DWORD dwInitLen);
|
||||
|
||||
// Appends a copy of szNew to the end of the list.
|
||||
//
|
||||
// NOTE: A new string with the same length as szNew is allocated and
|
||||
// stored in ms. This makes future internal freeing easier, but means
|
||||
// the function caller is responsible for freeing the parameter.
|
||||
BOOL
|
||||
MultiString_Append(MultiString *ms,
|
||||
LPCTSTR szNew);
|
||||
|
||||
// Removes the string at dwIdx, freeing the memory used.
|
||||
BOOL
|
||||
MultiString_Remove(MultiString *ms,
|
||||
DWORD dwIdx);
|
||||
|
||||
// Replaces the string at dwIdx with szNew. Allocations are performed
|
||||
// similar to MultiString_Append.
|
||||
BOOL
|
||||
MultiString_Replace(MultiString *ms,
|
||||
DWORD dwIdx,
|
||||
LPCTSTR szNew);
|
||||
|
||||
// Frees all memory in a MultiString structure.
|
||||
void
|
||||
MultiString_Dispose(MultiString *ms);
|
||||
|
||||
typedef enum _HelperShortcut {
|
||||
HSC_MACOS, // Pretend to be like MacOS (Win+Shift+4)
|
||||
HSC_WIN10, // Pretend to be like Windows (Win+Shift+S)
|
||||
HSC_CUSTOM // Use a custom keyboard shortcut
|
||||
} HlprKbd;
|
||||
|
||||
typedef struct _GlobalConfig {
|
||||
TCHAR ScreenshotDir[MAX_PATH];
|
||||
BOOL Upload;
|
||||
BOOL KeepScreenshots;
|
||||
BOOL HelperStartup;
|
||||
HlprKbd HelperShortcut;
|
||||
} Config;
|
||||
|
||||
typedef enum _AuthMethod {
|
||||
CFG_NOAUTH, // Anonymous HTTP requests
|
||||
CFG_BASICAUTH, // Use HTTP Basic auth
|
||||
CFG_DIGESTAUTH, // Use HTTP Digest auth
|
||||
CFG_TOKENAUTH // Use a custom Authorization header
|
||||
} AuthMethod;
|
||||
|
||||
typedef struct _UploadConfig {
|
||||
LPTSTR Name;
|
||||
LPTSTR URL;
|
||||
LPTSTR Method;
|
||||
/*
|
||||
* NOTE: If AuthType == CFG_TOKENAUTH, Username is blank/NULL and
|
||||
* Password is the token.
|
||||
*/
|
||||
LPTSTR Username;
|
||||
LPTSTR Password;
|
||||
AuthMethod HTTPAuthMethod;
|
||||
|
||||
MultiString Headers;
|
||||
MultiString Parameters;
|
||||
} UploadConfig;
|
||||
|
||||
|
||||
// Gets the current configuration from the registry.
|
||||
Config *GetConfig(void);
|
||||
// Saves the Config object to the registry.
|
||||
BOOL SaveConfig(Config *cfg);
|
||||
// Frees all memory associated with the Config object.
|
||||
void FreeConfig(Config *cfg);
|
196
CommonCfg/MultiString.c
Normal file
196
CommonCfg/MultiString.c
Normal file
|
@ -0,0 +1,196 @@
|
|||
#include "stdafx.h"
|
||||
|
||||
#define STRSAFE_NO_DEPRECATE
|
||||
#include <Strsafe.h>
|
||||
|
||||
#define CurAlloc Reserved[0]
|
||||
|
||||
|
||||
BOOL
|
||||
MultiString_Init(MultiString *ms,
|
||||
DWORD dwInitLen)
|
||||
{
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
if (!ms) {
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (dwInitLen) {
|
||||
ms->CurAlloc = dwInitLen;
|
||||
ms->Values = HeapAlloc(hHeap,
|
||||
HEAP_ZERO_MEMORY,
|
||||
sizeof(LPTSTR) * dwInitLen);
|
||||
if (!ms->Values) return FALSE;
|
||||
ms->Count = 0;
|
||||
} else {
|
||||
// Otherwise, this amounts to a zero-out
|
||||
ZeroMemory(ms, sizeof(MultiString));
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
__inline static LPTSTR
|
||||
CreateStrCopy(LPCTSTR szStr)
|
||||
{
|
||||
HRESULT hrRes;
|
||||
LPTSTR szNewCopy;
|
||||
// dwLen needs to include the NULL terminator
|
||||
size_t dwLen = _tcslen(szStr) + 1;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
// Allocate the new string
|
||||
szNewCopy = HeapAlloc(hHeap,
|
||||
HEAP_ZERO_MEMORY,
|
||||
sizeof(TCHAR) * dwLen);
|
||||
if (!szNewCopy) return NULL;
|
||||
|
||||
// Copy the actual data over
|
||||
hrRes = StringCchCopy(szNewCopy,
|
||||
dwLen,
|
||||
szStr);
|
||||
if (FAILED(hrRes)) {
|
||||
HeapFree(hHeap, 0, szNewCopy);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return szNewCopy;
|
||||
}
|
||||
|
||||
BOOL
|
||||
MultiString_Append(MultiString *ms,
|
||||
LPCTSTR szNew)
|
||||
{
|
||||
LPTSTR szNewCopy = NULL;
|
||||
DWORD dwNewLen;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
if (!ms || !szNew) {
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
dwNewLen = (DWORD)_tcslen(szNew) + 1;
|
||||
|
||||
// Do we need to allocate more room for pointers?
|
||||
if (ms->Values == NULL) {
|
||||
// Oops, we have nothing! Let's allocate a couple
|
||||
if (!MultiString_Init(ms, 3)) {
|
||||
return FALSE;
|
||||
}
|
||||
} else if (ms->CurAlloc == ms->Count) {
|
||||
DWORD dwNewAlloc = ms->CurAlloc + 3;
|
||||
LPTSTR *pszNew = HeapReAlloc(hHeap,
|
||||
0,
|
||||
ms->Values,
|
||||
sizeof(LPTSTR) * dwNewAlloc);
|
||||
if (!pszNew) {
|
||||
// ReAlloc failed :<
|
||||
return FALSE;
|
||||
}
|
||||
ms->CurAlloc = dwNewAlloc;
|
||||
ms->Values = pszNew;
|
||||
}
|
||||
|
||||
szNewCopy = CreateStrCopy(szNew);
|
||||
if (!szNewCopy) return FALSE;
|
||||
|
||||
// All set, append to the end and increment Count
|
||||
ms->Values[ms->Count++] = szNewCopy;
|
||||
ms->TotalLength += dwNewLen;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL
|
||||
MultiString_Remove(MultiString *ms,
|
||||
DWORD dwIdx)
|
||||
{
|
||||
DWORD dwLen = 0;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
if (!ms) return FALSE;
|
||||
|
||||
if (dwIdx >= ms->Count) {
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
} else if (ms->Values[dwIdx] != NULL) {
|
||||
dwLen = (DWORD)_tcslen(ms->Values[dwIdx]) + 1;
|
||||
|
||||
HeapFree(hHeap, 0, ms->Values[dwIdx]);
|
||||
}
|
||||
|
||||
|
||||
// Shift down the remaining strings
|
||||
if (dwIdx < ms->Count - 1) {
|
||||
size_t i;
|
||||
for (i = dwIdx; i < ms->Count - 1; i++) {
|
||||
ms->Values[i] = ms->Values[i + 1];
|
||||
}
|
||||
}
|
||||
|
||||
ms->Count--;
|
||||
ms->TotalLength -= dwLen;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL
|
||||
MultiString_Replace(MultiString *ms,
|
||||
DWORD dwIdx,
|
||||
LPCTSTR szNew)
|
||||
{
|
||||
DWORD dwOldLen = 0,
|
||||
dwNewLen = 0;
|
||||
LPTSTR szTmp;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
if (!ms || !szNew) return FALSE;
|
||||
|
||||
if (dwIdx >= ms->Count) {
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
dwNewLen = (DWORD)_tcslen(szNew) + 1;
|
||||
|
||||
// Create the copied new string
|
||||
szTmp = CreateStrCopy(szNew);
|
||||
if (!szTmp) return FALSE;
|
||||
|
||||
// Perform the switcheroo
|
||||
if (ms->Values[dwIdx] != NULL) {
|
||||
dwOldLen = (DWORD)_tcslen(ms->Values[dwIdx]) + 1;
|
||||
|
||||
HeapFree(hHeap, 0, ms->Values[dwIdx]);
|
||||
}
|
||||
|
||||
ms->Values[dwIdx] = szTmp;
|
||||
ms->TotalLength = ms->TotalLength + dwNewLen - dwOldLen;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void
|
||||
MultiString_Dispose(MultiString *ms)
|
||||
{
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
DWORD i;
|
||||
|
||||
if (!ms) return;
|
||||
|
||||
if (ms->Values != NULL) {
|
||||
for (i = 0; i < ms->Count; i++) {
|
||||
HeapFree(hHeap, 0, ms->Values[i]);
|
||||
}
|
||||
|
||||
HeapFree(hHeap, 0, ms->Values);
|
||||
ms->Values = NULL;
|
||||
}
|
||||
ms->Count = 0;
|
||||
ms->CurAlloc = 0;
|
||||
|
||||
return;
|
||||
}
|
29
CommonCfg/ReadMe.txt
Normal file
29
CommonCfg/ReadMe.txt
Normal file
|
@ -0,0 +1,29 @@
|
|||
========================================================================
|
||||
STATIC LIBRARY : CommonCfg Project Overview
|
||||
========================================================================
|
||||
|
||||
AppWizard has created this CommonCfg library project for you.
|
||||
This file contains a summary of what you will find in each of the files that
|
||||
make up your CommonCfg application.
|
||||
|
||||
|
||||
CommonCfg.vcproj
|
||||
This is the main project file for VC++ projects generated using an Application Wizard.
|
||||
It contains information about the version of Visual C++ that generated the file, and
|
||||
information about the platforms, configurations, and project features selected with the
|
||||
Application Wizard.
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
StdAfx.h, StdAfx.cpp
|
||||
These files are used to build a precompiled header (PCH) file
|
||||
named CommonCfg.pch and a precompiled types file named StdAfx.obj.
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
Other notes:
|
||||
|
||||
AppWizard uses "TODO:" comments to indicate parts of the source code you
|
||||
should add to or customize.
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
280
CommonCfg/RegHelper.c
Normal file
280
CommonCfg/RegHelper.c
Normal file
|
@ -0,0 +1,280 @@
|
|||
#include "stdafx.h"
|
||||
|
||||
#define STRSAFE_NO_DEPRECATE
|
||||
#include <Strsafe.h>
|
||||
|
||||
// Used by CopyRegValue specifically for copying
|
||||
// REG_MULTI_SZ values, because those in particular are
|
||||
// really funky.
|
||||
static BOOL
|
||||
CopyMultiValue(HKEY hKey,
|
||||
PVOID pVal,
|
||||
LPCTSTR szName,
|
||||
DWORD dwSize)
|
||||
{
|
||||
int iStrCount = 0;
|
||||
LPTSTR szMulti = NULL,
|
||||
ptr;
|
||||
BOOL bWasNull = FALSE;
|
||||
LONG lRes;
|
||||
MultiString *msData = (MultiString *)pVal;
|
||||
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
szMulti = HeapAlloc(hHeap,
|
||||
HEAP_ZERO_MEMORY,
|
||||
dwSize + sizeof(TCHAR));
|
||||
if (!szMulti) return FALSE;
|
||||
|
||||
// Get the multi-string value
|
||||
if (!(lRes = RegQueryValueEx(hKey,
|
||||
szName,
|
||||
0,
|
||||
NULL,
|
||||
szMulti,
|
||||
&dwSize)))
|
||||
{
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
SetLastError(lRes);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
for (ptr = szMulti; (ptr - szMulti) < (LONG)dwSize; ptr++) {
|
||||
if (*ptr == 0) {
|
||||
if (bWasNull) {
|
||||
// Two NULLs in a row, we're done!
|
||||
break;
|
||||
} else {
|
||||
// End of string, add to the list
|
||||
bWasNull = TRUE;
|
||||
iStrCount++;
|
||||
}
|
||||
}
|
||||
bWasNull = FALSE;
|
||||
}
|
||||
|
||||
if (!bWasNull) {
|
||||
// Not properly NULL terminated, sigh...
|
||||
// Make sure to count the last string.
|
||||
iStrCount++;
|
||||
}
|
||||
|
||||
if (!MultiString_Init(msData, iStrCount)) {
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
return FALSE;
|
||||
} else {
|
||||
int i;
|
||||
for (i = 0, ptr = szMulti; i < iStrCount; i++, ptr += strlen(ptr) + 1) {
|
||||
if (!MultiString_Append(msData, ptr)) {
|
||||
DWORD err = GetLastError();
|
||||
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
MultiString_Dispose(msData);
|
||||
|
||||
SetLastError(err);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL
|
||||
CopyRegValue(HKEY hKey,
|
||||
PVOID pVal,
|
||||
LPCTSTR szName,
|
||||
DWORD dwType,
|
||||
DWORD dwSize)
|
||||
{
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
PVOID pData = pVal;
|
||||
LONG lRes;
|
||||
|
||||
if (pVal == NULL ||
|
||||
szName == NULL ||
|
||||
hKey == NULL) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (dwType == REG_BINARY ||
|
||||
dwType == REG_SZ) {
|
||||
pData = HeapAlloc(hHeap, HEAP_ZERO_MEMORY, dwSize);
|
||||
if (!pData) return FALSE;
|
||||
*(PVOID *)pVal = pData;
|
||||
} else if (dwType == REG_MULTI_SZ) {
|
||||
// REG_MULTI_SZ is complex enough to warrant its own
|
||||
// function
|
||||
return CopyMultiValue(hKey, pVal, szName, dwSize);
|
||||
}
|
||||
|
||||
if ((lRes = RegQueryValueEx(hKey,
|
||||
szName,
|
||||
NULL,
|
||||
NULL,
|
||||
pData,
|
||||
&dwSize)) != ERROR_SUCCESS)
|
||||
{
|
||||
SetLastError(lRes);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// Enumerates across all values in a key, running the given
|
||||
// RegEnumCallback. Use `pData` to pass application-defined
|
||||
// data to your enumerator callback.
|
||||
BOOL RegGetAllValues(HKEY hKey,
|
||||
RegEnumCallback cb,
|
||||
PVOID pData)
|
||||
{
|
||||
LONG lRes;
|
||||
TCHAR szValName[512];
|
||||
DWORD dwNameLen = 512,
|
||||
dwIdx,
|
||||
dwValType,
|
||||
dwValSize;
|
||||
if (!hKey || !cb) return FALSE;
|
||||
|
||||
for (dwIdx = 0;
|
||||
dwNameLen = 512, // reset dwNameLen first
|
||||
!(lRes = RegEnumValue(hKey,
|
||||
dwIdx,
|
||||
szValName,
|
||||
&dwNameLen,
|
||||
0,
|
||||
&dwValType,
|
||||
NULL,
|
||||
&dwValSize));
|
||||
dwIdx++) {
|
||||
// Enforce null termination
|
||||
szValName[min(511, dwNameLen)] = 0;
|
||||
// pass to callback
|
||||
if (!cb(hKey,
|
||||
szValName,
|
||||
dwValSize,
|
||||
dwValType,
|
||||
pData)) {
|
||||
// Callback returned failure, bail out
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
if (lRes != ERROR_NO_MORE_ITEMS) {
|
||||
// Some enumeration error happened, store it
|
||||
// and report the failure
|
||||
SetLastError(lRes);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL
|
||||
RegStoreMultiString(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
MultiString *msData)
|
||||
{
|
||||
LPTSTR szMulti;
|
||||
DWORD dwMultiSize;
|
||||
LONG lRes;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
|
||||
if (!msData->TotalLength) return FALSE;
|
||||
|
||||
// Total size + second NULL terminator
|
||||
dwMultiSize = (DWORD)msData->TotalLength + 1;
|
||||
szMulti = HeapAlloc(hHeap,
|
||||
HEAP_ZERO_MEMORY,
|
||||
dwMultiSize * sizeof(TCHAR));
|
||||
if (!szMulti) return FALSE;
|
||||
|
||||
// Copy all the strings into one buffer, as per REG_MULTI_SZ
|
||||
{
|
||||
DWORD i, dwCurLen;
|
||||
for (i = 0, dwCurLen = 0;
|
||||
i < msData->Count && dwCurLen < dwMultiSize;
|
||||
dwCurLen += (DWORD)_tcslen(msData->Values[i++]) + 1) {
|
||||
HRESULT hrRes = StringCchCopy(&szMulti[dwCurLen],
|
||||
_tcslen(msData->Values[i]) + 1,
|
||||
msData->Values[i]);
|
||||
if (FAILED(hrRes)) {
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
lRes = RegSetValueEx(hKey,
|
||||
szValName,
|
||||
0,
|
||||
REG_MULTI_SZ,
|
||||
szMulti,
|
||||
dwMultiSize);
|
||||
|
||||
HeapFree(hHeap, 0, szMulti);
|
||||
|
||||
if (lRes != ERROR_SUCCESS) {
|
||||
SetLastError(lRes);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// Stores a value in the registry, making assumptions based on the
|
||||
// key type.
|
||||
BOOL
|
||||
RegStoreValue(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
PVOID pData,
|
||||
DWORD dwValType)
|
||||
{
|
||||
DWORD dwStoreSize;
|
||||
LONG lRes;
|
||||
if (!hKey || !szValName || !pData) return FALSE;
|
||||
|
||||
switch (dwValType) {
|
||||
case REG_SZ:
|
||||
case REG_EXPAND_SZ:
|
||||
dwStoreSize = (DWORD)_tcslen((LPTSTR)pData) + sizeof(TCHAR);
|
||||
break;
|
||||
case REG_DWORD:
|
||||
dwStoreSize = sizeof(DWORD);
|
||||
break;
|
||||
#ifdef QWORD
|
||||
case REG_QWORD:
|
||||
dwStoreSize = sizeof(QWORD);
|
||||
break;
|
||||
#endif
|
||||
case REG_BINARY:
|
||||
// TODO: handle REG_BINARY? will we ever use it?
|
||||
OutputDebugString(_T("REG_BINARY attempted to be stored! Unsupported"));
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
case REG_MULTI_SZ:
|
||||
return RegStoreMultiString(hKey,
|
||||
szValName,
|
||||
(MultiString *)pData);
|
||||
default:
|
||||
// ignore
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
lRes = RegSetValueEx(hKey,
|
||||
szValName,
|
||||
0,
|
||||
dwValType,
|
||||
pData,
|
||||
dwStoreSize);
|
||||
if (lRes != ERROR_SUCCESS) {
|
||||
SetLastError(lRes);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
68
CommonCfg/RegHelper.h
Normal file
68
CommonCfg/RegHelper.h
Normal file
|
@ -0,0 +1,68 @@
|
|||
// Helper functions for handling the registry
|
||||
#pragma once
|
||||
|
||||
// Used behind CopyIfMatch. Copies a given registry value to
|
||||
// another location, regardless of type.
|
||||
BOOL CopyRegValue(HKEY hKey,
|
||||
PVOID pVal,
|
||||
LPCTSTR szName,
|
||||
DWORD dwType,
|
||||
DWORD dwSize);
|
||||
|
||||
// Callback for RegGetAllValues
|
||||
typedef BOOL (*RegEnumCallback)(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
DWORD dwValSize,
|
||||
DWORD dwValType,
|
||||
PVOID pData);
|
||||
|
||||
// Enumerates across all values in a key, running the given
|
||||
// RegEnumCallback. Use `pData` to pass application-defined
|
||||
// data to your enumerator callback.
|
||||
BOOL RegGetAllValues(HKEY hKey,
|
||||
RegEnumCallback cb,
|
||||
PVOID pData);
|
||||
|
||||
// Wrapper function for storing reg values, regardless of type
|
||||
BOOL RegStoreValue(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
PVOID pData,
|
||||
DWORD dwValType);
|
||||
|
||||
// Used primarily by RegEnumCallback, hence the hardcoded
|
||||
// var names.
|
||||
// You might want to check out one of the Get*Config functions
|
||||
// for more background on how to use this, but it should make the
|
||||
// callback function as easy as:
|
||||
//
|
||||
// CopyIfMatch(hKey, myStruct,
|
||||
// myField, REG_SZ) // or any type
|
||||
// else CopyIfMatch(hKey, myStruct,
|
||||
// myOtherField, REG_DWORD) // also note: no semicolons
|
||||
// // ... and so on
|
||||
#define CopyIfMatch(hk,x,name,type) \
|
||||
if (!_tcsncmp(_T(#name), \
|
||||
szValName, \
|
||||
_tcslen(_T(#name))) \
|
||||
&& (dwValType & 0xfff) == type) { \
|
||||
if (!CopyRegValue(hk, \
|
||||
&((x)->name), \
|
||||
_T(#name), \
|
||||
type, \
|
||||
dwValSize)) { \
|
||||
return FALSE; \
|
||||
} \
|
||||
}
|
||||
|
||||
// Helper macro for Save*Config functions. Assumes a BOOL-returning
|
||||
// function in a vacuum.
|
||||
#define StoreConfig(hk,x,name,type) \
|
||||
if (!RegStoreValue(hk, _T(#name), &(x)->name, type)) { \
|
||||
DWORD dwRegErr = GetLastError(); \
|
||||
RegCloseKey(hk); \
|
||||
return FALSE; \
|
||||
}
|
||||
|
||||
#define ROOT_KEYNAME "SOFTWARE\\Grabby"
|
||||
// Hack to handle REG_SZ values that are actually TCHAR[MAX_PATH].
|
||||
#define REG_PATH_SZ (0xf000 & REG_SZ)
|
65
CommonCfg/UploadConfig.c
Normal file
65
CommonCfg/UploadConfig.c
Normal file
|
@ -0,0 +1,65 @@
|
|||
#include "stdafx.h"
|
||||
|
||||
static BOOL
|
||||
UploadConfigCb(HKEY hKey,
|
||||
LPTSTR szValName,
|
||||
DWORD dwValSize,
|
||||
DWORD dwValType,
|
||||
PVOID pData)
|
||||
{
|
||||
UploadConfig *ucfg = pData;
|
||||
if (!ucfg) return FALSE;
|
||||
|
||||
CopyIfMatch(hKey, ucfg,
|
||||
Name, REG_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
URL, REG_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
Method, REG_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
Username, REG_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
Password, REG_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
HTTPAuthMethod, REG_DWORD)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
Headers, REG_MULTI_SZ)
|
||||
else CopyIfMatch(hKey, ucfg,
|
||||
Parameters, REG_MULTI_SZ)
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
UploadConfig *
|
||||
GetUploadConfig(void)
|
||||
{
|
||||
|
||||
HKEY hkUploadKey = NULL;
|
||||
HANDLE hHeap = GetProcessHeap();
|
||||
LONG lRes;
|
||||
UploadConfig *ucfg = HeapAlloc(hHeap,
|
||||
HEAP_ZERO_MEMORY,
|
||||
sizeof(UploadConfig));
|
||||
|
||||
if (!ucfg) return NULL;
|
||||
|
||||
// TODO: defaults?
|
||||
lRes = RegOpenKeyEx(HKEY_CURRENT_USER,
|
||||
_T(ROOT_KEYNAME "\\Upload"),
|
||||
0,
|
||||
KEY_READ,
|
||||
&hkUploadKey);
|
||||
|
||||
if (lRes) {
|
||||
SetLastError(lRes);
|
||||
HeapFree(hHeap, 0, ucfg);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!RegGetAllValues(hkUploadKey, UploadConfigCb, ucfg)) {
|
||||
HeapFree(hHeap, 0, ucfg);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return ucfg;
|
||||
}
|
1
CommonCfg/stdafx.c
Normal file
1
CommonCfg/stdafx.c
Normal file
|
@ -0,0 +1 @@
|
|||
#include "stdafx.h"
|
17
CommonCfg/stdafx.h
Normal file
17
CommonCfg/stdafx.h
Normal file
|
@ -0,0 +1,17 @@
|
|||
// stdafx.h : include file for standard system include files,
|
||||
// or project specific include files that are used frequently, but
|
||||
// are changed infrequently
|
||||
//
|
||||
|
||||
#pragma once
|
||||
|
||||
|
||||
#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers
|
||||
#include <Windows.h>
|
||||
#include <tchar.h>
|
||||
#include <ShlObj.h>
|
||||
#include <shlwapi.h>
|
||||
|
||||
// TODO: reference additional headers your program requires here
|
||||
#include "RegHelper.h"
|
||||
#include "Export/Config.h"
|
18
Grabby.sln
18
Grabby.sln
|
@ -1,5 +1,13 @@
|
|||
Microsoft Visual Studio Solution File, Format Version 8.00
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Grabby", "Grabby.vcproj", "{700E5DD7-DD00-46D9-92DF-2C132940F53D}"
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Grabby", "Grabby\Grabby.vcproj", "{700E5DD7-DD00-46D9-92DF-2C132940F53D}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "GrbyCfg", "GrbyCfg\GrbyCfg.vcproj", "{BBB3E933-71CC-4EF7-BF56-52371B9AF938}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CommonCfg", "CommonCfg\CommonCfg.vcproj", "{61829180-05C1-4865-B9C3-FEB983AD6997}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
|
@ -13,6 +21,14 @@ Global
|
|||
{700E5DD7-DD00-46D9-92DF-2C132940F53D}.Debug.Build.0 = Debug|Win32
|
||||
{700E5DD7-DD00-46D9-92DF-2C132940F53D}.Release.ActiveCfg = Release|Win32
|
||||
{700E5DD7-DD00-46D9-92DF-2C132940F53D}.Release.Build.0 = Release|Win32
|
||||
{BBB3E933-71CC-4EF7-BF56-52371B9AF938}.Debug.ActiveCfg = Debug|Win32
|
||||
{BBB3E933-71CC-4EF7-BF56-52371B9AF938}.Debug.Build.0 = Debug|Win32
|
||||
{BBB3E933-71CC-4EF7-BF56-52371B9AF938}.Release.ActiveCfg = Release|Win32
|
||||
{BBB3E933-71CC-4EF7-BF56-52371B9AF938}.Release.Build.0 = Release|Win32
|
||||
{61829180-05C1-4865-B9C3-FEB983AD6997}.Debug.ActiveCfg = Debug|Win32
|
||||
{61829180-05C1-4865-B9C3-FEB983AD6997}.Debug.Build.0 = Debug|Win32
|
||||
{61829180-05C1-4865-B9C3-FEB983AD6997}.Release.ActiveCfg = Release|Win32
|
||||
{61829180-05C1-4865-B9C3-FEB983AD6997}.Release.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
EndGlobalSection
|
||||
|
|
|
@ -5,6 +5,7 @@
|
|||
#include "Bitmap.h"
|
||||
#include "Overlay.h"
|
||||
#include "Grabby.h"
|
||||
#include <Config.h>
|
||||
|
||||
/**
|
||||
* Print an error with a given context before bailing out
|
||||
|
@ -43,7 +44,7 @@ void Die(LPTSTR lpContextMsg)
|
|||
_T("Catastrophic Error"),
|
||||
MB_OK | MB_ICONERROR);
|
||||
} else {
|
||||
_sntprintf(lpszFullMsg, iFullLen, lpszFmt, lpContextMsg, lpszError);
|
||||
StringCchPrintf(lpszFullMsg, iFullLen, lpszFmt, lpContextMsg, lpszError);
|
||||
MessageBox(NULL,
|
||||
lpszFullMsg,
|
||||
_T("Fatal Error"),
|
||||
|
@ -62,16 +63,24 @@ int APIENTRY _tWinMain(HINSTANCE hInstance,
|
|||
SYSTEMTIME stNow = {0};
|
||||
RECT capRegion = {0};
|
||||
Screen *scrn = CreateScreen();
|
||||
#define OUTPUT_DIR_LEN 96
|
||||
TCHAR szOutputDir[OUTPUT_DIR_LEN + 1];
|
||||
#define FULL_OUT_PATH_LEN OUTPUT_DIR_LEN + 24
|
||||
TCHAR szFullOutPath[FULL_OUT_PATH_LEN + 1];
|
||||
Config *cfg;
|
||||
TCHAR szFullOutPath[MAX_PATH];
|
||||
HRESULT hRes;
|
||||
|
||||
if (!scrn) {
|
||||
Die("Couldn't get screen information");
|
||||
}
|
||||
|
||||
cfg = GetConfig();
|
||||
if (!cfg) {
|
||||
Die("Couldn't get config");
|
||||
}
|
||||
|
||||
if (!PathFileExists(cfg->ScreenshotDir) &&
|
||||
!CreateDirectory(cfg->ScreenshotDir, NULL)) {
|
||||
Die("Couldn't create configured folder");
|
||||
}
|
||||
|
||||
switch (CreateOverlay(hInstance, scrn)) {
|
||||
case -1:
|
||||
Die("Couldn't create overlay window");
|
||||
|
@ -86,16 +95,12 @@ int APIENTRY _tWinMain(HINSTANCE hInstance,
|
|||
|
||||
GetChosenRect(&capRegion);
|
||||
|
||||
if (!GetTempPath(OUTPUT_DIR_LEN, szOutputDir)) {
|
||||
Die("Couldn't get temporary directory");
|
||||
}
|
||||
|
||||
GetLocalTime(&stNow);
|
||||
|
||||
hRes = StringCchPrintf(szFullOutPath,
|
||||
FULL_OUT_PATH_LEN,
|
||||
"%s\\scrn_%04d%02d%02d_%02d%02d%02d.bmp",
|
||||
szOutputDir,
|
||||
MAX_PATH,
|
||||
"%s\\Screenshot at %04d-%02d-%02d %02d.%02d.%02d.bmp",
|
||||
cfg->ScreenshotDir,
|
||||
stNow.wYear,
|
||||
stNow.wMonth,
|
||||
stNow.wDay,
|
Before Width: | Height: | Size: 23 KiB After Width: | Height: | Size: 23 KiB |
|
@ -1,4 +1,4 @@
|
|||
//Microsoft Visual C++ generated resource script.
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
|
@ -10,12 +10,58 @@
|
|||
#define APSTUDIO_HIDDEN_SYMBOLS
|
||||
#include "windows.h"
|
||||
#undef APSTUDIO_HIDDEN_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// Japanese resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_JPN)
|
||||
LANGUAGE 17, 1
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_JAPANESE, SUBLANG_DEFAULT
|
||||
#pragma code_page(932)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#define APSTUDIO_HIDDEN_SYMBOLS\r\n"
|
||||
"#include ""windows.h""\r\n"
|
||||
"#undef APSTUDIO_HIDDEN_SYMBOLS\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
#endif // Japanese resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
|
@ -24,95 +70,10 @@ LANGUAGE 17, 1
|
|||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
|
||||
IDI_GRABBY ICON "Grabby.ico"
|
||||
IDI_SMALL ICON "small.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Menu
|
||||
//
|
||||
|
||||
IDC_GRABBY MENU
|
||||
BEGIN
|
||||
POPUP "&File"
|
||||
BEGIN
|
||||
MENUITEM "E&xit", IDM_EXIT
|
||||
END
|
||||
POPUP "&Help"
|
||||
BEGIN
|
||||
MENUITEM "&About ...", IDM_ABOUT
|
||||
END
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Accelerator
|
||||
//
|
||||
|
||||
IDC_GRABBY ACCELERATORS
|
||||
BEGIN
|
||||
"?", IDM_ABOUT, ASCII, ALT
|
||||
"/", IDM_ABOUT, ASCII, ALT
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Dialog
|
||||
//
|
||||
|
||||
IDD_ABOUTBOX DIALOG 22, 17, 230, 75
|
||||
STYLE DS_MODALFRAME | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "About"
|
||||
FONT 9, "System"
|
||||
BEGIN
|
||||
ICON IDI_GRABBY,IDC_MYICON,14,9,16,16
|
||||
LTEXT "Grabby Version 1.0",IDC_STATIC,49,10,119,8,SS_NOPREFIX
|
||||
LTEXT "Copyright (C) 2024",IDC_STATIC,49,20,119,8
|
||||
DEFPUSHBUTTON "OK",IDOK,195,6,30,11,WS_GROUP
|
||||
END
|
||||
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#define APSTUDIO_HIDDEN_SYMBOLS\r\n"
|
||||
"#include ""windows.h""\r\n"
|
||||
"#undef APSTUDIO_HIDDEN_SYMBOLS\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// String Table
|
||||
//
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDC_GRABBY "GRABBY"
|
||||
IDS_APP_TITLE "Grabby"
|
||||
END
|
||||
|
||||
#endif
|
||||
IDI_GRABBY ICON "Grabby.ico"
|
||||
IDI_SMALL ICON "small.ico"
|
||||
IDI_ICON1 ICON "icon1.ico"
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
@ -126,3 +87,4 @@ END
|
|||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
|
@ -19,6 +19,7 @@
|
|||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="D:\Projects\curl\include;..\CommonCfg\Export"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_WINDOWS"
|
||||
MinimalRebuild="TRUE"
|
||||
BasicRuntimeChecks="3"
|
||||
|
@ -32,8 +33,10 @@
|
|||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
AdditionalDependencies="libcurl_a.lib shlwapi.lib"
|
||||
OutputFile="$(OutDir)/Grabby.exe"
|
||||
LinkIncremental="2"
|
||||
AdditionalLibraryDirectories="D:\Projects\curl\lib"
|
||||
GenerateDebugInformation="TRUE"
|
||||
ProgramDatabaseFile="$(OutDir)/Grabby.pdb"
|
||||
SubSystem="2"
|
||||
|
@ -67,18 +70,22 @@
|
|||
CharacterSet="2">
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
AdditionalIncludeDirectories="D:\Projects\curl\include;..\CommonCfg\Export"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_WINDOWS"
|
||||
RuntimeLibrary="4"
|
||||
UsePrecompiledHeader="3"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="TRUE"
|
||||
DebugInformationFormat="3"/>
|
||||
DebugInformationFormat="3"
|
||||
CompileAs="1"/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
AdditionalDependencies="libcurl_a.lib shlwapi.lib"
|
||||
OutputFile="$(OutDir)/Grabby.exe"
|
||||
LinkIncremental="1"
|
||||
AdditionalLibraryDirectories="D:\Projects\curl\lib"
|
||||
GenerateDebugInformation="TRUE"
|
||||
SubSystem="2"
|
||||
OptimizeReferences="2"
|
||||
|
@ -107,6 +114,9 @@
|
|||
</Configuration>
|
||||
</Configurations>
|
||||
<References>
|
||||
<ProjectReference
|
||||
ReferencedProjectIdentifier="{61829180-05C1-4865-B9C3-FEB983AD6997}"
|
||||
Name="CommonCfg"/>
|
||||
</References>
|
||||
<Files>
|
||||
<Filter
|
||||
|
@ -159,12 +169,15 @@
|
|||
<File
|
||||
RelativePath=".\Grabby.rc">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\icon1.ico">
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\small.ico">
|
||||
</File>
|
||||
</Filter>
|
||||
<File
|
||||
RelativePath=".\ReadMe.txt">
|
||||
RelativePath="..\ReadMe.txt">
|
||||
</File>
|
||||
</Files>
|
||||
<Globals>
|
BIN
Grabby/icon1.ico
Normal file
BIN
Grabby/icon1.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 766 B |
36
Grabby/resource.h
Normal file
36
Grabby/resource.h
Normal file
|
@ -0,0 +1,36 @@
|
|||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by Grabby.rc
|
||||
//
|
||||
#define IDC_MYICON 2
|
||||
#define IDD_GRABBY_DIALOG 102
|
||||
#define IDS_APP_TITLE 103
|
||||
#define IDM_ABOUT 104
|
||||
#define IDM_EXIT 105
|
||||
#define IDI_GRABBY 107
|
||||
#define IDI_SMALL 108
|
||||
#define IDC_GRABBY 109
|
||||
#define IDR_MAINFRAME 128
|
||||
#define IDI_ICON1 129
|
||||
#define IDC_TABVIEW 1000
|
||||
#define IDC_APPLY 1001
|
||||
#define IDC_EDIT1 1004
|
||||
#define IDC_BUTTON1 1005
|
||||
#define IDC_CHECK1 1006
|
||||
#define IDC_URLINPUT 1007
|
||||
#define IDC_ENCODEFILE 1008
|
||||
#define IDC_COMBO1 1009
|
||||
#define IDC_UPLOADMETHOD 1009
|
||||
#define IDC_STATIC -1
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NO_MFC 1
|
||||
#define _APS_NEXT_RESOURCE_VALUE 132
|
||||
#define _APS_NEXT_COMMAND_VALUE 32771
|
||||
#define _APS_NEXT_CONTROL_VALUE 1010
|
||||
#define _APS_NEXT_SYMED_VALUE 110
|
||||
#endif
|
||||
#endif
|
Before Width: | Height: | Size: 23 KiB After Width: | Height: | Size: 23 KiB |
|
@ -9,6 +9,7 @@
|
|||
#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers
|
||||
// Windows Header Files:
|
||||
#include <windows.h>
|
||||
#include <shlwapi.h>
|
||||
// C RunTime Header Files
|
||||
#include <stdlib.h>
|
||||
#include <malloc.h>
|
||||
|
@ -16,4 +17,4 @@
|
|||
#include <stdio.h>
|
||||
#include <tchar.h>
|
||||
|
||||
#include <Strsafe.h>
|
||||
#include <Strsafe.h>
|
11
GrbyCfg/Dialog.c
Normal file
11
GrbyCfg/Dialog.c
Normal file
|
@ -0,0 +1,11 @@
|
|||
#define _IS_DIALOG_C_
|
||||
#include "stdafx.h"
|
||||
#include "Dialog.h"
|
||||
|
||||
|
||||
void
|
||||
InitUserMsgs(void)
|
||||
{
|
||||
DEFINE_USER_MSG(WMU_SAVE_CONFIG);
|
||||
DEFINE_USER_MSG(WMU_SETTING_CHANGED);
|
||||
}
|
25
GrbyCfg/Dialog.h
Normal file
25
GrbyCfg/Dialog.h
Normal file
|
@ -0,0 +1,25 @@
|
|||
#pragma once
|
||||
|
||||
#define _DLG_MSG_SUFFIX "{990f4b34-579a-4fbc-a5b2-08f46ef5e9c5}"
|
||||
#define USER_MSG_NAME(name) _T( #name _DLG_MSG_SUFFIX )
|
||||
#define DEFINE_USER_MSG(name) {\
|
||||
LPCTSTR name##_MSG = USER_MSG_NAME(name); \
|
||||
name = RegisterWindowMessage(name##_MSG); \
|
||||
}
|
||||
#define DECLARE_USER_MSG(name) \
|
||||
UINT name;
|
||||
|
||||
/* --- */
|
||||
|
||||
DECLARE_USER_MSG(WMU_SAVE_CONFIG)
|
||||
DECLARE_USER_MSG(WMU_SETTING_CHANGED)
|
||||
|
||||
void InitUserMsgs(void);
|
||||
|
||||
#define ChangedSetting(hwnd) \
|
||||
SendMessage(hwnd, \
|
||||
WMU_SETTING_CHANGED, \
|
||||
0, 0)
|
||||
|
||||
#define IsChecked(ref) \
|
||||
(IsDlgButtonChecked(hDlg, ref) == BST_CHECKED)
|
4
GrbyCfg/General.h
Normal file
4
GrbyCfg/General.h
Normal file
|
@ -0,0 +1,4 @@
|
|||
#pragma once
|
||||
|
||||
// Define the dialog proc
|
||||
DEF_DLGPROC(GeneralTab);
|
182
GrbyCfg/GeneralCfg.c
Normal file
182
GrbyCfg/GeneralCfg.c
Normal file
|
@ -0,0 +1,182 @@
|
|||
/* General configuration dialog */
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "GrbyCfg.h"
|
||||
|
||||
int CALLBACK
|
||||
ScreenshotBrowseCallback(HWND hWnd,
|
||||
UINT uMsg,
|
||||
LPARAM lParam,
|
||||
LPARAM lpData)
|
||||
{
|
||||
if (uMsg == BFFM_INITIALIZED && lpData) {
|
||||
// Set root dir
|
||||
SendMessage(hWnd,
|
||||
BFFM_SETSELECTION,
|
||||
1,
|
||||