mirror of
https://github.com/chibicitiberiu/rainmeter-studio.git
synced 2024-02-24 04:33:31 +00:00
Work on trimming native rainmeter library. Incomplete (won't build!!!)
This commit is contained in:
parent
b8c8f2a1b0
commit
dc7eff73b4
@ -32,7 +32,6 @@
|
||||
</ResourceCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="Language.rc" />
|
||||
<ResourceCompile Include="Resource.rc">
|
||||
<ExcludedFromBuild>true</ExcludedFromBuild>
|
||||
</ResourceCompile>
|
||||
|
@ -15,9 +15,6 @@
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="Language.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="Resource.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
|
@ -20,13 +20,10 @@
|
||||
#include "../Common/PathUtil.h"
|
||||
#include "CommandHandler.h"
|
||||
#include "ConfigParser.h"
|
||||
#include "DialogAbout.h"
|
||||
#include "DialogManage.h"
|
||||
#include "Measure.h"
|
||||
#include "Logger.h"
|
||||
#include "Rainmeter.h"
|
||||
#include "System.h"
|
||||
#include "TrayWindow.h"
|
||||
#include "resource.h"
|
||||
|
||||
namespace {
|
||||
@ -708,26 +705,12 @@ void CommandHandler::DoSetWallpaperBang(std::vector<std::wstring>& args, MeterWi
|
||||
|
||||
void CommandHandler::DoAboutBang(std::vector<std::wstring>& args, MeterWindow* meterWindow)
|
||||
{
|
||||
DialogAbout::Open(args.empty() ? L"" : args[0].c_str());
|
||||
LogErrorF(L"!About: about bang is unsupported.");
|
||||
}
|
||||
|
||||
void CommandHandler::DoManageBang(std::vector<std::wstring>& args, MeterWindow* meterWindow)
|
||||
{
|
||||
const size_t argsSize = args.size();
|
||||
if (argsSize >= 2 && argsSize <= 3)
|
||||
{
|
||||
DialogManage::Open(args[0].c_str(),
|
||||
args[1].c_str(),
|
||||
(argsSize == 3) ? args[2].c_str() : L"");
|
||||
}
|
||||
else if (argsSize <= 1)
|
||||
{
|
||||
DialogManage::Open(args.empty() ? L"" : args[0].c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
LogErrorF(meterWindow, L"!Manage: Invalid parameters");
|
||||
}
|
||||
LogErrorF(L"!Manage: manage bang is unsupported.");
|
||||
}
|
||||
|
||||
void CommandHandler::DoSkinMenuBang(std::vector<std::wstring>& args, MeterWindow* skin)
|
||||
|
@ -92,7 +92,7 @@ void ConfigParser::SetBuiltInVariables(const std::wstring& filename, const std::
|
||||
return m_BuiltInVariables.insert(std::make_pair(name, value));
|
||||
};
|
||||
|
||||
insertVariable(L"PROGRAMPATH", GetRainmeter().GetPath());
|
||||
insertVariable(L"PROGRAMPATH", GetRainmeter().GetWorkDirectory());
|
||||
insertVariable(L"PROGRAMDRIVE", GetRainmeter().GetDrive());
|
||||
insertVariable(L"SETTINGSPATH", GetRainmeter().GetSettingsPath());
|
||||
insertVariable(L"SKINSPATH", GetRainmeter().GetSkinPath());
|
||||
|
@ -1,690 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2013 Rainmeter Team
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "StdAfx.h"
|
||||
#include "../Common/MenuTemplate.h"
|
||||
#include "../Common/Gfx/CanvasD2D.h"
|
||||
#include "ContextMenu.h"
|
||||
#include "Rainmeter.h"
|
||||
#include "Litestep.h"
|
||||
#include "MeterWindow.h"
|
||||
#include "System.h"
|
||||
#include "TrayWindow.h"
|
||||
#include "resource.h"
|
||||
|
||||
ContextMenu::ContextMenu() :
|
||||
m_MenuActive(false)
|
||||
{
|
||||
}
|
||||
|
||||
/*
|
||||
** Opens the context menu in given coordinates.
|
||||
*/
|
||||
void ContextMenu::ShowMenu(POINT pos, MeterWindow* meterWindow)
|
||||
{
|
||||
static const MenuTemplate s_Menu[] =
|
||||
{
|
||||
MENU_ITEM(IDM_MANAGE, ID_STR_MANAGE),
|
||||
MENU_ITEM(IDM_ABOUT, ID_STR_ABOUT),
|
||||
MENU_ITEM(IDM_SHOW_HELP, ID_STR_HELP),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_SUBMENU(ID_STR_SKINS,
|
||||
MENU_ITEM_GRAYED(0, ID_STR_NOSKINS),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_OPENSKINSFOLDER, ID_STR_OPENFOLDER),
|
||||
MENU_ITEM(IDM_DISABLEDRAG, ID_STR_DISABLEDRAGGING)),
|
||||
MENU_SUBMENU(ID_STR_THEMES,
|
||||
MENU_ITEM_GRAYED(0, ID_STR_NOTHEMES)),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_EDITCONFIG, ID_STR_EDITSETTINGS),
|
||||
MENU_ITEM(IDM_REFRESH, ID_STR_REFRESHALL),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_SUBMENU(ID_STR_LOGGING,
|
||||
MENU_ITEM(IDM_SHOWLOGFILE, ID_STR_SHOWLOGFILE),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_STARTLOG, ID_STR_STARTLOGGING),
|
||||
MENU_ITEM(IDM_STOPLOG, ID_STR_STOPLOGGING),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_DELETELOGFILE, ID_STR_DELETELOGFILE),
|
||||
MENU_ITEM(IDM_DEBUGLOG, ID_STR_DEBUGMODE)),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_QUIT, ID_STR_EXIT)
|
||||
};
|
||||
|
||||
if (m_MenuActive || (meterWindow && meterWindow->IsClosing())) return;
|
||||
|
||||
// Show context menu, if no actions were executed
|
||||
HMENU menu = MenuTemplate::CreateMenu(s_Menu, _countof(s_Menu), GetString);
|
||||
if (!menu) return;
|
||||
|
||||
m_MenuActive = true;
|
||||
Rainmeter& rainmeter = GetRainmeter();
|
||||
|
||||
SetMenuDefaultItem(menu, IDM_MANAGE, MF_BYCOMMAND);
|
||||
|
||||
if (_waccess(GetLogger().GetLogFilePath().c_str(), 0) == -1)
|
||||
{
|
||||
EnableMenuItem(menu, IDM_SHOWLOGFILE, MF_BYCOMMAND | MF_GRAYED);
|
||||
EnableMenuItem(menu, IDM_DELETELOGFILE, MF_BYCOMMAND | MF_GRAYED);
|
||||
EnableMenuItem(menu, IDM_STOPLOG, MF_BYCOMMAND | MF_GRAYED);
|
||||
}
|
||||
else
|
||||
{
|
||||
EnableMenuItem(
|
||||
menu,
|
||||
(GetLogger().IsLogToFile()) ? IDM_STARTLOG : IDM_STOPLOG,
|
||||
MF_BYCOMMAND | MF_GRAYED);
|
||||
}
|
||||
|
||||
if (rainmeter.m_Debug)
|
||||
{
|
||||
CheckMenuItem(menu, IDM_DEBUGLOG, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
HMENU allSkinsMenu = GetSubMenu(menu, 4);
|
||||
if (allSkinsMenu)
|
||||
{
|
||||
if (!rainmeter.m_SkinRegistry.IsEmpty())
|
||||
{
|
||||
DeleteMenu(allSkinsMenu, 0, MF_BYPOSITION); // "No skins available" menuitem
|
||||
CreateAllSkinsMenu(allSkinsMenu);
|
||||
}
|
||||
|
||||
if (rainmeter.m_DisableDragging)
|
||||
{
|
||||
CheckMenuItem(allSkinsMenu, IDM_DISABLEDRAG, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
}
|
||||
|
||||
HMENU layoutMenu = GetSubMenu(menu, 5);
|
||||
if (layoutMenu)
|
||||
{
|
||||
if (!rainmeter.m_Layouts.empty())
|
||||
{
|
||||
DeleteMenu(layoutMenu, 0, MF_BYPOSITION); // "No layouts available" menuitem
|
||||
CreateLayoutMenu(layoutMenu);
|
||||
}
|
||||
}
|
||||
|
||||
if (meterWindow)
|
||||
{
|
||||
HMENU rainmeterMenu = menu;
|
||||
menu = CreateSkinMenu(meterWindow, 0, allSkinsMenu);
|
||||
|
||||
InsertMenu(menu, IDM_CLOSESKIN, MF_BYCOMMAND | MF_POPUP, (UINT_PTR)rainmeterMenu, L"Rainmeter");
|
||||
InsertMenu(menu, IDM_CLOSESKIN, MF_BYCOMMAND | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
else
|
||||
{
|
||||
InsertMenu(menu, 12, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
|
||||
// Create a menu for all active skins
|
||||
int index = 0;
|
||||
std::map<std::wstring, MeterWindow*>::const_iterator iter = rainmeter.m_MeterWindows.begin();
|
||||
for (; iter != rainmeter.m_MeterWindows.end(); ++iter)
|
||||
{
|
||||
MeterWindow* mw = ((*iter).second);
|
||||
HMENU skinMenu = CreateSkinMenu(mw, index, allSkinsMenu);
|
||||
InsertMenu(menu, 12, MF_BYPOSITION | MF_POPUP, (UINT_PTR)skinMenu, mw->GetFolderPath().c_str());
|
||||
++index;
|
||||
}
|
||||
|
||||
// Add update notification item
|
||||
if (rainmeter.m_NewVersion)
|
||||
{
|
||||
InsertMenu(menu, 0, MF_BYPOSITION, IDM_NEW_VERSION, GetString(ID_STR_UPDATEAVAILABLE));
|
||||
HiliteMenuItem(rainmeter.GetTrayWindow()->GetWindow(), menu, 0, MF_BYPOSITION | MF_HILITE);
|
||||
InsertMenu(menu, 1, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
HWND hWnd = WindowFromPoint(pos);
|
||||
if (hWnd != nullptr)
|
||||
{
|
||||
MeterWindow* mw = rainmeter.GetMeterWindow(hWnd);
|
||||
if (mw)
|
||||
{
|
||||
// Cancel the mouse event beforehand
|
||||
mw->SetMouseLeaveEvent(true);
|
||||
}
|
||||
}
|
||||
|
||||
DisplayMenu(pos, menu, meterWindow ? meterWindow->GetWindow() : rainmeter.m_TrayWindow->GetWindow());
|
||||
DestroyMenu(menu);
|
||||
|
||||
m_MenuActive = false;
|
||||
}
|
||||
|
||||
void ContextMenu::ShowSkinCustomMenu(POINT pos, MeterWindow* meterWindow)
|
||||
{
|
||||
if (m_MenuActive || meterWindow->IsClosing()) return;
|
||||
|
||||
m_MenuActive = true;
|
||||
|
||||
HMENU menu = CreatePopupMenu();
|
||||
AppendSkinCustomMenu(meterWindow, 0, menu, true);
|
||||
|
||||
DisplayMenu(pos, menu, meterWindow->GetWindow());
|
||||
DestroyMenu(menu);
|
||||
|
||||
m_MenuActive = false;
|
||||
}
|
||||
|
||||
void ContextMenu::DisplayMenu(POINT pos, HMENU menu, HWND parentWindow)
|
||||
{
|
||||
// Set the window to foreground
|
||||
HWND foregroundWindow = GetForegroundWindow();
|
||||
if (foregroundWindow != parentWindow)
|
||||
{
|
||||
const DWORD foregroundThreadID = GetWindowThreadProcessId(foregroundWindow, nullptr);
|
||||
const DWORD currentThreadID = GetCurrentThreadId();
|
||||
AttachThreadInput(currentThreadID, foregroundThreadID, TRUE);
|
||||
SetForegroundWindow(parentWindow);
|
||||
AttachThreadInput(currentThreadID, foregroundThreadID, FALSE);
|
||||
}
|
||||
|
||||
// Show context menu
|
||||
TrackPopupMenu(
|
||||
menu,
|
||||
TPM_RIGHTBUTTON | TPM_LEFTALIGN | (*GetString(ID_STR_ISRTL) == L'1' ? TPM_LAYOUTRTL : 0),
|
||||
pos.x,
|
||||
pos.y,
|
||||
0,
|
||||
parentWindow,
|
||||
nullptr);
|
||||
}
|
||||
|
||||
HMENU ContextMenu::CreateSkinMenu(MeterWindow* meterWindow, int index, HMENU menu)
|
||||
{
|
||||
static const MenuTemplate s_Menu[] =
|
||||
{
|
||||
MENU_ITEM(IDM_SKIN_OPENSKINSFOLDER, 0),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_SUBMENU(ID_STR_VARIANTS,
|
||||
MENU_SEPARATOR()),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_SUBMENU(ID_STR_SETTINGS,
|
||||
MENU_SUBMENU(ID_STR_POSITION,
|
||||
MENU_SUBMENU(ID_STR_DISPLAYMONITOR,
|
||||
MENU_ITEM(IDM_SKIN_MONITOR_PRIMARY, ID_STR_USEDEFAULTMONITOR),
|
||||
MENU_ITEM(ID_MONITOR_FIRST, ID_STR_VIRTUALSCREEN),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_MONITOR_AUTOSELECT, ID_STR_AUTOSELECTMONITOR)),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_VERYTOPMOST, ID_STR_STAYTOPMOST),
|
||||
MENU_ITEM(IDM_SKIN_TOPMOST, ID_STR_TOPMOST),
|
||||
MENU_ITEM(IDM_SKIN_NORMAL, ID_STR_NORMAL),
|
||||
MENU_ITEM(IDM_SKIN_BOTTOM, ID_STR_BOTTOM),
|
||||
MENU_ITEM(IDM_SKIN_ONDESKTOP, ID_STR_ONDESKTOP),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_FROMRIGHT, ID_STR_FROMRIGHT),
|
||||
MENU_ITEM(IDM_SKIN_FROMBOTTOM, ID_STR_FROMBOTTOM),
|
||||
MENU_ITEM(IDM_SKIN_XPERCENTAGE, ID_STR_XASPERCENTAGE),
|
||||
MENU_ITEM(IDM_SKIN_YPERCENTAGE, ID_STR_YASPERCENTAGE)),
|
||||
MENU_SUBMENU(ID_STR_TRANSPARENCY,
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_0, ID_STR_0PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_10, ID_STR_10PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_20, ID_STR_20PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_30, ID_STR_30PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_40, ID_STR_40PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_50, ID_STR_50PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_60, ID_STR_60PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_70, ID_STR_70PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_80, ID_STR_80PERCENT),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_90, ID_STR_90PERCENT),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_FADEIN, ID_STR_FADEIN),
|
||||
MENU_ITEM(IDM_SKIN_TRANSPARENCY_FADEOUT, ID_STR_FADEOUT)),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_HIDEONMOUSE, ID_STR_HIDEONMOUSEOVER),
|
||||
MENU_ITEM(IDM_SKIN_DRAGGABLE, ID_STR_DRAGGABLE),
|
||||
MENU_ITEM(IDM_SKIN_REMEMBERPOSITION, ID_STR_SAVEPOSITION),
|
||||
MENU_ITEM(IDM_SKIN_SNAPTOEDGES, ID_STR_SNAPTOEDGES),
|
||||
MENU_ITEM(IDM_SKIN_CLICKTHROUGH, ID_STR_CLICKTHROUGH),
|
||||
MENU_ITEM(IDM_SKIN_KEEPONSCREEN, ID_STR_KEEPONSCREEN),
|
||||
MENU_ITEM(IDM_SKIN_USED2D, ID_STR_USED2D)),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_SKIN_MANAGESKIN, ID_STR_MANAGESKIN),
|
||||
MENU_ITEM(IDM_SKIN_EDITSKIN, ID_STR_EDITSKIN),
|
||||
MENU_ITEM(IDM_SKIN_REFRESH, ID_STR_REFRESHSKIN),
|
||||
MENU_SEPARATOR(),
|
||||
MENU_ITEM(IDM_CLOSESKIN, ID_STR_UNLOADSKIN)
|
||||
};
|
||||
|
||||
HMENU skinMenu = MenuTemplate::CreateMenu(s_Menu, _countof(s_Menu), GetString);
|
||||
if (!skinMenu) return nullptr;
|
||||
|
||||
// Tick the position
|
||||
HMENU settingsMenu = GetSubMenu(skinMenu, 4);
|
||||
if (settingsMenu)
|
||||
{
|
||||
HMENU posMenu = GetSubMenu(settingsMenu, 0);
|
||||
if (posMenu)
|
||||
{
|
||||
const UINT checkPos = IDM_SKIN_NORMAL - (UINT)meterWindow->GetWindowZPosition();
|
||||
CheckMenuRadioItem(posMenu, checkPos, checkPos, checkPos, MF_BYCOMMAND);
|
||||
|
||||
if (meterWindow->GetXFromRight()) CheckMenuItem(posMenu, IDM_SKIN_FROMRIGHT, MF_BYCOMMAND | MF_CHECKED);
|
||||
if (meterWindow->GetYFromBottom()) CheckMenuItem(posMenu, IDM_SKIN_FROMBOTTOM, MF_BYCOMMAND | MF_CHECKED);
|
||||
if (meterWindow->GetXPercentage()) CheckMenuItem(posMenu, IDM_SKIN_XPERCENTAGE, MF_BYCOMMAND | MF_CHECKED);
|
||||
if (meterWindow->GetYPercentage()) CheckMenuItem(posMenu, IDM_SKIN_YPERCENTAGE, MF_BYCOMMAND | MF_CHECKED);
|
||||
|
||||
HMENU monitorMenu = GetSubMenu(posMenu, 0);
|
||||
if (monitorMenu)
|
||||
{
|
||||
CreateMonitorMenu(monitorMenu, meterWindow);
|
||||
}
|
||||
}
|
||||
|
||||
// Tick the transparency
|
||||
HMENU alphaMenu = GetSubMenu(settingsMenu, 1);
|
||||
if (alphaMenu)
|
||||
{
|
||||
UINT checkPos = (UINT)(10 - meterWindow->GetAlphaValue() / 25.5);
|
||||
checkPos = min(9, checkPos);
|
||||
checkPos = max(0, checkPos);
|
||||
CheckMenuRadioItem(alphaMenu, checkPos, checkPos, checkPos, MF_BYPOSITION);
|
||||
|
||||
switch (meterWindow->GetWindowHide())
|
||||
{
|
||||
case HIDEMODE_FADEIN:
|
||||
CheckMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEIN, MF_BYCOMMAND | MF_CHECKED);
|
||||
EnableMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEOUT, MF_BYCOMMAND | MF_GRAYED);
|
||||
break;
|
||||
|
||||
case HIDEMODE_FADEOUT:
|
||||
CheckMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEOUT, MF_BYCOMMAND | MF_CHECKED);
|
||||
EnableMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEIN, MF_BYCOMMAND | MF_GRAYED);
|
||||
break;
|
||||
|
||||
case HIDEMODE_HIDE:
|
||||
EnableMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEIN, MF_BYCOMMAND | MF_GRAYED);
|
||||
EnableMenuItem(alphaMenu, IDM_SKIN_TRANSPARENCY_FADEOUT, MF_BYCOMMAND | MF_GRAYED);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Tick the settings
|
||||
switch (meterWindow->GetWindowHide())
|
||||
{
|
||||
case HIDEMODE_HIDE:
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_HIDEONMOUSE, MF_BYCOMMAND | MF_CHECKED);
|
||||
break;
|
||||
|
||||
case HIDEMODE_FADEIN:
|
||||
case HIDEMODE_FADEOUT:
|
||||
EnableMenuItem(settingsMenu, IDM_SKIN_HIDEONMOUSE, MF_BYCOMMAND | MF_GRAYED);
|
||||
break;
|
||||
}
|
||||
|
||||
if (meterWindow->GetSnapEdges())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_SNAPTOEDGES, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (meterWindow->GetSavePosition())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_REMEMBERPOSITION, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (GetRainmeter().m_DisableDragging)
|
||||
{
|
||||
EnableMenuItem(settingsMenu, IDM_SKIN_DRAGGABLE, MF_BYCOMMAND | MF_GRAYED);
|
||||
}
|
||||
else if (meterWindow->GetWindowDraggable())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_DRAGGABLE, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (meterWindow->GetClickThrough())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_CLICKTHROUGH, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (meterWindow->GetKeepOnScreen())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_KEEPONSCREEN, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (Gfx::CanvasD2D::Initialize())
|
||||
{
|
||||
if (!GetRainmeter().GetUseD2D())
|
||||
{
|
||||
EnableMenuItem(settingsMenu, IDM_SKIN_USED2D, MF_BYCOMMAND | MF_GRAYED);
|
||||
}
|
||||
else if (meterWindow->GetUseD2D())
|
||||
{
|
||||
CheckMenuItem(settingsMenu, IDM_SKIN_USED2D, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
DeleteMenu(settingsMenu, IDM_SKIN_USED2D, MF_BYCOMMAND);
|
||||
}
|
||||
Gfx::CanvasD2D::Finalize();
|
||||
}
|
||||
|
||||
// Add the name of the Skin to the menu
|
||||
const std::wstring& skinName = meterWindow->GetFolderPath();
|
||||
ModifyMenu(skinMenu, IDM_SKIN_OPENSKINSFOLDER, MF_BYCOMMAND, IDM_SKIN_OPENSKINSFOLDER, skinName.c_str());
|
||||
SetMenuDefaultItem(skinMenu, IDM_SKIN_OPENSKINSFOLDER, FALSE);
|
||||
|
||||
// Remove dummy menuitem from the variants menu
|
||||
HMENU variantsMenu = GetSubMenu(skinMenu, 2);
|
||||
if (variantsMenu)
|
||||
{
|
||||
DeleteMenu(variantsMenu, 0, MF_BYPOSITION);
|
||||
}
|
||||
|
||||
// Give the menuitem the unique id that depends on the skin
|
||||
ChangeSkinIndex(skinMenu, index);
|
||||
|
||||
// Add the variants menu
|
||||
if (variantsMenu)
|
||||
{
|
||||
const SkinRegistry::Folder& skinFolder = *GetRainmeter().m_SkinRegistry.FindFolder(skinName);
|
||||
for (int i = 0, isize = (int)skinFolder.files.size(); i < isize; ++i)
|
||||
{
|
||||
InsertMenu(variantsMenu, i, MF_BYPOSITION, skinFolder.baseID + i, skinFolder.files[i].c_str());
|
||||
}
|
||||
|
||||
if (skinFolder.active)
|
||||
{
|
||||
UINT checkPos = skinFolder.active - 1;
|
||||
CheckMenuRadioItem(variantsMenu, checkPos, checkPos, checkPos, MF_BYPOSITION);
|
||||
}
|
||||
}
|
||||
|
||||
// Add skin root menu
|
||||
int itemCount = GetMenuItemCount(menu);
|
||||
if (itemCount > 0)
|
||||
{
|
||||
std::wstring root = meterWindow->GetFolderPath();
|
||||
std::wstring::size_type pos = root.find_first_of(L'\\');
|
||||
if (pos != std::wstring::npos)
|
||||
{
|
||||
root.erase(pos);
|
||||
}
|
||||
|
||||
for (int i = 0; i < itemCount; ++i)
|
||||
{
|
||||
const UINT state = GetMenuState(menu, i, MF_BYPOSITION);
|
||||
if (state == 0xFFFFFFFF || (state & MF_POPUP) == 0) break;
|
||||
|
||||
WCHAR buffer[MAX_PATH];
|
||||
if (GetMenuString(menu, i, buffer, MAX_PATH, MF_BYPOSITION))
|
||||
{
|
||||
if (_wcsicmp(root.c_str(), buffer) == 0)
|
||||
{
|
||||
HMENU skinRootMenu = GetSubMenu(menu, i);
|
||||
if (skinRootMenu)
|
||||
{
|
||||
InsertMenu(skinMenu, 3, MF_BYPOSITION | MF_POPUP, (UINT_PTR)skinRootMenu, root.c_str());
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
AppendSkinCustomMenu(meterWindow, index, skinMenu, false);
|
||||
|
||||
return skinMenu;
|
||||
}
|
||||
|
||||
void ContextMenu::AppendSkinCustomMenu(
|
||||
MeterWindow* meterWindow, int index, HMENU menu, bool standaloneMenu)
|
||||
{
|
||||
// Add custom actions to the context menu
|
||||
std::wstring contextTitle = meterWindow->GetParser().ReadString(L"Rainmeter", L"ContextTitle", L"");
|
||||
if (contextTitle.empty())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
auto isTitleSeparator = [](const std::wstring& title)
|
||||
{
|
||||
return title.find_first_not_of(L'-') == std::wstring::npos;
|
||||
};
|
||||
|
||||
std::wstring contextAction = meterWindow->GetParser().ReadString(L"Rainmeter", L"ContextAction", L"");
|
||||
if (contextAction.empty() && !isTitleSeparator(contextTitle))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
std::vector<std::wstring> cTitles;
|
||||
WCHAR buffer[128];
|
||||
int i = 1;
|
||||
|
||||
while (!contextTitle.empty() &&
|
||||
(!contextAction.empty() || isTitleSeparator(contextTitle)) &&
|
||||
(IDM_SKIN_CUSTOMCONTEXTMENU_FIRST + i - 1) <= IDM_SKIN_CUSTOMCONTEXTMENU_LAST) // Set maximum context items in resource.h
|
||||
{
|
||||
// Trim long titles
|
||||
if (contextTitle.size() > 30)
|
||||
{
|
||||
contextTitle.replace(27, contextTitle.size() - 27, L"...");
|
||||
}
|
||||
|
||||
cTitles.push_back(contextTitle);
|
||||
|
||||
_snwprintf_s(buffer, _TRUNCATE, L"ContextTitle%i", ++i);
|
||||
contextTitle = meterWindow->GetParser().ReadString(L"Rainmeter", buffer, L"");
|
||||
_snwprintf_s(buffer, _TRUNCATE, L"ContextAction%i", i);
|
||||
contextAction = meterWindow->GetParser().ReadString(L"Rainmeter", buffer, L"");
|
||||
}
|
||||
|
||||
// Build a sub-menu if more than three items
|
||||
const size_t titleSize = cTitles.size();
|
||||
if (titleSize <= 3 || standaloneMenu)
|
||||
{
|
||||
size_t position = 0;
|
||||
for (size_t i = 0; i < titleSize; ++i)
|
||||
{
|
||||
if (isTitleSeparator(cTitles[i]))
|
||||
{
|
||||
if (standaloneMenu)
|
||||
{
|
||||
AppendMenu(menu, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Separators not allowed in main top-level menu
|
||||
--position;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
const UINT_PTR id = (index << 16) | (IDM_SKIN_CUSTOMCONTEXTMENU_FIRST + i);
|
||||
InsertMenu(menu, (UINT)(position + 1), MF_BYPOSITION | MF_STRING, id, cTitles[i].c_str());
|
||||
}
|
||||
|
||||
++position;
|
||||
}
|
||||
|
||||
if (position != 0 && !standaloneMenu)
|
||||
{
|
||||
InsertMenu(menu, 1, MF_BYPOSITION | MF_STRING | MF_GRAYED, 0, L"Custom skin actions");
|
||||
InsertMenu(menu, 1, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
HMENU customMenu = CreatePopupMenu();
|
||||
InsertMenu(menu, 1, MF_BYPOSITION | MF_POPUP, (UINT_PTR)customMenu, L"Custom skin actions");
|
||||
|
||||
for (size_t i = 0; i < titleSize; ++i)
|
||||
{
|
||||
if (isTitleSeparator(cTitles[i]))
|
||||
{
|
||||
AppendMenu(customMenu, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
else
|
||||
{
|
||||
const UINT_PTR id = (index << 16) | (IDM_SKIN_CUSTOMCONTEXTMENU_FIRST + i);
|
||||
AppendMenu(customMenu, MF_BYPOSITION | MF_STRING, id, cTitles[i].c_str());
|
||||
}
|
||||
}
|
||||
|
||||
InsertMenu(menu, 1, MF_BYPOSITION | MF_SEPARATOR, 0, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
int ContextMenu::CreateAllSkinsMenuRecursive(HMENU skinMenu, int index)
|
||||
{
|
||||
SkinRegistry& skinRegistry = GetRainmeter().m_SkinRegistry;
|
||||
const int initialLevel = skinRegistry.GetFolder(index).level;
|
||||
int menuIndex = 0;
|
||||
|
||||
const size_t max = skinRegistry.GetFolderCount();
|
||||
while (index < max)
|
||||
{
|
||||
const SkinRegistry::Folder& skinFolder = skinRegistry.GetFolder(index);
|
||||
if (skinFolder.level != initialLevel)
|
||||
{
|
||||
return index - 1;
|
||||
}
|
||||
|
||||
HMENU subMenu = CreatePopupMenu();
|
||||
|
||||
// Add current folder
|
||||
InsertMenu(skinMenu, menuIndex, MF_POPUP | MF_BYPOSITION, (UINT_PTR)subMenu, skinFolder.name.c_str());
|
||||
|
||||
// Add subfolders
|
||||
const bool hasSubfolder = (index + 1) < max && skinRegistry.GetFolder(index + 1).level == initialLevel + 1;
|
||||
if (hasSubfolder)
|
||||
{
|
||||
index = CreateAllSkinsMenuRecursive(subMenu, index + 1);
|
||||
}
|
||||
|
||||
// Add files
|
||||
{
|
||||
int fileIndex = 0;
|
||||
const int fileCount = (int)skinFolder.files.size();
|
||||
for ( ; fileIndex < fileCount; ++fileIndex)
|
||||
{
|
||||
InsertMenu(subMenu, fileIndex, MF_STRING | MF_BYPOSITION, skinFolder.baseID + fileIndex, skinFolder.files[fileIndex].c_str());
|
||||
}
|
||||
|
||||
if (skinFolder.active)
|
||||
{
|
||||
UINT checkPos = skinFolder.active - 1;
|
||||
CheckMenuRadioItem(subMenu, checkPos, checkPos, checkPos, MF_BYPOSITION);
|
||||
}
|
||||
|
||||
if (hasSubfolder && fileIndex != 0)
|
||||
{
|
||||
InsertMenu(subMenu, fileIndex, MF_SEPARATOR | MF_BYPOSITION, 0, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
++menuIndex;
|
||||
++index;
|
||||
}
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
void ContextMenu::CreateLayoutMenu(HMENU layoutMenu)
|
||||
{
|
||||
const auto& layouts = GetRainmeter().m_Layouts;
|
||||
for (size_t i = 0, isize = layouts.size(); i < isize; ++i)
|
||||
{
|
||||
InsertMenu(layoutMenu, (UINT)i, MF_BYPOSITION, ID_THEME_FIRST + i, layouts[i].c_str());
|
||||
}
|
||||
}
|
||||
|
||||
void ContextMenu::CreateMonitorMenu(HMENU monitorMenu, MeterWindow* meterWindow)
|
||||
{
|
||||
const bool screenDefined = meterWindow->GetXScreenDefined();
|
||||
const int screenIndex = meterWindow->GetXScreen();
|
||||
|
||||
// for the "Specified monitor" (@n)
|
||||
const size_t numOfMonitors = System::GetMonitorCount(); // intentional
|
||||
const std::vector<MonitorInfo>& monitors = System::GetMultiMonitorInfo().monitors;
|
||||
|
||||
int i = 1;
|
||||
for (auto iter = monitors.cbegin(); iter != monitors.cend(); ++iter, ++i)
|
||||
{
|
||||
WCHAR buffer[64];
|
||||
size_t len = _snwprintf_s(buffer, _TRUNCATE, L"@%i: ", i);
|
||||
|
||||
std::wstring item(buffer, len);
|
||||
|
||||
if ((*iter).monitorName.size() > 32)
|
||||
{
|
||||
item.append((*iter).monitorName, 0, 32);
|
||||
item += L"...";
|
||||
}
|
||||
else
|
||||
{
|
||||
item += (*iter).monitorName;
|
||||
}
|
||||
|
||||
const UINT flags =
|
||||
MF_BYPOSITION |
|
||||
((screenDefined && screenIndex == i) ? MF_CHECKED : MF_UNCHECKED) |
|
||||
((*iter).active ? MF_ENABLED : MF_GRAYED);
|
||||
InsertMenu(monitorMenu, i + 2, flags, ID_MONITOR_FIRST + i, item.c_str());
|
||||
}
|
||||
|
||||
if (!screenDefined)
|
||||
{
|
||||
CheckMenuItem(monitorMenu, IDM_SKIN_MONITOR_PRIMARY, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (screenDefined && screenIndex == 0)
|
||||
{
|
||||
CheckMenuItem(monitorMenu, ID_MONITOR_FIRST, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
|
||||
if (meterWindow->GetAutoSelectScreen())
|
||||
{
|
||||
CheckMenuItem(monitorMenu, IDM_SKIN_MONITOR_AUTOSELECT, MF_BYCOMMAND | MF_CHECKED);
|
||||
}
|
||||
}
|
||||
|
||||
void ContextMenu::ChangeSkinIndex(HMENU menu, int index)
|
||||
{
|
||||
if (index > 0)
|
||||
{
|
||||
const int count = GetMenuItemCount(menu);
|
||||
for (int i = 0; i < count; ++i)
|
||||
{
|
||||
HMENU subMenu = GetSubMenu(menu, i);
|
||||
if (subMenu)
|
||||
{
|
||||
ChangeSkinIndex(subMenu, index);
|
||||
}
|
||||
else
|
||||
{
|
||||
MENUITEMINFO mii = {sizeof(MENUITEMINFO)};
|
||||
mii.fMask = MIIM_FTYPE | MIIM_ID;
|
||||
GetMenuItemInfo(menu, i, TRUE, &mii);
|
||||
if ((mii.fType & MFT_SEPARATOR) == 0)
|
||||
{
|
||||
mii.wID |= (index << 16);
|
||||
mii.fMask = MIIM_ID;
|
||||
SetMenuItemInfo(menu, i, TRUE, &mii);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,58 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2013 Rainmeter Team
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef RM_LIBRARY_CONTEXTMENU_H
|
||||
#define RM_LIBRARY_CONTEXTMENU_H
|
||||
|
||||
#include <Windows.h>
|
||||
|
||||
class MeterWindow;
|
||||
|
||||
// Handles the creation and display of Rainmeter and skin context menus.
|
||||
class ContextMenu
|
||||
{
|
||||
public:
|
||||
ContextMenu();
|
||||
|
||||
ContextMenu(const ContextMenu& other) = delete;
|
||||
ContextMenu& operator=(ContextMenu other) = delete;
|
||||
|
||||
bool IsMenuActive() { return m_MenuActive; }
|
||||
|
||||
void ShowMenu(POINT pos, MeterWindow* meterWindow);
|
||||
void ShowSkinCustomMenu(POINT pos, MeterWindow* meterWindow);
|
||||
|
||||
static void CreateMonitorMenu(HMENU monitorMenu, MeterWindow* meterWindow);
|
||||
|
||||
private:
|
||||
static void DisplayMenu(POINT pos, HMENU menu, HWND parentWindow);
|
||||
|
||||
static HMENU CreateSkinMenu(MeterWindow* meterWindow, int index, HMENU menu);
|
||||
static void AppendSkinCustomMenu(
|
||||
MeterWindow* meterWindow, int index, HMENU menu, bool standaloneMenu);
|
||||
static void ChangeSkinIndex(HMENU subMenu, int index);
|
||||
|
||||
static void CreateAllSkinsMenu(HMENU skinMenu) { CreateAllSkinsMenuRecursive(skinMenu, 0); }
|
||||
static int CreateAllSkinsMenuRecursive(HMENU skinMenu, int index);
|
||||
|
||||
static void CreateLayoutMenu(HMENU layoutMenu);
|
||||
|
||||
bool m_MenuActive;
|
||||
};
|
||||
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
@ -1,182 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2011 Birunthan Mohanathas
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __DIALOGABOUT_H__
|
||||
#define __DIALOGABOUT_H__
|
||||
|
||||
#include "../Common/Dialog.h"
|
||||
#include "Logger.h"
|
||||
#include "MeterWindow.h"
|
||||
|
||||
class DialogAbout : public Dialog
|
||||
{
|
||||
public:
|
||||
DialogAbout();
|
||||
virtual ~DialogAbout();
|
||||
|
||||
DialogAbout(const DialogAbout& other) = delete;
|
||||
DialogAbout& operator=(DialogAbout other) = delete;
|
||||
|
||||
static Dialog* GetDialog() { return c_Dialog; }
|
||||
|
||||
static void Open(int tab = 0);
|
||||
static void Open(const WCHAR* name);
|
||||
static void ShowAboutLog();
|
||||
|
||||
static void AddLogItem(Logger::Level level, LPCWSTR time, LPCWSTR source, LPCWSTR message);
|
||||
static void UpdateSkins();
|
||||
static void UpdateMeasures(MeterWindow* meterWindow);
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnInitDialog(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
// Log tab
|
||||
class TabLog : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_ItemsListView = 100,
|
||||
Id_ErrorCheckBox,
|
||||
Id_WarningCheckBox,
|
||||
Id_NoticeCheckBox,
|
||||
Id_DebugCheckBox,
|
||||
Id_ClearButton
|
||||
};
|
||||
|
||||
TabLog();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
virtual void Resize(int w, int h);
|
||||
|
||||
void AddItem(Logger::Level level, LPCWSTR time, LPCWSTR source, LPCWSTR message);
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
bool m_Error;
|
||||
bool m_Warning;
|
||||
bool m_Notice;
|
||||
bool m_Debug;
|
||||
};
|
||||
|
||||
// Measures tab
|
||||
class TabSkins : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_SkinsListBox = 100,
|
||||
Id_ItemsListView
|
||||
};
|
||||
|
||||
TabSkins();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
virtual void Resize(int w, int h);
|
||||
|
||||
void UpdateSkinList();
|
||||
void UpdateMeasureList(MeterWindow* meterWindow);
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
static int CALLBACK ListSortProc(LPARAM lParam1, LPARAM lParam2, LPARAM lParamSort);
|
||||
|
||||
MeterWindow* m_SkinWindow;
|
||||
};
|
||||
|
||||
// Plugins tab
|
||||
class TabPlugins : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_ItemsListView = 100
|
||||
};
|
||||
|
||||
TabPlugins();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
virtual void Resize(int w, int h);
|
||||
|
||||
private:
|
||||
typedef LPCTSTR (*GETPLUGINAUTHOR)();
|
||||
typedef UINT (*GETPLUGINVERSION)();
|
||||
};
|
||||
|
||||
// Version tab
|
||||
class TabVersion : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_AppIcon = 100,
|
||||
Id_VersionLabel,
|
||||
Id_HomeLink,
|
||||
Id_LicenseLink,
|
||||
Id_WinVerLabel,
|
||||
Id_PathLabel,
|
||||
Id_IniFileLabel,
|
||||
Id_SkinPathLabel,
|
||||
Id_CopyButton
|
||||
};
|
||||
|
||||
TabVersion();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
virtual void Resize(int w, int h);
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
};
|
||||
|
||||
enum Id
|
||||
{
|
||||
Id_CloseButton = IDCLOSE,
|
||||
Id_Tab = 100
|
||||
};
|
||||
|
||||
Tab& GetActiveTab();
|
||||
|
||||
TabLog m_TabLog;
|
||||
TabSkins m_TabSkins;
|
||||
TabPlugins m_TabPlugins;
|
||||
TabVersion m_TabVersion;
|
||||
|
||||
static WINDOWPLACEMENT c_WindowPlacement;
|
||||
static DialogAbout* c_Dialog;
|
||||
};
|
||||
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
@ -1,193 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2011 Birunthan Mohanathas
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __DIALOGMANAGE_H__
|
||||
#define __DIALOGMANAGE_H__
|
||||
|
||||
#include "../Common/Dialog.h"
|
||||
#include "resource.h"
|
||||
|
||||
class DialogManage : public Dialog
|
||||
{
|
||||
public:
|
||||
DialogManage();
|
||||
virtual ~DialogManage();
|
||||
|
||||
DialogManage(const DialogManage& other) = delete;
|
||||
DialogManage& operator=(DialogManage other) = delete;
|
||||
|
||||
static Dialog* GetDialog() { return c_Dialog; }
|
||||
|
||||
static void Open(const WCHAR* tabName, const WCHAR* param1, const WCHAR* param2);
|
||||
static void Open(const WCHAR* name);
|
||||
static void Open(int tab = 0);
|
||||
static void OpenSkin(MeterWindow* meterWindow);
|
||||
|
||||
static void UpdateSkins(MeterWindow* meterWindow, bool deleted = false);
|
||||
static void UpdateLayouts();
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnInitDialog(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
// Skins tab
|
||||
class TabSkins : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_ActiveSkinsButton = 100,
|
||||
Id_SkinsTreeView,
|
||||
Id_CreateSkinPackageButton,
|
||||
Id_FileLabel,
|
||||
Id_ConfigLabel,
|
||||
Id_AuthorLabel,
|
||||
Id_VersionLabel,
|
||||
Id_LicenseLabel,
|
||||
Id_DescriptionLabel,
|
||||
Id_AddMetadataLink,
|
||||
Id_XPositionEdit,
|
||||
Id_YPositionEdit,
|
||||
Id_ZPositionDropDownList,
|
||||
Id_LoadOrderEdit,
|
||||
Id_OnHoverDropDownList,
|
||||
Id_TransparencyDropDownList,
|
||||
Id_DisplayMonitorButton,
|
||||
Id_DraggableCheckBox,
|
||||
Id_ClickThroughCheckBox,
|
||||
Id_KeepOnScreenCheckBox,
|
||||
Id_SavePositionCheckBox,
|
||||
Id_SnapToEdgesCheckBox,
|
||||
|
||||
Id_LoadButton = IDM_MANAGESKINSMENU_LOAD,
|
||||
Id_RefreshButton = IDM_MANAGESKINSMENU_REFRESH,
|
||||
Id_EditButton = IDM_MANAGESKINSMENU_EDIT
|
||||
};
|
||||
|
||||
TabSkins();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
|
||||
void Update(MeterWindow* meterWindow, bool deleted);
|
||||
|
||||
static void SelectTreeItem(HWND tree, HTREEITEM item, LPCWSTR name);
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnNotify(WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
void SetControls();
|
||||
void DisableControls(bool clear = false);
|
||||
void ReadSkin();
|
||||
|
||||
static std::wstring GetTreeSelectionPath(HWND tree);
|
||||
static int PopulateTree(HWND tree, TVINSERTSTRUCT& tvi, int index = 0);
|
||||
|
||||
std::wstring m_SkinFileName;
|
||||
std::wstring m_SkinFolderPath;
|
||||
MeterWindow* m_SkinWindow;
|
||||
bool m_HandleCommands;
|
||||
bool m_IgnoreUpdate;
|
||||
};
|
||||
|
||||
// Layouts tab
|
||||
class TabLayouts : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_List = 100,
|
||||
Id_LoadButton,
|
||||
Id_DeleteButton,
|
||||
Id_EditButton,
|
||||
Id_SaveButton,
|
||||
Id_SaveEmptyThemeCheckBox,
|
||||
Id_ExcludeUnusedSkinsCheckBox,
|
||||
Id_IncludeWallpaperCheckBox,
|
||||
Id_NameLabel
|
||||
};
|
||||
|
||||
TabLayouts();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
|
||||
void Update();
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
};
|
||||
|
||||
// Settings tab
|
||||
class TabSettings : public Tab
|
||||
{
|
||||
public:
|
||||
enum Id
|
||||
{
|
||||
Id_CheckForUpdatesCheckBox = 100,
|
||||
Id_LockSkinsCheckBox,
|
||||
Id_ResetStatisticsButton,
|
||||
Id_LogToFileCheckBox,
|
||||
Id_VerboseLoggingCheckbox,
|
||||
Id_ShowLogFileButton,
|
||||
Id_DeleteLogFileButton,
|
||||
Id_LanguageDropDownList,
|
||||
Id_EditorEdit,
|
||||
Id_EditorBrowseButton,
|
||||
Id_ShowTrayIconCheckBox,
|
||||
Id_UseD2DCheckBox
|
||||
};
|
||||
|
||||
TabSettings();
|
||||
|
||||
void Create(HWND owner);
|
||||
virtual void Initialize();
|
||||
|
||||
protected:
|
||||
virtual INT_PTR HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
INT_PTR OnCommand(WPARAM wParam, LPARAM lParam);
|
||||
};
|
||||
|
||||
enum Id
|
||||
{
|
||||
Id_CloseButton = IDCLOSE,
|
||||
Id_Tab = 100,
|
||||
Id_RefreshAllButton,
|
||||
Id_EditSettingsButton,
|
||||
Id_OpenLogButton,
|
||||
Id_HelpButton
|
||||
};
|
||||
|
||||
Tab& GetActiveTab();
|
||||
|
||||
TabSkins m_TabSkins;
|
||||
TabLayouts m_TabLayouts;
|
||||
TabSettings m_TabSettings;
|
||||
|
||||
static WINDOWPLACEMENT c_WindowPlacement;
|
||||
static DialogManage* c_Dialog;
|
||||
};
|
||||
|
||||
#endif
|
@ -1,3 +1,13 @@
|
||||
#pragma once
|
||||
|
||||
#define EXPORT extern "C" _declspec(dllexport)
|
||||
|
||||
namespace Results {
|
||||
|
||||
enum CallResult
|
||||
{
|
||||
Ok = 0,
|
||||
InvalidHandle = 1
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -4,29 +4,29 @@
|
||||
#include "HandleManager.h"
|
||||
#include "Exports_Common.h"
|
||||
|
||||
EXPORT bool Group_BelongsToGroup (bool* result, int32_t handle, LPWSTR str)
|
||||
EXPORT int Group_BelongsToGroup(bool* result, int32_t handle, LPWSTR str)
|
||||
{
|
||||
Group* group = (Group*)handle_get_resource (handle);
|
||||
Group* group = (Group*) handle_get_resource(handle);
|
||||
|
||||
if (group != nullptr)
|
||||
{
|
||||
*result = group->BelongsToGroup (str);
|
||||
return true;
|
||||
*result = group->BelongsToGroup(str);
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Group_Destroy (int32_t handle)
|
||||
EXPORT int Group_Destroy(int32_t handle)
|
||||
{
|
||||
Group* group = (Group*)handle_get_resource (handle);
|
||||
Group* group = (Group*) handle_get_resource(handle);
|
||||
|
||||
if (group != nullptr)
|
||||
{
|
||||
handle_free (handle);
|
||||
handle_free(handle);
|
||||
delete group;
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
@ -4,18 +4,16 @@
|
||||
#include "HandleManager.h"
|
||||
#include "Exports_Common.h"
|
||||
|
||||
|
||||
|
||||
EXPORT bool Meter_Destroy (int handle)
|
||||
EXPORT int Meter_Destroy(int handle)
|
||||
{
|
||||
Meter* meter = (Meter*)handle_get_resource (handle);
|
||||
Meter* meter = (Meter*) handle_get_resource(handle);
|
||||
|
||||
if (meter != nullptr)
|
||||
{
|
||||
handle_free (handle);
|
||||
handle_free(handle);
|
||||
delete meter;
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
@ -4,32 +4,32 @@
|
||||
#include "HandleManager.h"
|
||||
#include "Exports_Common.h"
|
||||
|
||||
EXPORT bool MeterString_Init (int* handle_result, int meterCanvasHandle, LPCWSTR name)
|
||||
EXPORT int MeterString_Init(int* handle_result, int meterCanvasHandle, LPCWSTR name)
|
||||
{
|
||||
MeterWindow* w = (MeterWindow*) handle_get_resource (meterCanvasHandle);
|
||||
MeterWindow* w = (MeterWindow*) handle_get_resource(meterCanvasHandle);
|
||||
|
||||
if (w != nullptr)
|
||||
{
|
||||
MeterString* result = new MeterString (w, name);
|
||||
*handle_result = handle_allocate (result);
|
||||
MeterString* result = new MeterString(w, name);
|
||||
*handle_result = handle_allocate(result);
|
||||
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool MeterString_Destroy (int handle)
|
||||
EXPORT int MeterString_Destroy(int handle)
|
||||
{
|
||||
MeterString* ms = (MeterString*) handle_get_resource (handle);
|
||||
MeterString* ms = (MeterString*) handle_get_resource(handle);
|
||||
|
||||
if (ms != nullptr)
|
||||
{
|
||||
handle_free (handle);
|
||||
handle_free(handle);
|
||||
delete ms;
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
|
@ -7,7 +7,7 @@
|
||||
*/
|
||||
bool Rainmeter_Initialize()
|
||||
{
|
||||
int res = GetRainmeter().Initialize(nullptr, nullptr);
|
||||
int res = GetRainmeter().Initialize();
|
||||
|
||||
// Success?
|
||||
if (res == 0)
|
||||
@ -22,6 +22,6 @@ bool Rainmeter_Initialize()
|
||||
*/
|
||||
void Rainmeter_Finalize(void* ptr)
|
||||
{
|
||||
Rainmeter* rainmeter = (Rainmeter*)ptr;
|
||||
Rainmeter* rainmeter = (Rainmeter*) ptr;
|
||||
rainmeter->Finalize();
|
||||
}
|
||||
|
@ -2,130 +2,130 @@
|
||||
#include "Exports_Common.h"
|
||||
#include "Section.h"
|
||||
|
||||
EXPORT bool Section_GetName (LPCWCHAR* result, int32_t handle)
|
||||
EXPORT int Section_GetName(LPCWCHAR* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->GetName();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_GetOriginalName (LPCWCHAR* result, int32_t handle)
|
||||
EXPORT int Section_GetOriginalName(LPCWCHAR* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->GetOriginalName().c_str();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_HasDynamicVariables (bool* result, int32_t handle)
|
||||
EXPORT int Section_HasDynamicVariables(bool* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->HasDynamicVariables();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_SetDynamicVariables (int32_t handle, bool value)
|
||||
EXPORT int Section_SetDynamicVariables(int32_t handle, bool value)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
section->SetDynamicVariables(value);
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_ResetUpdateCounter (int32_t handle)
|
||||
EXPORT int Section_ResetUpdateCounter(int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
section->ResetUpdateCounter();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_GetUpdateCounter (int* result, int32_t handle)
|
||||
EXPORT int Section_GetUpdateCounter(int* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->GetUpdateCounter();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
|
||||
EXPORT bool Section_GetUpdateDivider (int* result, int32_t handle)
|
||||
EXPORT int Section_GetUpdateDivider(int* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->GetUpdateDivider();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_GetOnUpdateAction (LPCWCHAR* result, int32_t handle)
|
||||
EXPORT int Section_GetOnUpdateAction(LPCWCHAR* result, int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
|
||||
if (section != nullptr)
|
||||
{
|
||||
*result = section->GetOnUpdateAction().c_str();
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_DoUpdateAction (int32_t handle)
|
||||
EXPORT int Section_DoUpdateAction(int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
if (section != nullptr)
|
||||
{
|
||||
section->DoUpdateAction ();
|
||||
return true;
|
||||
section->DoUpdateAction();
|
||||
return Results::Ok;
|
||||
}
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
||||
|
||||
EXPORT bool Section_Destroy (int32_t handle)
|
||||
EXPORT int Section_Destroy(int32_t handle)
|
||||
{
|
||||
Section* section = (Section*) handle_get_resource (handle);
|
||||
Section* section = (Section*) handle_get_resource(handle);
|
||||
if (section != nullptr)
|
||||
{
|
||||
handle_free (handle);
|
||||
handle_free(handle);
|
||||
delete section;
|
||||
return true;
|
||||
return Results::Ok;
|
||||
}
|
||||
return false;
|
||||
return Results::InvalidHandle;
|
||||
}
|
@ -34,10 +34,12 @@
|
||||
<ClCompile Include="ConfigParser_Test.cpp">
|
||||
<ExcludedFromBuild>$(ExcludeTests)</ExcludedFromBuild>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ContextMenu.cpp" />
|
||||
<ClCompile Include="DialogAbout.cpp" />
|
||||
<ClCompile Include="DialogManage.cpp" />
|
||||
<ClCompile Include="Exports_Meter.cpp" />
|
||||
<ClCompile Include="Exports_MeterString.cpp" />
|
||||
<ClCompile Include="Exports_Rainmeter.cpp" />
|
||||
<ClCompile Include="Group.cpp" />
|
||||
<ClCompile Include="Exports_Group.cpp" />
|
||||
<ClCompile Include="HandleManager.cpp" />
|
||||
<ClCompile Include="IfActions.cpp" />
|
||||
<ClCompile Include="Litestep.cpp" />
|
||||
<ClCompile Include="Logger.cpp" />
|
||||
@ -73,17 +75,11 @@
|
||||
<ClCompile Include="Rainmeter.cpp" />
|
||||
<ClCompile Include="Export.cpp" />
|
||||
<ClCompile Include="Section.cpp" />
|
||||
<ClCompile Include="SkinRegistry.cpp" />
|
||||
<ClCompile Include="SkinRegistry_Test.cpp">
|
||||
<ExcludedFromBuild>$(ExcludeTests)</ExcludedFromBuild>
|
||||
</ClCompile>
|
||||
<ClCompile Include="StdAfx.cpp">
|
||||
<PrecompiledHeader>Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<ClCompile Include="System.cpp" />
|
||||
<ClCompile Include="TintedImage.cpp" />
|
||||
<ClCompile Include="TrayWindow.cpp" />
|
||||
<ClCompile Include="UpdateCheck.cpp" />
|
||||
<ClCompile Include="lua\LuaManager.cpp" />
|
||||
<ClCompile Include="lua\LuaScript.cpp" />
|
||||
<ClCompile Include="lua\glue\LuaMeasure.cpp" />
|
||||
@ -92,18 +88,21 @@
|
||||
<ClCompile Include="lua\glue\LuaGlobal.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="..\Language\Language.rc" />
|
||||
<ResourceCompile Include="Library.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="CommandHandler.h" />
|
||||
<ClInclude Include="ConfigParser.h" />
|
||||
<ClInclude Include="ContextMenu.h" />
|
||||
<ClInclude Include="DialogAbout.h" />
|
||||
<ClInclude Include="Error.h" />
|
||||
<ClInclude Include="Exports_Common.h" />
|
||||
<ClCompile Include="Exports_Section.cpp">
|
||||
<FileType>CppHeader</FileType>
|
||||
</ClCompile>
|
||||
<ClInclude Include="Group.h" />
|
||||
<ClInclude Include="HandleManager.h" />
|
||||
<ClInclude Include="IfActions.h" />
|
||||
<ClInclude Include="Litestep.h" />
|
||||
<ClInclude Include="DialogManage.h" />
|
||||
<ClInclude Include="Logger.h" />
|
||||
<ClInclude Include="Measure.h" />
|
||||
<ClInclude Include="MeasureCalc.h" />
|
||||
@ -139,12 +138,9 @@
|
||||
<ClInclude Include="RainmeterQuery.h" />
|
||||
<ClInclude Include="resource.h" />
|
||||
<ClInclude Include="Section.h" />
|
||||
<ClInclude Include="SkinRegistry.h" />
|
||||
<ClInclude Include="StdAfx.h" />
|
||||
<ClInclude Include="System.h" />
|
||||
<ClInclude Include="TintedImage.h" />
|
||||
<ClInclude Include="TrayWindow.h" />
|
||||
<ClInclude Include="UpdateCheck.h" />
|
||||
<ClInclude Include="lua\LuaManager.h" />
|
||||
<ClInclude Include="lua\LuaScript.h" />
|
||||
</ItemGroup>
|
||||
|
@ -19,6 +19,12 @@
|
||||
<Filter Include="Lua\glue">
|
||||
<UniqueIdentifier>{941dce28-a314-4492-befb-5770432c98bf}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Source Files\Exports">
|
||||
<UniqueIdentifier>{86873eb6-7daf-4cde-b957-2c1bfc5aa066}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Header Files\Exports">
|
||||
<UniqueIdentifier>{2bd33bb1-d45c-4072-9ef2-cfa77bbf82df}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ConfigParser.cpp">
|
||||
@ -126,12 +132,6 @@
|
||||
<ClCompile Include="TintedImage.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="TrayWindow.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="UpdateCheck.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="lua\LuaManager.cpp">
|
||||
<Filter>Lua</Filter>
|
||||
</ClCompile>
|
||||
@ -150,12 +150,6 @@
|
||||
<ClCompile Include="lua\glue\LuaGlobal.cpp">
|
||||
<Filter>Lua\glue</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="DialogAbout.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="DialogManage.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Export.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
@ -171,21 +165,30 @@
|
||||
<ClCompile Include="CommandHandler.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SkinRegistry.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SkinRegistry_Test.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ContextMenu.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="IfActions.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="MeasureString.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="HandleManager.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Exports_Group.cpp">
|
||||
<Filter>Source Files\Exports</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Exports_Section.cpp">
|
||||
<Filter>Source Files\Exports</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Exports_Meter.cpp">
|
||||
<Filter>Source Files\Exports</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Exports_MeterString.cpp">
|
||||
<Filter>Source Files\Exports</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Exports_Rainmeter.cpp">
|
||||
<Filter>Source Files\Exports</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="ConfigParser.h">
|
||||
@ -299,24 +302,12 @@
|
||||
<ClInclude Include="TintedImage.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="TrayWindow.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="UpdateCheck.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="lua\LuaManager.h">
|
||||
<Filter>Lua</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="lua\LuaScript.h">
|
||||
<Filter>Lua</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="DialogAbout.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="DialogManage.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Export.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
@ -332,23 +323,26 @@
|
||||
<ClInclude Include="CommandHandler.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SkinRegistry.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ContextMenu.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="IfActions.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="MeasureString.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="HandleManager.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Exports_Common.h">
|
||||
<Filter>Header Files\Exports</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="Library.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\Language\Language.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="Exports.def">
|
||||
|
@ -31,7 +31,7 @@ UINT GetUniqueID()
|
||||
WCHAR* GetString(UINT id)
|
||||
{
|
||||
LPWSTR pData;
|
||||
int len = LoadString(GetRainmeter().GetResourceInstance(), id, (LPWSTR)&pData, 0);
|
||||
int len = LoadString(GetRainmeter().GetModuleInstance(), id, (LPWSTR)&pData, 0);
|
||||
return len ? pData : L"";
|
||||
}
|
||||
|
||||
|
@ -33,7 +33,7 @@ const size_t MAX_LOG_ENTIRES = 20;
|
||||
} // namespace
|
||||
|
||||
Logger::Logger() :
|
||||
m_LogToFile(false)
|
||||
m_LoggerCallback (nullptr)
|
||||
{
|
||||
System::InitializeCriticalSection(&m_CsLog);
|
||||
System::InitializeCriticalSection(&m_CsLogDelay);
|
||||
@ -51,56 +51,6 @@ Logger& Logger::GetInstance()
|
||||
return s_Logger;
|
||||
}
|
||||
|
||||
void Logger::StartLogFile()
|
||||
{
|
||||
const WCHAR* filePath = m_LogFilePath.c_str();
|
||||
if (_waccess(filePath, 0) == -1)
|
||||
{
|
||||
// Create empty log file.
|
||||
HANDLE file = CreateFile(filePath, GENERIC_WRITE, 0, nullptr, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, nullptr);
|
||||
if (file != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
CloseHandle(file);
|
||||
}
|
||||
else
|
||||
{
|
||||
const std::wstring text = GetFormattedString(ID_STR_LOGFILECREATEFAIL, filePath);
|
||||
GetRainmeter().ShowMessage(nullptr, text.c_str(), MB_OK | MB_ICONERROR);
|
||||
SetLogToFile(false);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
SetLogToFile(true);
|
||||
}
|
||||
|
||||
void Logger::StopLogFile()
|
||||
{
|
||||
SetLogToFile(false);
|
||||
}
|
||||
|
||||
void Logger::DeleteLogFile()
|
||||
{
|
||||
const WCHAR* filePath = m_LogFilePath.c_str();
|
||||
if (_waccess(filePath, 0) != -1)
|
||||
{
|
||||
const std::wstring text = GetFormattedString(ID_STR_LOGFILEDELETE, filePath);
|
||||
const int res = GetRainmeter().ShowMessage(nullptr, text.c_str(), MB_YESNO | MB_ICONQUESTION);
|
||||
if (res == IDYES)
|
||||
{
|
||||
SetLogToFile(false);
|
||||
System::RemoveFile(m_LogFilePath);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Logger::SetLogToFile(bool logToFile)
|
||||
{
|
||||
m_LogToFile = logToFile;
|
||||
WritePrivateProfileString(
|
||||
L"Rainmeter", L"Logging", logToFile ? L"1" : L"0", GetRainmeter().GetIniFile().c_str());
|
||||
}
|
||||
|
||||
void Logger::LogInternal(Level level, ULONGLONG timestamp, const WCHAR* source, const WCHAR* msg)
|
||||
{
|
||||
WCHAR timestampSz[128];
|
||||
@ -121,15 +71,11 @@ void Logger::LogInternal(Level level, ULONGLONG timestamp, const WCHAR* source,
|
||||
m_Entries.pop_front();
|
||||
}
|
||||
|
||||
DialogAbout::AddLogItem(level, timestampSz, source, msg);
|
||||
WriteToLogFile(entry);
|
||||
}
|
||||
// Call callback function
|
||||
if (m_LoggerCallback != nullptr)
|
||||
(*m_LoggerCallback)(entry.level, entry.timestamp.c_str(), source, msg);
|
||||
|
||||
void Logger::WriteToLogFile(Entry& entry)
|
||||
{
|
||||
#ifndef _DEBUG
|
||||
if (!m_LogToFile) return;
|
||||
#endif
|
||||
#ifdef _DEBUG
|
||||
|
||||
const WCHAR* levelSz =
|
||||
(entry.level == Level::Error) ? L"ERRO" :
|
||||
@ -146,26 +92,9 @@ void Logger::WriteToLogFile(Entry& entry)
|
||||
message += entry.message;
|
||||
message += L'\n';
|
||||
|
||||
#ifdef _DEBUG
|
||||
_RPTW0(_CRT_WARN, message.c_str());
|
||||
if (!m_LogToFile) return;
|
||||
#endif
|
||||
OutputDebugStringW (message.c_str ());
|
||||
|
||||
const WCHAR* filePath = m_LogFilePath.c_str();
|
||||
if (_waccess(filePath, 0) == -1)
|
||||
{
|
||||
// The file has been deleted manually.
|
||||
StopLogFile();
|
||||
}
|
||||
else
|
||||
{
|
||||
FILE* file = _wfopen(filePath, L"a+, ccs=UTF-8");
|
||||
if (file)
|
||||
{
|
||||
fputws(message.c_str(), file);
|
||||
fclose(file);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void Logger::Log(Level level, const WCHAR* source, const WCHAR* msg)
|
||||
|
@ -49,14 +49,9 @@ public:
|
||||
|
||||
static Logger& GetInstance();
|
||||
|
||||
void SetLogFilePath(std::wstring path) { m_LogFilePath = path; }
|
||||
typedef void (*LoggerCallback) (Level level, LPCWSTR timestamp, LPCWSTR source, LPCWSTR message);
|
||||
|
||||
void StartLogFile();
|
||||
void StopLogFile();
|
||||
void DeleteLogFile();
|
||||
|
||||
bool IsLogToFile() { return m_LogToFile; }
|
||||
void SetLogToFile(bool logToFile);
|
||||
void SetLogCallback(LoggerCallback callback) { m_LoggerCallback = callback; }
|
||||
|
||||
void Log(Level level, const WCHAR* source, const WCHAR* msg);
|
||||
void LogVF(Level level, const WCHAR* source, const WCHAR* format, va_list args);
|
||||
@ -64,16 +59,11 @@ public:
|
||||
void LogSection(Logger::Level level, Section* section, const WCHAR* message);
|
||||
void LogSectionVF(Logger::Level level, Section* section, const WCHAR* format, va_list args);
|
||||
|
||||
const std::wstring& GetLogFilePath() { return m_LogFilePath; }
|
||||
|
||||
const std::list<Entry>& GetEntries() { return m_Entries; }
|
||||
|
||||
private:
|
||||
void LogInternal(Level level, ULONGLONG timestamp, const WCHAR* source, const WCHAR* msg);
|
||||
|
||||
// Appends |entry| to the log file.
|
||||
void WriteToLogFile(Entry& entry);
|
||||
|
||||
Logger();
|
||||
~Logger();
|
||||
|
||||
@ -81,7 +71,7 @@ private:
|
||||
Logger& operator=(Logger other) = delete;
|
||||
|
||||
bool m_LogToFile;
|
||||
std::wstring m_LogFilePath;
|
||||
LoggerCallback m_LoggerCallback;
|
||||
|
||||
std::list<Entry> m_Entries;
|
||||
|
||||
|
@ -19,13 +19,10 @@
|
||||
#include "StdAfx.h"
|
||||
#include "MeterWindow.h"
|
||||
#include "Rainmeter.h"
|
||||
#include "TrayWindow.h"
|
||||
#include "System.h"
|
||||
#include "Error.h"
|
||||
#include "Meter.h"
|
||||
#include "Measure.h"
|
||||
#include "DialogAbout.h"
|
||||
#include "DialogManage.h"
|
||||
#include "resource.h"
|
||||
#include "Litestep.h"
|
||||
#include "MeasureCalc.h"
|
||||
@ -414,7 +411,7 @@ void MeterWindow::Refresh(bool init, bool all)
|
||||
|
||||
if (!ReadSkin())
|
||||
{
|
||||
GetRainmeter().DeactivateSkin(this, -1);
|
||||
GetRainmeter().DeactivateSkin(this);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -798,7 +795,7 @@ void MeterWindow::DoBang(Bang bang, const std::vector<std::wstring>& args)
|
||||
|
||||
case Bang::UpdateMeasure:
|
||||
UpdateMeasure(args[0]);
|
||||
DialogAbout::UpdateMeasures(this);
|
||||
// TODO: update measure callback
|
||||
break;
|
||||
|
||||
case Bang::DisableMeasureGroup:
|
||||
@ -827,7 +824,7 @@ void MeterWindow::DoBang(Bang bang, const std::vector<std::wstring>& args)
|
||||
|
||||
case Bang::UpdateMeasureGroup:
|
||||
UpdateMeasure(args[0], true);
|
||||
DialogAbout::UpdateMeasures(this);
|
||||
// DialogAbout::UpdateMeasures(this);
|
||||
break;
|
||||
|
||||
case Bang::Show:
|
||||
@ -1880,7 +1877,7 @@ void MeterWindow::ScreenToWindow()
|
||||
*/
|
||||
void MeterWindow::ReadOptions()
|
||||
{
|
||||
WCHAR buffer[32];
|
||||
/*WCHAR buffer[32];
|
||||
|
||||
const WCHAR* section = m_FolderPath.c_str();
|
||||
ConfigParser parser;
|
||||
@ -1953,7 +1950,7 @@ void MeterWindow::ReadOptions()
|
||||
}
|
||||
|
||||
// Set WindowXScreen/WindowYScreen temporarily
|
||||
WindowToScreen();
|
||||
WindowToScreen();*/
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1962,7 +1959,7 @@ void MeterWindow::ReadOptions()
|
||||
*/
|
||||
void MeterWindow::WriteOptions(INT setting)
|
||||
{
|
||||
const WCHAR* iniFile = GetRainmeter().GetIniFile().c_str();
|
||||
/*const WCHAR* iniFile = GetRainmeter().GetIniFile().c_str();
|
||||
|
||||
if (*iniFile)
|
||||
{
|
||||
@ -1971,7 +1968,7 @@ void MeterWindow::WriteOptions(INT setting)
|
||||
|
||||
if (setting != OPTION_ALL)
|
||||
{
|
||||
DialogManage::UpdateSkins(this);
|
||||
//DialogManage::UpdateSkins(this);
|
||||
}
|
||||
|
||||
if (setting & OPTION_POSITION)
|
||||
@ -2046,7 +2043,7 @@ void MeterWindow::WriteOptions(INT setting)
|
||||
{
|
||||
WritePrivateProfileString(section, L"UseD2D", m_UseD2D ? L"1" : L"0", iniFile);
|
||||
}
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
/*
|
||||
@ -2063,7 +2060,7 @@ bool MeterWindow::ReadSkin()
|
||||
if (_waccess(iniFile.c_str(), 0) == -1)
|
||||
{
|
||||
std::wstring message = GetFormattedString(ID_STR_UNABLETOREFRESHSKIN, m_FolderPath.c_str(), m_FileName.c_str());
|
||||
GetRainmeter().ShowMessage(m_Window, message.c_str(), MB_OK | MB_ICONEXCLAMATION);
|
||||
// unsupported: GetRainmeter().ShowMessage(m_Window, message.c_str(), MB_OK | MB_ICONEXCLAMATION);
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -2095,8 +2092,7 @@ bool MeterWindow::ReadSkin()
|
||||
_snwprintf_s(buffer, _TRUNCATE, L"%u.%u", appVersion / 1000000, (appVersion / 1000) % 1000);
|
||||
}
|
||||
|
||||
std::wstring text = GetFormattedString(ID_STR_NEWVERSIONREQUIRED, m_FolderPath.c_str(), m_FileName.c_str(), buffer);
|
||||
GetRainmeter().ShowMessage(m_Window, text.c_str(), MB_OK | MB_ICONEXCLAMATION);
|
||||
// TODO: throw error or something
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -2234,7 +2230,7 @@ bool MeterWindow::ReadSkin()
|
||||
do
|
||||
{
|
||||
// Try program folder first
|
||||
std::wstring szFontFile = GetRainmeter().GetPath() + L"Fonts\\";
|
||||
std::wstring szFontFile = GetRainmeter().GetWorkDirectory() + L"Fonts\\";
|
||||
szFontFile += localFont;
|
||||
if (!m_FontCollection->AddFile(szFontFile.c_str()))
|
||||
{
|
||||
@ -2310,7 +2306,7 @@ bool MeterWindow::ReadSkin()
|
||||
if (m_Meters.empty())
|
||||
{
|
||||
std::wstring text = GetFormattedString(ID_STR_NOMETERSINSKIN, m_FolderPath.c_str(), m_FileName.c_str());
|
||||
GetRainmeter().ShowMessage(m_Window, text.c_str(), MB_OK | MB_ICONEXCLAMATION);
|
||||
// Unsupported: GetRainmeter().ShowMessage(m_Window, text.c_str(), MB_OK | MB_ICONEXCLAMATION);
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -2767,7 +2763,7 @@ void MeterWindow::Update(bool refresh)
|
||||
}
|
||||
}
|
||||
|
||||
DialogAbout::UpdateMeasures(this);
|
||||
// TODO: call update measures callback
|
||||
|
||||
// Update all meters
|
||||
bool bActiveTransition = false;
|
||||
@ -2792,13 +2788,8 @@ void MeterWindow::Update(bool refresh)
|
||||
SetResizeWindowMode(RESIZEMODE_CHECK);
|
||||
}
|
||||
|
||||
// If our option is to disable when in an RDP session, then check if in an RDP session.
|
||||
// Only redraw if we are not in a remote session
|
||||
if (GetRainmeter().IsRedrawable())
|
||||
{
|
||||
Redraw();
|
||||
}
|
||||
}
|
||||
|
||||
// Post-updates
|
||||
PostUpdate(bActiveTransition);
|
||||
@ -3391,22 +3382,10 @@ LRESULT MeterWindow::OnCommand(UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
switch (wParam)
|
||||
{
|
||||
case IDM_SKIN_EDITSKIN:
|
||||
GetRainmeter().EditSkinFile(m_FolderPath, m_FileName);
|
||||
break;
|
||||
|
||||
case IDM_SKIN_REFRESH:
|
||||
Refresh(false);
|
||||
break;
|
||||
|
||||
case IDM_SKIN_OPENSKINSFOLDER:
|
||||
GetRainmeter().OpenSkinFolder(m_FolderPath);
|
||||
break;
|
||||
|
||||
case IDM_SKIN_MANAGESKIN:
|
||||
DialogManage::OpenSkin(this);
|
||||
break;
|
||||
|
||||
case IDM_SKIN_VERYTOPMOST:
|
||||
SetWindowZPosition(ZPOSITION_ONTOPMOST);
|
||||
break;
|
||||
@ -3466,7 +3445,7 @@ LRESULT MeterWindow::OnCommand(UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||
case IDM_CLOSESKIN:
|
||||
if (m_State != STATE_CLOSING)
|
||||
{
|
||||
GetRainmeter().DeactivateSkin(this, -1);
|
||||
GetRainmeter().DeactivateSkin(this);
|
||||
}
|
||||
break;
|
||||
|
||||
@ -3559,20 +3538,6 @@ LRESULT MeterWindow::OnCommand(UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||
GetRainmeter().ExecuteCommand(action.c_str(), this);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Forward to tray window, which handles all the other commands
|
||||
HWND tray = GetRainmeter().GetTrayWindow()->GetWindow();
|
||||
|
||||
if (wParam == IDM_QUIT)
|
||||
{
|
||||
PostMessage(tray, WM_COMMAND, wParam, lParam);
|
||||
}
|
||||
else
|
||||
{
|
||||
SendMessage(tray, WM_COMMAND, wParam, lParam);
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
@ -3667,7 +3632,7 @@ void MeterWindow::SavePositionIfAppropriate()
|
||||
else
|
||||
{
|
||||
ScreenToWindow();
|
||||
DialogManage::UpdateSkins(this);
|
||||
// TODO: call update skins callback
|
||||
}
|
||||
}
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -14,7 +14,7 @@
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
*/
|
||||
|
||||
#ifndef __RAINMETER_H__
|
||||
#define __RAINMETER_H__
|
||||
@ -25,10 +25,9 @@
|
||||
#include <list>
|
||||
#include <string>
|
||||
#include "CommandHandler.h"
|
||||
#include "ContextMenu.h"
|
||||
#include "Logger.h"
|
||||
#include "MeterWindow.h"
|
||||
#include "SkinRegistry.h"
|
||||
#include "../Common/PathUtil.h"
|
||||
|
||||
#define MAX_LINE_LENGTH 4096
|
||||
|
||||
@ -56,14 +55,21 @@ struct GlobalOptions
|
||||
};
|
||||
|
||||
class ConfigParser;
|
||||
class TrayWindow;
|
||||
|
||||
class Rainmeter
|
||||
{
|
||||
public:
|
||||
|
||||
#pragma region Singleton
|
||||
|
||||
/// <brief>
|
||||
/// Gets the instance
|
||||
/// </brief>
|
||||
static Rainmeter& GetInstance();
|
||||
|
||||
int Initialize(LPCWSTR iniPath, LPCWSTR layout);
|
||||
#pragma endregion
|
||||
|
||||
int Initialize();
|
||||
void Finalize();
|
||||
|
||||
int MessagePump();
|
||||
@ -73,8 +79,6 @@ public:
|
||||
ConfigParser* GetCurrentParser() { return m_CurrentParser; }
|
||||
void SetCurrentParser(ConfigParser* parser) { m_CurrentParser = parser; }
|
||||
|
||||
TrayWindow* GetTrayWindow() { return m_TrayWindow; }
|
||||
|
||||
bool HasMeterWindow(const MeterWindow* meterWindow) const;
|
||||
|
||||
MeterWindow* GetMeterWindow(const std::wstring& folderPath);
|
||||
@ -84,93 +88,60 @@ public:
|
||||
void GetMeterWindowsByLoadOrder(std::multimap<int, MeterWindow*>& windows, const std::wstring& group = std::wstring());
|
||||
std::map<std::wstring, MeterWindow*>& GetAllMeterWindows() { return m_MeterWindows; }
|
||||
|
||||
const std::vector<std::wstring>& GetAllLayouts() { return m_Layouts; }
|
||||
|
||||
void RemoveMeterWindow(MeterWindow* meterWindow);
|
||||
void AddUnmanagedMeterWindow(MeterWindow* meterWindow);
|
||||
void RemoveUnmanagedMeterWindow(MeterWindow* meterWindow);
|
||||
|
||||
bool ActivateSkin(const std::wstring& folderPath);
|
||||
bool ActivateSkin(const std::wstring& folderPath, const std::wstring& file);
|
||||
void ActivateSkin(int folderIndex, int fileIndex);
|
||||
void DeactivateSkin(MeterWindow* meterWindow, int folderIndex, bool save = true);
|
||||
void ToggleSkin(int folderIndex, int fileIndex);
|
||||
void ActivateSkin(std::wstring file);
|
||||
void DeactivateSkin(MeterWindow* meterWindow);
|
||||
void ToggleSkin(std::wstring file);
|
||||
void ToggleSkinWithID(UINT id);
|
||||
|
||||
const std::wstring& GetPath() { return m_Path; }
|
||||
const std::wstring& GetIniFile() { return m_IniFile; }
|
||||
const std::wstring& GetDataFile() { return m_DataFile; }
|
||||
const std::wstring& GetSettingsPath() { return m_SettingsPath; }
|
||||
const std::wstring& GetSkinPath() { return m_SkinPath; }
|
||||
void SetSkinPath(const std::wstring& skinPath);
|
||||
std::wstring GetLayoutPath() { return m_SettingsPath + L"Layouts\\"; }
|
||||
std::wstring GetPluginPath() { return m_Path + L"Plugins\\"; }
|
||||
std::wstring GetUserPluginPath() { return m_SettingsPath + L"Plugins\\"; }
|
||||
std::wstring GetAddonPath() { return m_SettingsPath + L"Addons\\"; }
|
||||
std::wstring GetWorkDirectory()
|
||||
{
|
||||
if (m_UseCurrentDirectory)
|
||||
{
|
||||
WCHAR buffer[MAX_PATH];
|
||||
GetCurrentDirectoryW(MAX_PATH, buffer);
|
||||
return buffer;
|
||||
}
|
||||
|
||||
bool HasUserPluginPath() { return (_wcsicmp(m_Path.c_str(), m_SettingsPath.c_str()) != 0); }
|
||||
return m_WorkDirectory;
|
||||
}
|
||||
|
||||
std::wstring GetDefaultSkinPath() { return m_Path + L"Defaults\\Skins\\"; }
|
||||
std::wstring GetDefaultLayoutPath() { return m_Path + L"Defaults\\Layouts\\"; }
|
||||
std::wstring GetDefaultPluginPath() { return m_Path + L"Defaults\\Plugins\\"; }
|
||||
std::wstring GetDefaultAddonPath() { return m_Path + L"Defaults\\Addons\\"; }
|
||||
std::wstring GetSkinPath() { return GetWorkDirectory() + L"Skins\\"; }
|
||||
std::wstring GetLayoutPath() { return GetWorkDirectory() + L"Layouts\\"; }
|
||||
std::wstring GetPluginPath() { return GetWorkDirectory() + L"Plugins\\"; }
|
||||
std::wstring GetUserPluginPath() { return GetWorkDirectory() + L"Plugins\\"; }
|
||||
std::wstring GetAddonPath() { return GetWorkDirectory() + L"Addons\\"; }
|
||||
|
||||
const std::wstring& GetDrive() { return m_Drive; }
|
||||
std::wstring GetDrive() { return PathUtil::GetVolume(GetWorkDirectory()); }
|
||||
|
||||
const std::wstring& GetSkinEditor() { return m_SkinEditor; }
|
||||
void SetSkinEditor(const std::wstring& path);
|
||||
const std::wstring& GetStatsDate() { return m_StatsDate; }
|
||||
|
||||
HWND GetWindow() { return m_Window; }
|
||||
|
||||
HINSTANCE GetModuleInstance() { return m_Instance; }
|
||||
HINSTANCE GetResourceInstance() { return m_ResourceInstance; }
|
||||
LCID GetResourceLCID() { return m_ResourceLCID; }
|
||||
|
||||
bool GetUseD2D() const { return m_UseD2D; }
|
||||
void SetUseD2D(bool enabled);
|
||||
|
||||
bool GetDebug() { return m_Debug; }
|
||||
bool GetDebug() const { return m_Debug; }
|
||||
|
||||
GlobalOptions& GetGlobalOptions() { return m_GlobalOptions; }
|
||||
|
||||
void ReloadSettings();
|
||||
void EditSettings();
|
||||
void EditSkinFile(const std::wstring& name, const std::wstring& iniFile);
|
||||
void OpenSkinFolder(const std::wstring& name = std::wstring());
|
||||
|
||||
void UpdateStats();
|
||||
void ReadStats();
|
||||
void WriteStats(bool bForce);
|
||||
void ResetStats();
|
||||
|
||||
bool GetDisableVersionCheck() { return m_DisableVersionCheck; }
|
||||
void SetDisableVersionCheck(bool check);
|
||||
bool GetNewVersion() { return m_NewVersion; }
|
||||
void SetNewVersion() { m_NewVersion = true; }
|
||||
|
||||
void ShowLogFile();
|
||||
|
||||
bool GetDisableRDP() { return m_DisableRDP; }
|
||||
bool IsRedrawable() { return (!GetDisableRDP() || !GetSystemMetrics(SM_REMOTESESSION)); }
|
||||
|
||||
bool GetDisableDragging() { return m_DisableDragging; }
|
||||
void SetDisableDragging(bool dragging);
|
||||
|
||||
bool IsNormalStayDesktop() { return m_NormalStayDesktop; }
|
||||
|
||||
void SetDebug(bool debug);
|
||||
|
||||
int ShowMessage(HWND parent, const WCHAR* text, UINT type);
|
||||
|
||||
bool IsMenuActive() { return m_ContextMenu.IsMenuActive(); }
|
||||
void ShowContextMenu(POINT pos, MeterWindow* mw) { return m_ContextMenu.ShowMenu(pos, mw); }
|
||||
void ShowSkinCustomContextMenu(POINT pos, MeterWindow* mw) { return m_ContextMenu.ShowSkinCustomMenu(pos, mw); }
|
||||
|
||||
const std::wstring& GetTrayExecuteR() { return m_TrayExecuteR; }
|
||||
const std::wstring& GetTrayExecuteM() { return m_TrayExecuteM; }
|
||||
const std::wstring& GetTrayExecuteDR() { return m_TrayExecuteDR; }
|
||||
const std::wstring& GetTrayExecuteDM() { return m_TrayExecuteDM; }
|
||||
bool IsMenuActive() { /* TODO: implement c# callback */ LogErrorF(L"IsMenuActive callback not implemented."); return false; }
|
||||
void ShowContextMenu(POINT pos, MeterWindow* mw) { /* TODO: implement c# callback */ LogErrorF(L"ShowContextMenu callback not implemented."); }
|
||||
void ShowSkinCustomContextMenu(POINT pos, MeterWindow* mw) { /* TODO: implement c# callback */ LogErrorF(L"ShowSkinCustomContextMenu callback not implemented."); }
|
||||
|
||||
void ExecuteBang(const WCHAR* bang, std::vector<std::wstring>& args, MeterWindow* meterWindow);
|
||||
void ExecuteCommand(const WCHAR* command, MeterWindow* meterWindow, bool multi = true);
|
||||
@ -178,85 +149,60 @@ public:
|
||||
|
||||
void RefreshAll();
|
||||
|
||||
bool LoadLayout(const std::wstring& name);
|
||||
void PreserveSetting(const std::wstring& from, LPCTSTR key, bool replace = true);
|
||||
bool LoadLayout(std::wstring filename = std::wstring());
|
||||
|
||||
friend class CommandHandler;
|
||||
friend class ContextMenu;
|
||||
friend class DialogManage;
|
||||
|
||||
private:
|
||||
|
||||
#pragma region Constructor, destructor
|
||||
|
||||
Rainmeter();
|
||||
~Rainmeter();
|
||||
|
||||
Rainmeter(const Rainmeter& other) = delete;
|
||||
Rainmeter& operator=(Rainmeter other) = delete;
|
||||
|
||||
#pragma endregion
|
||||
|
||||
static LRESULT CALLBACK MainWndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
void ActivateActiveSkins();
|
||||
void CreateMeterWindow(const std::wstring& folderPath, const std::wstring& file);
|
||||
void CreateMeterWindow(std::wstring file);
|
||||
void DeleteAllMeterWindows();
|
||||
void DeleteAllUnmanagedMeterWindows();
|
||||
void WriteActive(const std::wstring& folderPath, int fileIndex);
|
||||
void ScanForSkins();
|
||||
void ScanForLayouts();
|
||||
void ReadGeneralSettings(const std::wstring& iniFile);
|
||||
void SetLoadOrder(int folderIndex, int order);
|
||||
void SetLoadOrder(const std::wstring& file, int order);
|
||||
int GetLoadOrder(const std::wstring& folderPath);
|
||||
void UpdateDesktopWorkArea(bool reset);
|
||||
std::wstring GetAbsolutePath(const std::wstring& path);
|
||||
std::wstring NormalizePath(const std::wstring& path);
|
||||
|
||||
void CreateOptionsFile();
|
||||
void CreateDataFile();
|
||||
void CreateComponentFolders(bool defaultIniLocation);
|
||||
void TestSettingsFile(bool bDefaultIniLocation);
|
||||
#pragma region Private fields
|
||||
|
||||
TrayWindow* m_TrayWindow;
|
||||
|
||||
std::multimap<int, int> m_SkinOrders;
|
||||
std::multimap<int, std::wstring> m_SkinOrders;
|
||||
std::map<std::wstring, MeterWindow*> m_MeterWindows;
|
||||
std::list<MeterWindow*> m_UnmanagedMeterWindows;
|
||||
std::vector<std::wstring> m_Layouts;
|
||||
|
||||
std::wstring m_Path;
|
||||
std::wstring m_IniFile;
|
||||
std::wstring m_DataFile;
|
||||
std::wstring m_StatsFile;
|
||||
std::wstring m_SettingsPath;
|
||||
std::wstring m_SkinPath;
|
||||
|
||||
std::wstring m_Drive;
|
||||
std::wstring m_WorkDirectory;
|
||||
bool m_UseCurrentDirectory; // TODO: getter, setter
|
||||
std::wstring m_StatsFile; // TODO: getter, setter
|
||||
std::wstring m_LayoutFile; // TODO: getter, setter
|
||||
|
||||
std::wstring m_StatsDate;
|
||||
|
||||
std::wstring m_TrayExecuteR;
|
||||
std::wstring m_TrayExecuteM;
|
||||
std::wstring m_TrayExecuteDR;
|
||||
std::wstring m_TrayExecuteDM;
|
||||
|
||||
bool m_UseD2D;
|
||||
|
||||
bool m_Debug;
|
||||
|
||||
bool m_DisableVersionCheck;
|
||||
bool m_NewVersion;
|
||||
|
||||
bool m_DesktopWorkAreaChanged;
|
||||
bool m_DesktopWorkAreaType;
|
||||
std::map<UINT, RECT> m_DesktopWorkAreas;
|
||||
std::vector<RECT> m_OldDesktopWorkAreas;
|
||||
|
||||
bool m_NormalStayDesktop;
|
||||
|
||||
bool m_DisableRDP;
|
||||
bool m_Debug;
|
||||
|
||||
bool m_DisableDragging;
|
||||
|
||||
std::wstring m_SkinEditor;
|
||||
|
||||
CommandHandler m_CommandHandler;
|
||||
ContextMenu m_ContextMenu;
|
||||
SkinRegistry m_SkinRegistry;
|
||||
|
||||
ConfigParser* m_CurrentParser;
|
||||
|
||||
@ -264,23 +210,15 @@ private:
|
||||
|
||||
HANDLE m_Mutex;
|
||||
HINSTANCE m_Instance;
|
||||
HMODULE m_ResourceInstance;
|
||||
LCID m_ResourceLCID;
|
||||
|
||||
ULONG_PTR m_GDIplusToken;
|
||||
|
||||
GlobalOptions m_GlobalOptions;
|
||||
|
||||
#pragma endregion
|
||||
};
|
||||
|
||||
// Convenience function.
|
||||
inline Rainmeter& GetRainmeter() { return Rainmeter::GetInstance(); }
|
||||
|
||||
#ifdef LIBRARY_EXPORTS
|
||||
#define EXPORT_PLUGIN EXTERN_C
|
||||
#else
|
||||
#define EXPORT_PLUGIN EXTERN_C __declspec(dllimport)
|
||||
#endif
|
||||
|
||||
EXPORT_PLUGIN int RainmeterMain(LPWSTR cmdLine);
|
||||
|
||||
#endif
|
||||
|
@ -89,7 +89,7 @@ These Queries return a string in a wide char format
|
||||
#define RAINMETER_QUERY_ID_SKINS_PATH 4101
|
||||
#define RAINMETER_QUERY_ID_SETTINGS_PATH 4102
|
||||
#define RAINMETER_QUERY_ID_PLUGINS_PATH 4103
|
||||
#define RAINMETER_QUERY_ID_PROGRAM_PATH 4104
|
||||
#define RAINMETER_QUERY_ID_PROGRAm_WorkDirectory 4104
|
||||
#define RAINMETER_QUERY_ID_LOG_PATH 4105
|
||||
#define RAINMETER_QUERY_ID_CONFIG_EDITOR 4106
|
||||
|
||||
|
@ -1,242 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2013 Rainmeter Team
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "StdAfx.h"
|
||||
#include "../Common/PathUtil.h"
|
||||
#include "SkinRegistry.h"
|
||||
#include "resource.h"
|
||||
|
||||
/*
|
||||
** Returns the skin folder path relative to the skin folder (e.g. illustro\Clock).
|
||||
*/
|
||||
std::wstring SkinRegistry::GetFolderPath(int folderIndex) const
|
||||
{
|
||||
// Traverse |m_Folders| backwards until level 1 is reached.
|
||||
const auto& skinFolder = m_Folders[folderIndex];
|
||||
std::wstring path = skinFolder.name;
|
||||
for (int i = skinFolder.level - 1, index = folderIndex; i >= 1; --i)
|
||||
{
|
||||
while (m_Folders[index].level != i)
|
||||
{
|
||||
--index;
|
||||
}
|
||||
|
||||
path.insert(0, L"\\");
|
||||
path.insert(0, m_Folders[index].name);
|
||||
}
|
||||
return path;
|
||||
}
|
||||
|
||||
/*
|
||||
** Finds the skin index for the specified skin folder path.
|
||||
*/
|
||||
int SkinRegistry::FindFolderIndex(const std::wstring& folderPath) const
|
||||
{
|
||||
if (folderPath.empty()) return -1;
|
||||
|
||||
const WCHAR* path = folderPath.c_str();
|
||||
int len = 0;
|
||||
while (path[len] && path[len] != L'\\') ++len;
|
||||
|
||||
int level = 1;
|
||||
for (int i = 0, isize = (int)m_Folders.size(); i < isize; ++i)
|
||||
{
|
||||
const auto& skinFolder = m_Folders[i];
|
||||
if (skinFolder.level == level)
|
||||
{
|
||||
if (skinFolder.name.length() == len && _wcsnicmp(skinFolder.name.c_str(), path, len) == 0)
|
||||
{
|
||||
path += len;
|
||||
if (*path)
|
||||
{
|
||||
++path; // Skip backslash
|
||||
len = 0;
|
||||
while (path[len] && path[len] != L'\\') ++len;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Match found
|
||||
return i;
|
||||
}
|
||||
|
||||
++level;
|
||||
}
|
||||
}
|
||||
else if (skinFolder.level < level)
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
SkinRegistry::Folder* SkinRegistry::FindFolder(const std::wstring& folderPath)
|
||||
{
|
||||
const int folderIndex = FindFolderIndex(folderPath);
|
||||
return (folderIndex != -1) ? &m_Folders[folderIndex] : nullptr;
|
||||
}
|
||||
|
||||
SkinRegistry::Indexes SkinRegistry::FindIndexes(const std::wstring& folderPath, const std::wstring& file)
|
||||
{
|
||||
const int folderIndex = FindFolderIndex(folderPath);
|
||||
if (folderIndex != -1)
|
||||
{
|
||||
const Folder& skinFolder = m_Folders[folderIndex];
|
||||
const WCHAR* fileSz = file.c_str();
|
||||
for (size_t i = 0, isize = skinFolder.files.size(); i < isize; ++i)
|
||||
{
|
||||
if (_wcsicmp(skinFolder.files[i].c_str(), fileSz) == 0)
|
||||
{
|
||||
return Indexes(folderIndex, (int)i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Indexes::Invalid(); // Not found.
|
||||
}
|
||||
|
||||
SkinRegistry::Indexes SkinRegistry::FindIndexesForID(UINT id)
|
||||
{
|
||||
if (id >= ID_CONFIG_FIRST && id <= ID_CONFIG_LAST)
|
||||
{
|
||||
// Check which skin was selected
|
||||
for (size_t i = 0, isize = m_Folders.size(); i < isize; ++i)
|
||||
{
|
||||
const Folder& skinFolder = m_Folders[i];
|
||||
if (id >= skinFolder.baseID &&
|
||||
id < (skinFolder.baseID + skinFolder.files.size()))
|
||||
{
|
||||
return Indexes((int)i, (int)(id - skinFolder.baseID));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return Indexes::Invalid(); // Not found.
|
||||
}
|
||||
|
||||
/*
|
||||
** Re-scans all the subfolders of |path| for .ini files and populates |m_Folders|.
|
||||
*/
|
||||
void SkinRegistry::Populate(const std::wstring& path)
|
||||
{
|
||||
m_Folders.clear();
|
||||
PopulateRecursive(path, L"", 0, 0);
|
||||
}
|
||||
|
||||
int SkinRegistry::PopulateRecursive(const std::wstring& path, std::wstring base, int index, UINT level)
|
||||
{
|
||||
WIN32_FIND_DATA fileData; // Data structure describes the file found
|
||||
HANDLE hSearch; // Search handle returned by FindFirstFile
|
||||
std::list<std::wstring> subfolders;
|
||||
|
||||
// Find all .ini files and subfolders
|
||||
std::wstring filter = path + base;
|
||||
filter += L"\\*";
|
||||
|
||||
hSearch = FindFirstFileEx(
|
||||
filter.c_str(),
|
||||
(IsWindows7OrGreater()) ? FindExInfoBasic : FindExInfoStandard,
|
||||
&fileData,
|
||||
FindExSearchNameMatch,
|
||||
nullptr,
|
||||
0);
|
||||
|
||||
bool foundFiles = false;
|
||||
if (hSearch != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
Folder folder;
|
||||
folder.baseID = ID_CONFIG_FIRST + index;
|
||||
folder.active = 0;
|
||||
folder.level = level;
|
||||
|
||||
do
|
||||
{
|
||||
const std::wstring filename = fileData.cFileName;
|
||||
|
||||
if (fileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
|
||||
{
|
||||
if (!PathUtil::IsDotOrDotDot(fileData.cFileName) &&
|
||||
!(level == 0 && wcscmp(L"@Backup", fileData.cFileName) == 0) &&
|
||||
!(level == 0 && wcscmp(L"Backup", fileData.cFileName) == 0) &&
|
||||
!(level == 1 && wcscmp(L"@Resources", fileData.cFileName) == 0))
|
||||
{
|
||||
subfolders.push_back(filename);
|
||||
}
|
||||
}
|
||||
else if (level != 0)
|
||||
{
|
||||
// Check whether the extension is ".ini"
|
||||
size_t filenameLen = filename.size();
|
||||
if (filenameLen >= 4 && _wcsicmp(fileData.cFileName + (filenameLen - 4), L".ini") == 0)
|
||||
{
|
||||
foundFiles = true;
|
||||
folder.files.push_back(filename);
|
||||
++index;
|
||||
}
|
||||
}
|
||||
}
|
||||
while (FindNextFile(hSearch, &fileData));
|
||||
|
||||
FindClose(hSearch);
|
||||
|
||||
if (level > 0 && (foundFiles || !subfolders.empty()))
|
||||
{
|
||||
if (level == 1)
|
||||
{
|
||||
folder.name = base;
|
||||
}
|
||||
else
|
||||
{
|
||||
std::wstring::size_type pos = base.rfind(L'\\') + 1;
|
||||
folder.name.assign(base, pos, base.length() - pos);
|
||||
}
|
||||
|
||||
m_Folders.push_back(std::move(folder));
|
||||
}
|
||||
}
|
||||
|
||||
if (level != 0)
|
||||
{
|
||||
base += L'\\';
|
||||
}
|
||||
|
||||
if (!subfolders.empty())
|
||||
{
|
||||
bool popFolder = !foundFiles;
|
||||
|
||||
std::list<std::wstring>::const_iterator iter = subfolders.begin();
|
||||
for ( ; iter != subfolders.end(); ++iter)
|
||||
{
|
||||
int newIndex = PopulateRecursive(path, base + (*iter), index, level + 1);
|
||||
if (newIndex != index)
|
||||
{
|
||||
popFolder = false;
|
||||
}
|
||||
|
||||
index = newIndex;
|
||||
}
|
||||
|
||||
if (popFolder)
|
||||
{
|
||||
m_Folders.pop_back();
|
||||
}
|
||||
}
|
||||
|
||||
return index;
|
||||
}
|
@ -1,105 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2013 Rainmeter Team
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef RM_LIBRARY_SKINDIRECTORY_H_
|
||||
#define RM_LIBRARY_SKINDIRECTORY_H_
|
||||
|
||||
#include <Windows.h>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <cstdint>
|
||||
|
||||
// Reprsents a hierarchy of skin folders (reprsented by the Folder struct) and the names of their
|
||||
// respective files.
|
||||
class SkinRegistry
|
||||
{
|
||||
public:
|
||||
SkinRegistry() = default;
|
||||
SkinRegistry(const SkinRegistry& other) = delete;
|
||||
SkinRegistry& operator=(SkinRegistry other) = delete;
|
||||
|
||||
struct Folder
|
||||
{
|
||||
std::wstring name;
|
||||
std::vector<std::wstring> files;
|
||||
UINT baseID;
|
||||
|
||||
int16_t active;
|
||||
int16_t level;
|
||||
|
||||
Folder() {}
|
||||
~Folder() {}
|
||||
|
||||
Folder(Folder&& r) :
|
||||
name(std::move(r.name)),
|
||||
files(std::move(r.files)),
|
||||
baseID(r.baseID),
|
||||
active(r.active),
|
||||
level(r.level)
|
||||
{
|
||||
}
|
||||
|
||||
Folder& operator=(Folder&& r)
|
||||
{
|
||||
name = std::move(r.name);
|
||||
files = std::move(r.files);
|
||||
baseID = r.baseID;
|
||||
active = r.active;
|
||||
level = r.level;
|
||||
return *this;
|
||||
}
|
||||
};
|
||||
|
||||
struct Indexes
|
||||
{
|
||||
int folder;
|
||||
int file;
|
||||
|
||||
Indexes(int folderIndex = 0, int fileIndex = 0) : folder(folderIndex), file(fileIndex) {}
|
||||
|
||||
bool IsValid() const { return folder != -1; }
|
||||
|
||||
static Indexes Invalid() { return Indexes(-1, 0); }
|
||||
};
|
||||
|
||||
int FindFolderIndex(const std::wstring& folderPath) const;
|
||||
Folder* FindFolder(const std::wstring& folderPath);
|
||||
|
||||
Indexes FindIndexes(const std::wstring& folderPath, const std::wstring& file);
|
||||
Indexes FindIndexesForID(UINT id);
|
||||
|
||||
std::wstring GetFolderPath(int folderIndex) const;
|
||||
|
||||
Folder& GetFolder(int index) { return m_Folders[index]; }
|
||||
int GetFolderCount() const { return (int)m_Folders.size(); }
|
||||
bool IsEmpty() const { return m_Folders.empty(); }
|
||||
|
||||
void Populate(const std::wstring& path);
|
||||
|
||||
private:
|
||||
int PopulateRecursive(const std::wstring& path, std::wstring base, int index, UINT level);
|
||||
|
||||
// Contains a sequential list of Folders. The folders are arranged as follows:
|
||||
// A (index: 0, level: 1)
|
||||
// B (index: 1, level: 2)
|
||||
// C (index: 2, level: 3)
|
||||
// D (index: 3, level: 2)
|
||||
std::vector<Folder> m_Folders;
|
||||
};
|
||||
|
||||
#endif
|
@ -1,104 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2013 Rainmeter Team
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "StdAfx.h"
|
||||
#include "SkinRegistry.h"
|
||||
#include "../Common/UnitTest.h"
|
||||
|
||||
TEST_CLASS(Library_SkinRegistry_Test)
|
||||
{
|
||||
public:
|
||||
Library_SkinRegistry_Test()
|
||||
{
|
||||
m_SkinRegistry.Populate(L"..\\..\\..\\Library\\Test\\SkinRegistry\\");
|
||||
}
|
||||
|
||||
TEST_METHOD(TestContents)
|
||||
{
|
||||
std::vector<std::wstring> files1;
|
||||
files1.push_back(L"1.ini");
|
||||
|
||||
std::vector<std::wstring> files3;
|
||||
files3.push_back(L"1.ini");
|
||||
files3.push_back(L"2.ini");
|
||||
files3.push_back(L"3.ini");
|
||||
|
||||
Assert::AreEqual(5, m_SkinRegistry.GetFolderCount());
|
||||
|
||||
const auto& folderA1 = m_SkinRegistry.GetFolder(0);
|
||||
Assert::AreEqual(L"A1", folderA1.name.c_str());
|
||||
Assert::AreEqual((int16_t)1, folderA1.level);
|
||||
Assert::IsTrue(folderA1.files.empty());
|
||||
|
||||
const auto& folderA1_B1 = m_SkinRegistry.GetFolder(1);
|
||||
Assert::AreEqual(L"B1", folderA1_B1.name.c_str());
|
||||
Assert::AreEqual((int16_t)2, folderA1_B1.level);
|
||||
Assert::IsTrue(files1 == folderA1_B1.files);
|
||||
|
||||
const auto& folderA1_B2 = m_SkinRegistry.GetFolder(2);
|
||||
Assert::AreEqual(L"B2", folderA1_B2.name.c_str());
|
||||
Assert::AreEqual((int16_t)2, folderA1_B2.level);
|
||||
Assert::IsTrue(files1 == folderA1_B2.files);
|
||||
|
||||
const auto& folderA1_B2_C1 = m_SkinRegistry.GetFolder(3);
|
||||
Assert::AreEqual(L"C1", folderA1_B2_C1.name.c_str());
|
||||
Assert::AreEqual((int16_t)3, folderA1_B2_C1.level);
|
||||
Assert::IsTrue(files1 == folderA1_B2_C1.files);
|
||||
|
||||
const auto& folderA2 = m_SkinRegistry.GetFolder(4);
|
||||
Assert::AreEqual(L"A2", folderA2.name.c_str());
|
||||
Assert::AreEqual((int16_t)1, folderA2.level);
|
||||
Assert::IsTrue(files3 == folderA2.files);
|
||||
}
|
||||
|
||||
TEST_METHOD(TestFindFolderIndex)
|
||||
{
|
||||
Assert::AreEqual(3, m_SkinRegistry.FindFolderIndex(L"A1\\B2\\C1"));
|
||||
Assert::AreEqual(-1, m_SkinRegistry.FindFolderIndex(L"A1\\B5\\C1"));
|
||||
}
|
||||
|
||||
TEST_METHOD(TestFindIndexes)
|
||||
{
|
||||
const auto indexes1 = m_SkinRegistry.FindIndexes(L"A1\\B2", L"1.ini");
|
||||
Assert::IsTrue(indexes1.folder == 2 && indexes1.file == 0);
|
||||
|
||||
const auto indexes2 = m_SkinRegistry.FindIndexes(L"A2", L"2.ini");
|
||||
Assert::IsTrue(indexes2.folder == 4 && indexes2.file == 1);
|
||||
|
||||
const auto indexes3 = m_SkinRegistry.FindIndexes(L"A3", L"1.ini");
|
||||
Assert::IsFalse(indexes3.IsValid());
|
||||
}
|
||||
|
||||
TEST_METHOD(TestFindIndexesForID)
|
||||
{
|
||||
const auto indexes1 = m_SkinRegistry.FindIndexesForID(30002);
|
||||
Assert::IsTrue(indexes1.folder == 2 && indexes1.file == 0);
|
||||
|
||||
const auto indexes2 = m_SkinRegistry.FindIndexesForID(30005);
|
||||
Assert::IsTrue(indexes2.folder == 4 && indexes2.file == 1);
|
||||
}
|
||||
|
||||
TEST_METHOD(TestGetFolderPath)
|
||||
{
|
||||
Assert::AreEqual(L"A1\\B2\\C1", m_SkinRegistry.GetFolderPath(3).c_str());
|
||||
Assert::AreEqual(L"A2", m_SkinRegistry.GetFolderPath(4).c_str());
|
||||
}
|
||||
|
||||
private:
|
||||
SkinRegistry m_SkinRegistry;
|
||||
};
|
@ -942,9 +942,8 @@ LRESULT CALLBACK System::WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lPa
|
||||
break;
|
||||
|
||||
case TIMER_RESUME:
|
||||
KillTimer(hWnd, TIMER_RESUME);
|
||||
if (GetRainmeter().IsRedrawable())
|
||||
{
|
||||
KillTimer(hWnd, TIMER_RESUME);
|
||||
std::map<std::wstring, MeterWindow*>::const_iterator iter = GetRainmeter().GetAllMeterWindows().begin();
|
||||
for ( ; iter != GetRainmeter().GetAllMeterWindows().end(); ++iter)
|
||||
{
|
||||
@ -1147,7 +1146,7 @@ void System::SetWallpaper(const std::wstring& wallpaper, const std::wstring& sty
|
||||
Bitmap bitmap(wallpaper.c_str());
|
||||
if (bitmap.GetLastStatus() == Ok)
|
||||
{
|
||||
std::wstring file = GetRainmeter().GetSettingsPath() + L"Wallpaper.bmp";
|
||||
std::wstring file = /*TODO - fix: GetRainmeter().GetSettingsPath() + */ L"Wallpaper.bmp";
|
||||
|
||||
const CLSID bmpClsid = { 0x557cf400, 0x1a04, 0x11d3, { 0x9a, 0x73, 0x0, 0x0, 0xf8, 0x1e, 0xf3, 0x2e } };
|
||||
if (bitmap.Save(file.c_str(), &bmpClsid) == Ok)
|
||||
|
@ -318,7 +318,7 @@ void TintedImage::LoadImage(const std::wstring& imageName, bool bLoadAlways)
|
||||
// Load the bitmap if defined
|
||||
if (!imageName.empty())
|
||||
{
|
||||
std::wstring filename = m_Path + imageName;
|
||||
std::wstring filename = m_WorkDirectory + imageName;
|
||||
if (m_MeterWindow) m_MeterWindow->MakePathAbsolute(filename);
|
||||
m_HasPathChanged = false;
|
||||
|
||||
@ -629,12 +629,12 @@ void TintedImage::ReadOptions(ConfigParser& parser, const WCHAR* section, const
|
||||
ColorMatrix oldColorMatrix = *m_ColorMatrix;
|
||||
RotateFlipType oldFlip = m_Flip;
|
||||
REAL oldRotate = m_Rotate;
|
||||
std::wstring oldPath = m_Path;
|
||||
std::wstring oldPath = m_WorkDirectory;
|
||||
|
||||
m_Path = parser.ReadString(section, m_OptionArray[OptionIndexImagePath], imagePath);
|
||||
PathUtil::AppendBacklashIfMissing(m_Path);
|
||||
m_WorkDirectory = parser.ReadString(section, m_OptionArray[OptionIndexImagePath], imagePath);
|
||||
PathUtil::AppendBacklashIfMissing(m_WorkDirectory);
|
||||
|
||||
m_HasPathChanged = (oldPath != m_Path);
|
||||
m_HasPathChanged = (oldPath != m_WorkDirectory);
|
||||
|
||||
if (!m_DisableTransform)
|
||||
{
|
||||
|
@ -128,7 +128,7 @@ protected:
|
||||
Gdiplus::REAL m_Rotate;
|
||||
bool m_UseExifOrientation;
|
||||
|
||||
std::wstring m_Path;
|
||||
std::wstring m_WorkDirectory;
|
||||
bool m_HasPathChanged;
|
||||
|
||||
std::wstring m_CacheKey;
|
||||
|
@ -1,736 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2004 Kimmo Pekkola
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "StdAfx.h"
|
||||
#include "TrayWindow.h"
|
||||
#include "Measure.h"
|
||||
#include "resource.h"
|
||||
#include "Litestep.h"
|
||||
#include "Rainmeter.h"
|
||||
#include "DialogAbout.h"
|
||||
#include "DialogManage.h"
|
||||
#include "System.h"
|
||||
#include "Error.h"
|
||||
#include "RainmeterQuery.h"
|
||||
#include "resource.h"
|
||||
#include "../Version.h"
|
||||
|
||||
#define RAINMETER_OFFICIAL L"http://rainmeter.net/cms/"
|
||||
#define RAINMETER_HELP L"http://docs.rainmeter.net/"
|
||||
|
||||
#define ZPOS_FLAGS (SWP_NOMOVE | SWP_NOSIZE | SWP_NOOWNERZORDER | SWP_NOACTIVATE | SWP_NOSENDCHANGING)
|
||||
|
||||
enum TIMER
|
||||
{
|
||||
TIMER_ADDTRAYICON = 1,
|
||||
TIMER_TRAYMEASURE = 3
|
||||
};
|
||||
enum INTERVAL
|
||||
{
|
||||
INTERVAL_ADDTRAYICON = 3000,
|
||||
INTERVAL_TRAYMEASURE = 1000
|
||||
};
|
||||
|
||||
const UINT WM_TASKBARCREATED = ::RegisterWindowMessage(L"TaskbarCreated");
|
||||
|
||||
using namespace Gdiplus;
|
||||
|
||||
TrayWindow::TrayWindow() :
|
||||
m_Icon(),
|
||||
m_Measure(),
|
||||
m_MeterType(TRAY_METER_TYPE_HISTOGRAM),
|
||||
m_Color1(0, 100, 0),
|
||||
m_Color2(0, 255, 0),
|
||||
m_Bitmap(),
|
||||
m_Values(),
|
||||
m_Pos(),
|
||||
m_Notification(TRAY_NOTIFICATION_NONE),
|
||||
m_TrayContextMenuEnabled(true),
|
||||
m_IconEnabled(true)
|
||||
{
|
||||
}
|
||||
|
||||
TrayWindow::~TrayWindow()
|
||||
{
|
||||
KillTimer(m_Window, TIMER_ADDTRAYICON);
|
||||
KillTimer(m_Window, TIMER_TRAYMEASURE);
|
||||
RemoveTrayIcon();
|
||||
|
||||
delete m_Bitmap;
|
||||
delete m_Measure;
|
||||
|
||||
for (size_t i = 0, isize = m_Icons.size(); i < isize; ++i)
|
||||
{
|
||||
DestroyIcon(m_Icons[i]);
|
||||
}
|
||||
m_Icons.clear();
|
||||
|
||||
if (m_Window) DestroyWindow(m_Window);
|
||||
}
|
||||
|
||||
void TrayWindow::Initialize()
|
||||
{
|
||||
WNDCLASS wc = {0};
|
||||
wc.lpfnWndProc = (WNDPROC)WndProc;
|
||||
wc.hInstance = GetRainmeter().GetModuleInstance();
|
||||
wc.lpszClassName = L"RainmeterTrayClass";
|
||||
wc.hIcon = GetIcon(IDI_RAINMETER);
|
||||
|
||||
RegisterClass(&wc);
|
||||
|
||||
m_Window = CreateWindowEx(
|
||||
WS_EX_TOOLWINDOW,
|
||||
L"RainmeterTrayClass",
|
||||
nullptr,
|
||||
WS_POPUP | WS_DISABLED,
|
||||
CW_USEDEFAULT,
|
||||
CW_USEDEFAULT,
|
||||
CW_USEDEFAULT,
|
||||
CW_USEDEFAULT,
|
||||
nullptr,
|
||||
nullptr,
|
||||
wc.hInstance,
|
||||
this);
|
||||
|
||||
SetWindowPos(m_Window, HWND_BOTTOM, 0, 0, 0, 0, ZPOS_FLAGS);
|
||||
}
|
||||
|
||||
bool TrayWindow::AddTrayIcon()
|
||||
{
|
||||
NOTIFYICONDATA tnid = {sizeof(NOTIFYICONDATA)};
|
||||
tnid.hWnd = m_Window;
|
||||
tnid.uID = IDI_TRAY;
|
||||
tnid.uFlags = NIF_MESSAGE | NIF_ICON | NIF_TIP;
|
||||
tnid.uCallbackMessage = WM_TRAY_NOTIFYICON;
|
||||
tnid.hIcon = m_Icon;
|
||||
wcsncpy_s(tnid.szTip, APPNAME, _TRUNCATE);
|
||||
|
||||
return (Shell_NotifyIcon(NIM_ADD, &tnid) || GetLastError() != ERROR_TIMEOUT);
|
||||
}
|
||||
|
||||
bool TrayWindow::IsTrayIconReady()
|
||||
{
|
||||
NOTIFYICONDATA tnid = {sizeof(NOTIFYICONDATA)};
|
||||
tnid.hWnd = m_Window;
|
||||
tnid.uID = IDI_TRAY;
|
||||
|
||||
return Shell_NotifyIcon(NIM_MODIFY, &tnid) != FALSE;
|
||||
}
|
||||
|
||||
void TrayWindow::TryAddTrayIcon()
|
||||
{
|
||||
if (IsTrayIconReady())
|
||||
{
|
||||
ModifyTrayIcon(0);
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_Icon)
|
||||
{
|
||||
DestroyIcon(m_Icon);
|
||||
m_Icon = nullptr;
|
||||
}
|
||||
|
||||
m_Icon = CreateTrayIcon(0);
|
||||
|
||||
if (!AddTrayIcon())
|
||||
{
|
||||
SetTimer(m_Window, TIMER_ADDTRAYICON, INTERVAL_ADDTRAYICON, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
void TrayWindow::CheckTrayIcon()
|
||||
{
|
||||
if (IsTrayIconReady() || AddTrayIcon())
|
||||
{
|
||||
KillTimer(m_Window, TIMER_ADDTRAYICON);
|
||||
}
|
||||
}
|
||||
|
||||
void TrayWindow::RemoveTrayIcon()
|
||||
{
|
||||
NOTIFYICONDATA tnid = {sizeof(NOTIFYICONDATA)};
|
||||
tnid.hWnd = m_Window;
|
||||
tnid.uID = IDI_TRAY;
|
||||
tnid.uFlags = 0;
|
||||
|
||||
Shell_NotifyIcon(NIM_DELETE, &tnid);
|
||||
|
||||
if (m_Icon)
|
||||
{
|
||||
DestroyIcon(m_Icon);
|
||||
m_Icon = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
void TrayWindow::ModifyTrayIcon(double value)
|
||||
{
|
||||
if (m_Icon)
|
||||
{
|
||||
DestroyIcon(m_Icon);
|
||||
m_Icon = nullptr;
|
||||
}
|
||||
|
||||
m_Icon = CreateTrayIcon(value);
|
||||
|
||||
NOTIFYICONDATA tnid = {sizeof(NOTIFYICONDATA)};
|
||||
tnid.hWnd = m_Window;
|
||||
tnid.uID = IDI_TRAY;
|
||||
tnid.uFlags = NIF_ICON;
|
||||
tnid.hIcon = m_Icon;
|
||||
|
||||
Shell_NotifyIcon(NIM_MODIFY, &tnid);
|
||||
}
|
||||
|
||||
HICON TrayWindow::CreateTrayIcon(double value)
|
||||
{
|
||||
if (m_Measure != nullptr)
|
||||
{
|
||||
if (m_MeterType == TRAY_METER_TYPE_HISTOGRAM)
|
||||
{
|
||||
m_Values[m_Pos] = value;
|
||||
m_Pos = (m_Pos + 1) % TRAYICON_SIZE;
|
||||
|
||||
Bitmap trayBitmap(TRAYICON_SIZE, TRAYICON_SIZE);
|
||||
Graphics graphics(&trayBitmap);
|
||||
graphics.SetSmoothingMode(SmoothingModeAntiAlias);
|
||||
|
||||
Point points[TRAYICON_SIZE + 2];
|
||||
points[0].X = 0;
|
||||
points[0].Y = TRAYICON_SIZE;
|
||||
points[TRAYICON_SIZE + 1].X = TRAYICON_SIZE - 1;
|
||||
points[TRAYICON_SIZE + 1].Y = TRAYICON_SIZE;
|
||||
|
||||
for (int i = 0; i < TRAYICON_SIZE; ++i)
|
||||
{
|
||||
points[i + 1].X = i;
|
||||
points[i + 1].Y = (int)(TRAYICON_SIZE * (1.0 - m_Values[(m_Pos + i) % TRAYICON_SIZE]));
|
||||
}
|
||||
|
||||
SolidBrush brush(m_Color1);
|
||||
graphics.FillRectangle(&brush, 0, 0, TRAYICON_SIZE, TRAYICON_SIZE);
|
||||
|
||||
SolidBrush brush2(m_Color2);
|
||||
graphics.FillPolygon(&brush2, points, TRAYICON_SIZE + 2);
|
||||
|
||||
HICON icon = nullptr;
|
||||
trayBitmap.GetHICON(&icon);
|
||||
return icon;
|
||||
}
|
||||
else if (m_MeterType == TRAY_METER_TYPE_BITMAP && (m_Bitmap || !m_Icons.empty()))
|
||||
{
|
||||
if (!m_Icons.empty())
|
||||
{
|
||||
size_t frame = 0;
|
||||
size_t frameCount = m_Icons.size();
|
||||
|
||||
// Select the correct frame linearly
|
||||
frame = (size_t)(value * frameCount);
|
||||
frame = min((frameCount - 1), frame);
|
||||
|
||||
return CopyIcon(m_Icons[frame]);
|
||||
}
|
||||
else
|
||||
{
|
||||
int frame = 0;
|
||||
int frameCount = 0;
|
||||
int newX, newY;
|
||||
|
||||
if (m_Bitmap->GetWidth() > m_Bitmap->GetHeight())
|
||||
{
|
||||
frameCount = m_Bitmap->GetWidth() / TRAYICON_SIZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
frameCount = m_Bitmap->GetHeight() / TRAYICON_SIZE;
|
||||
}
|
||||
|
||||
// Select the correct frame linearly
|
||||
frame = (int)(value * frameCount);
|
||||
frame = min((frameCount - 1), frame);
|
||||
|
||||
if (m_Bitmap->GetWidth() > m_Bitmap->GetHeight())
|
||||
{
|
||||
newX = frame * TRAYICON_SIZE;
|
||||
newY = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
newX = 0;
|
||||
newY = frame * TRAYICON_SIZE;
|
||||
}
|
||||
|
||||
Bitmap trayBitmap(TRAYICON_SIZE, TRAYICON_SIZE);
|
||||
Graphics graphics(&trayBitmap);
|
||||
graphics.SetSmoothingMode(SmoothingModeAntiAlias);
|
||||
|
||||
// Blit the image
|
||||
Rect r(0, 0, TRAYICON_SIZE, TRAYICON_SIZE);
|
||||
graphics.DrawImage(m_Bitmap, r, newX, newY, TRAYICON_SIZE, TRAYICON_SIZE, UnitPixel);
|
||||
|
||||
HICON icon = nullptr;
|
||||
trayBitmap.GetHICON(&icon);
|
||||
return icon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Return the default icon if there is no valid measure
|
||||
return GetIcon(IDI_TRAY);
|
||||
}
|
||||
|
||||
void TrayWindow::ShowNotification(TRAY_NOTIFICATION id, const WCHAR* title, const WCHAR* text)
|
||||
{
|
||||
if (m_Notification == TRAY_NOTIFICATION_NONE)
|
||||
{
|
||||
NOTIFYICONDATA nid = {sizeof(NOTIFYICONDATA)};
|
||||
nid.hWnd = m_Window;
|
||||
nid.uID = IDI_TRAY;
|
||||
nid.uFlags = NIF_INFO;
|
||||
nid.uTimeout = 30000;
|
||||
nid.dwInfoFlags = NIIF_USER;
|
||||
wcsncpy_s(nid.szInfoTitle, title, _TRUNCATE);
|
||||
wcsncpy_s(nid.szInfo, text, _TRUNCATE);
|
||||
|
||||
if (IsWindows7OrGreater())
|
||||
{
|
||||
nid.dwInfoFlags |= NIIF_LARGE_ICON;
|
||||
nid.hBalloonIcon = GetIcon(IDI_RAINMETER, true);
|
||||
}
|
||||
|
||||
if (Shell_NotifyIcon(NIM_MODIFY, &nid))
|
||||
{
|
||||
m_Notification = id;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void TrayWindow::ShowWelcomeNotification()
|
||||
{
|
||||
ShowNotification(TRAY_NOTIFICATION_WELCOME, GetString(ID_STR_WELCOME), GetString(ID_STR_CLICKTOMANAGE));
|
||||
}
|
||||
|
||||
void TrayWindow::ShowUpdateNotification(const WCHAR* newVersion)
|
||||
{
|
||||
std::wstring text = GetFormattedString(ID_STR_CLICKTODOWNLOAD, newVersion);
|
||||
ShowNotification(TRAY_NOTIFICATION_UPDATE, GetString(ID_STR_UPDATEAVAILABLE), text.c_str());
|
||||
}
|
||||
|
||||
void TrayWindow::SetTrayIcon(bool enabled)
|
||||
{
|
||||
enabled ? TryAddTrayIcon() : RemoveTrayIcon();
|
||||
m_IconEnabled = enabled;
|
||||
|
||||
// Save to Rainmeter.ini.
|
||||
const std::wstring& iniFile = GetRainmeter().GetIniFile();
|
||||
WritePrivateProfileString(L"Rainmeter", L"TrayIcon", enabled ? nullptr : L"0", iniFile.c_str());
|
||||
}
|
||||
|
||||
void TrayWindow::ReadOptions(ConfigParser& parser)
|
||||
{
|
||||
// Clear old Settings
|
||||
KillTimer(m_Window, TIMER_ADDTRAYICON);
|
||||
KillTimer(m_Window, TIMER_TRAYMEASURE);
|
||||
|
||||
delete m_Measure;
|
||||
m_Measure = nullptr;
|
||||
|
||||
delete m_Bitmap;
|
||||
m_Bitmap = nullptr;
|
||||
|
||||
std::vector<HICON>::const_iterator iter = m_Icons.begin();
|
||||
for ( ; iter != m_Icons.end(); ++iter)
|
||||
{
|
||||
DestroyIcon((*iter));
|
||||
}
|
||||
m_Icons.clear();
|
||||
|
||||
m_MeterType = TRAY_METER_TYPE_NONE;
|
||||
|
||||
// Read tray settings
|
||||
m_IconEnabled = parser.ReadBool(L"Rainmeter", L"TrayIcon", true);
|
||||
if (m_IconEnabled)
|
||||
{
|
||||
const std::wstring& measureName = parser.ReadString(L"TrayMeasure", L"Measure", L"");
|
||||
|
||||
if (!measureName.empty())
|
||||
{
|
||||
ConfigParser* oldParser = GetRainmeter().GetCurrentParser();
|
||||
GetRainmeter().SetCurrentParser(&parser);
|
||||
|
||||
m_Measure = Measure::Create(measureName.c_str(), nullptr, L"TrayMeasure");
|
||||
if (m_Measure)
|
||||
{
|
||||
m_Measure->ReadOptions(parser);
|
||||
}
|
||||
|
||||
GetRainmeter().SetCurrentParser(oldParser);
|
||||
}
|
||||
|
||||
const WCHAR* type = parser.ReadString(L"TrayMeasure", L"TrayMeter", m_Measure ? L"HISTOGRAM" : L"NONE").c_str();
|
||||
if (_wcsicmp(type, L"NONE") == 0)
|
||||
{
|
||||
// Use main icon
|
||||
}
|
||||
else if (_wcsicmp(type, L"HISTOGRAM") == 0)
|
||||
{
|
||||
m_MeterType = TRAY_METER_TYPE_HISTOGRAM;
|
||||
m_Color1 = parser.ReadColor(L"TrayMeasure", L"TrayColor1", Color::MakeARGB(255, 0, 100, 0));
|
||||
m_Color2 = parser.ReadColor(L"TrayMeasure", L"TrayColor2", Color::MakeARGB(255, 0, 255, 0));
|
||||
}
|
||||
else if (_wcsicmp(type, L"BITMAP") == 0)
|
||||
{
|
||||
m_MeterType = TRAY_METER_TYPE_BITMAP;
|
||||
|
||||
std::wstring imageName = parser.ReadString(L"TrayMeasure", L"TrayBitmap", L"");
|
||||
|
||||
// Load the bitmaps if defined
|
||||
if (!imageName.empty())
|
||||
{
|
||||
imageName.insert(0, GetRainmeter().GetSkinPath());
|
||||
const WCHAR* imagePath = imageName.c_str();
|
||||
if (_wcsicmp(imagePath + (imageName.size() - 4), L".ico") == 0)
|
||||
{
|
||||
int count = 1;
|
||||
HICON hIcon = nullptr;
|
||||
|
||||
// Load the icons
|
||||
do
|
||||
{
|
||||
WCHAR buffer[MAX_PATH];
|
||||
_snwprintf_s(buffer, _TRUNCATE, imagePath, count++);
|
||||
|
||||
hIcon = (HICON)LoadImage(nullptr, buffer, IMAGE_ICON, TRAYICON_SIZE, TRAYICON_SIZE, LR_LOADFROMFILE);
|
||||
if (hIcon) m_Icons.push_back(hIcon);
|
||||
if (wcscmp(imagePath, buffer) == 0) break;
|
||||
}
|
||||
while(hIcon != nullptr);
|
||||
}
|
||||
|
||||
if (m_Icons.empty())
|
||||
{
|
||||
// No icons found so load as bitmap
|
||||
delete m_Bitmap;
|
||||
m_Bitmap = new Bitmap(imagePath);
|
||||
Status status = m_Bitmap->GetLastStatus();
|
||||
if (Ok != status)
|
||||
{
|
||||
delete m_Bitmap;
|
||||
m_Bitmap = nullptr;
|
||||
LogWarningF(L"Bitmap image not found: %s", imagePath);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
LogErrorF(L"No such TrayMeter: %s", type);
|
||||
}
|
||||
|
||||
TryAddTrayIcon();
|
||||
|
||||
if (m_Measure)
|
||||
{
|
||||
SetTimer(m_Window, TIMER_TRAYMEASURE, INTERVAL_TRAYMEASURE, nullptr); // Update the tray once per sec
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
RemoveTrayIcon();
|
||||
}
|
||||
}
|
||||
|
||||
LRESULT CALLBACK TrayWindow::WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
TrayWindow* tray = GetRainmeter().GetTrayWindow();
|
||||
|
||||
switch (uMsg)
|
||||
{
|
||||
case WM_COMMAND:
|
||||
switch (wParam)
|
||||
{
|
||||
case IDM_MANAGE:
|
||||
DialogManage::Open();
|
||||
break;
|
||||
|
||||
case IDM_ABOUT:
|
||||
DialogAbout::Open();
|
||||
break;
|
||||
|
||||
case IDM_SHOW_HELP:
|
||||
CommandHandler::RunFile(RAINMETER_HELP);
|
||||
break;
|
||||
|
||||
case IDM_NEW_VERSION:
|
||||
CommandHandler::RunFile(RAINMETER_OFFICIAL);
|
||||
break;
|
||||
|
||||
case IDM_REFRESH:
|
||||
PostMessage(GetRainmeter().GetWindow(), WM_RAINMETER_DELAYED_REFRESH_ALL, (WPARAM)nullptr, (LPARAM)nullptr);
|
||||
break;
|
||||
|
||||
case IDM_SHOWLOGFILE:
|
||||
GetRainmeter().ShowLogFile();
|
||||
break;
|
||||
|
||||
case IDM_STARTLOG:
|
||||
GetLogger().StartLogFile();
|
||||
break;
|
||||
|
||||
case IDM_STOPLOG:
|
||||
GetLogger().StopLogFile();
|
||||
break;
|
||||
|
||||
case IDM_DELETELOGFILE:
|
||||
GetLogger().DeleteLogFile();
|
||||
break;
|
||||
|
||||
case IDM_DEBUGLOG:
|
||||
GetRainmeter().SetDebug(!GetRainmeter().GetDebug());
|
||||
break;
|
||||
|
||||
case IDM_DISABLEDRAG:
|
||||
GetRainmeter().SetDisableDragging(!GetRainmeter().GetDisableDragging());
|
||||
break;
|
||||
|
||||
case IDM_EDITCONFIG:
|
||||
GetRainmeter().EditSettings();
|
||||
break;
|
||||
|
||||
case IDM_QUIT:
|
||||
PostQuitMessage(0);
|
||||
break;
|
||||
|
||||
case IDM_OPENSKINSFOLDER:
|
||||
GetRainmeter().OpenSkinFolder();
|
||||
break;
|
||||
|
||||
default:
|
||||
{
|
||||
UINT mID = wParam & 0x0FFFF;
|
||||
|
||||
if (mID >= ID_THEME_FIRST && mID <= ID_THEME_LAST)
|
||||
{
|
||||
int pos = mID - ID_THEME_FIRST;
|
||||
|
||||
const std::vector<std::wstring>& layouts = GetRainmeter().GetAllLayouts();
|
||||
if (pos >= 0 && pos < (int)layouts.size())
|
||||
{
|
||||
GetRainmeter().LoadLayout(layouts[pos]);
|
||||
}
|
||||
}
|
||||
else if (mID >= ID_CONFIG_FIRST && mID <= ID_CONFIG_LAST)
|
||||
{
|
||||
GetRainmeter().ToggleSkinWithID(mID);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Forward the message to correct window
|
||||
int index = (int)(wParam >> 16);
|
||||
const std::map<std::wstring, MeterWindow*>& windows = GetRainmeter().GetAllMeterWindows();
|
||||
|
||||
if (index < (int)windows.size())
|
||||
{
|
||||
std::map<std::wstring, MeterWindow*>::const_iterator iter = windows.begin();
|
||||
for ( ; iter != windows.end(); ++iter)
|
||||
{
|
||||
--index;
|
||||
if (index < 0)
|
||||
{
|
||||
MeterWindow* meterWindow = (*iter).second;
|
||||
SendMessage(meterWindow->GetWindow(), WM_COMMAND, mID, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
break; // Don't send WM_COMMANDS any further
|
||||
|
||||
case WM_TRAY_NOTIFYICON:
|
||||
{
|
||||
UINT uMouseMsg = (UINT)lParam;
|
||||
LPCWSTR bang;
|
||||
|
||||
// Check TrayExecute actions
|
||||
switch (uMouseMsg)
|
||||
{
|
||||
case WM_MBUTTONDOWN:
|
||||
bang = GetRainmeter().GetTrayExecuteM().c_str();
|
||||
break;
|
||||
|
||||
case WM_RBUTTONDOWN:
|
||||
bang = GetRainmeter().GetTrayExecuteR().c_str();
|
||||
break;
|
||||
|
||||
case WM_MBUTTONDBLCLK:
|
||||
bang = GetRainmeter().GetTrayExecuteDM().c_str();
|
||||
break;
|
||||
|
||||
case WM_RBUTTONDBLCLK:
|
||||
bang = GetRainmeter().GetTrayExecuteDR().c_str();
|
||||
break;
|
||||
|
||||
default:
|
||||
bang = L"";
|
||||
break;
|
||||
}
|
||||
|
||||
if (*bang &&
|
||||
!IsCtrlKeyDown()) // Ctrl is pressed, so only run default action
|
||||
{
|
||||
GetRainmeter().ExecuteCommand(bang, nullptr);
|
||||
tray->m_TrayContextMenuEnabled = (uMouseMsg != WM_RBUTTONDOWN);
|
||||
break;
|
||||
}
|
||||
|
||||
// Run default UI action
|
||||
switch (uMouseMsg)
|
||||
{
|
||||
case WM_RBUTTONDOWN:
|
||||
tray->m_TrayContextMenuEnabled = true;
|
||||
break;
|
||||
|
||||
case WM_RBUTTONUP:
|
||||
if (tray->m_TrayContextMenuEnabled)
|
||||
{
|
||||
POINT pos = System::GetCursorPosition();
|
||||
GetRainmeter().ShowContextMenu(pos, nullptr);
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_LBUTTONUP:
|
||||
case WM_LBUTTONDBLCLK:
|
||||
DialogManage::Open();
|
||||
break;
|
||||
|
||||
case NIN_BALLOONUSERCLICK:
|
||||
if (tray->m_Notification == TRAY_NOTIFICATION_WELCOME)
|
||||
{
|
||||
DialogManage::Open();
|
||||
}
|
||||
else if (tray->m_Notification == TRAY_NOTIFICATION_UPDATE)
|
||||
{
|
||||
CommandHandler::RunFile(RAINMETER_OFFICIAL);
|
||||
}
|
||||
tray->m_Notification = TRAY_NOTIFICATION_NONE;
|
||||
break;
|
||||
|
||||
case NIN_BALLOONHIDE:
|
||||
case NIN_BALLOONTIMEOUT:
|
||||
tray->m_Notification = TRAY_NOTIFICATION_NONE;
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_QUERY_RAINMETER:
|
||||
if (IsWindow((HWND)lParam))
|
||||
{
|
||||
auto sendCopyData = [&](const std::wstring& data)
|
||||
{
|
||||
COPYDATASTRUCT cds;
|
||||
cds.dwData = wParam;
|
||||
cds.cbData = (DWORD)((data.length() + 1) * sizeof(WCHAR));
|
||||
cds.lpData = (PVOID)data.c_str();
|
||||
SendMessage((HWND)lParam, WM_COPYDATA, (WPARAM)hWnd, (LPARAM)&cds);
|
||||
};
|
||||
|
||||
switch (wParam)
|
||||
{
|
||||
case RAINMETER_QUERY_ID_SKINS_PATH:
|
||||
sendCopyData(GetRainmeter().GetSkinPath());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_SETTINGS_PATH:
|
||||
sendCopyData(GetRainmeter().GetSettingsPath());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_PLUGINS_PATH:
|
||||
sendCopyData(GetRainmeter().GetPluginPath());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_PROGRAM_PATH:
|
||||
sendCopyData(GetRainmeter().GetPath());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_LOG_PATH:
|
||||
sendCopyData(GetLogger().GetLogFilePath());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_CONFIG_EDITOR:
|
||||
sendCopyData(GetRainmeter().GetSkinEditor());
|
||||
return 0;
|
||||
|
||||
case RAINMETER_QUERY_ID_IS_DEBUGGING:
|
||||
{
|
||||
BOOL debug = GetRainmeter().GetDebug();
|
||||
SendMessage((HWND)lParam, WM_QUERY_RAINMETER_RETURN, (WPARAM)hWnd, (LPARAM)debug);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
|
||||
case WM_COPYDATA:
|
||||
{
|
||||
COPYDATASTRUCT* cds = (COPYDATASTRUCT*)lParam;
|
||||
if (cds->dwData == RAINMETER_QUERY_ID_SKIN_WINDOWHANDLE)
|
||||
{
|
||||
LPCWSTR folderPath = (LPCWSTR)cds->lpData;
|
||||
MeterWindow* mw = GetRainmeter().GetMeterWindow(folderPath);
|
||||
return (mw) ? (LRESULT)mw->GetWindow() : 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
|
||||
case WM_TIMER:
|
||||
if (wParam == TIMER_TRAYMEASURE)
|
||||
{
|
||||
if (tray->m_Measure)
|
||||
{
|
||||
tray->m_Measure->Update();
|
||||
tray->ModifyTrayIcon(tray->m_Measure->GetRelativeValue());
|
||||
}
|
||||
}
|
||||
else if (wParam == TIMER_ADDTRAYICON)
|
||||
{
|
||||
tray->CheckTrayIcon();
|
||||
}
|
||||
break;
|
||||
|
||||
case WM_DESTROY:
|
||||
PostQuitMessage(0);
|
||||
break;
|
||||
|
||||
default:
|
||||
if (uMsg == WM_TASKBARCREATED)
|
||||
{
|
||||
if (tray->IsTrayIconEnabled())
|
||||
{
|
||||
tray->RemoveTrayIcon();
|
||||
tray->TryAddTrayIcon();
|
||||
}
|
||||
}
|
||||
return DefWindowProc(hWnd, uMsg, wParam, lParam);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
@ -1,101 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2004 Kimmo Pekkola
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __TRAYWINDOW_H__
|
||||
#define __TRAYWINDOW_H__
|
||||
|
||||
#include <windows.h>
|
||||
#include <ole2.h> // For Gdiplus.h.
|
||||
#include <gdiplus.h>
|
||||
#include <vector>
|
||||
|
||||
#define WM_TRAY_NOTIFYICON WM_USER + 101
|
||||
#define TRAYICON_SIZE 16
|
||||
|
||||
enum TRAY_METER_TYPE
|
||||
{
|
||||
TRAY_METER_TYPE_NONE,
|
||||
TRAY_METER_TYPE_HISTOGRAM,
|
||||
TRAY_METER_TYPE_BITMAP
|
||||
};
|
||||
|
||||
class ConfigParser;
|
||||
class Measure;
|
||||
|
||||
class TrayWindow
|
||||
{
|
||||
public:
|
||||
TrayWindow();
|
||||
~TrayWindow();
|
||||
|
||||
TrayWindow(const TrayWindow& other) = delete;
|
||||
TrayWindow& operator=(TrayWindow other) = delete;
|
||||
|
||||
void Initialize();
|
||||
|
||||
void ReadOptions(ConfigParser& parser);
|
||||
HWND GetWindow() { return m_Window; }
|
||||
bool IsTrayIconEnabled() { return m_IconEnabled; }
|
||||
void SetTrayIcon(bool enabled);
|
||||
|
||||
void ShowWelcomeNotification();
|
||||
void ShowUpdateNotification(const WCHAR* newVersion);
|
||||
|
||||
protected:
|
||||
static LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
private:
|
||||
enum TRAY_NOTIFICATION
|
||||
{
|
||||
TRAY_NOTIFICATION_NONE,
|
||||
TRAY_NOTIFICATION_WELCOME,
|
||||
TRAY_NOTIFICATION_UPDATE
|
||||
};
|
||||
|
||||
bool AddTrayIcon();
|
||||
bool IsTrayIconReady();
|
||||
void TryAddTrayIcon();
|
||||
void CheckTrayIcon();
|
||||
void RemoveTrayIcon();
|
||||
void ModifyTrayIcon(double value);
|
||||
HICON CreateTrayIcon(double value);
|
||||
|
||||
void ShowNotification(TRAY_NOTIFICATION id, const WCHAR* title, const WCHAR* text);
|
||||
|
||||
HICON m_Icon;
|
||||
HWND m_Window;
|
||||
Measure* m_Measure;
|
||||
|
||||
TRAY_METER_TYPE m_MeterType;
|
||||
Gdiplus::Color m_Color1;
|
||||
Gdiplus::Color m_Color2;
|
||||
Gdiplus::Bitmap* m_Bitmap;
|
||||
|
||||
std::vector<HICON> m_Icons;
|
||||
|
||||
double m_Values[TRAYICON_SIZE];
|
||||
int m_Pos;
|
||||
|
||||
TRAY_NOTIFICATION m_Notification;
|
||||
|
||||
bool m_TrayContextMenuEnabled;
|
||||
|
||||
bool m_IconEnabled;
|
||||
};
|
||||
|
||||
#endif
|
@ -1,97 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2004 Kimmo Pekkola
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include "StdAfx.h"
|
||||
#include "Litestep.h"
|
||||
#include "Rainmeter.h"
|
||||
#include "TrayWindow.h"
|
||||
#include "../Version.h"
|
||||
|
||||
void CheckVersion(void* dummy)
|
||||
{
|
||||
HINTERNET hRootHandle = InternetOpen(
|
||||
L"Rainmeter",
|
||||
INTERNET_OPEN_TYPE_PRECONFIG,
|
||||
nullptr,
|
||||
nullptr,
|
||||
0);
|
||||
|
||||
if (hRootHandle == nullptr)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
HINTERNET hUrlDump = InternetOpenUrl(
|
||||
hRootHandle, L"http://rainmeter.github.io/rainmeter/release", nullptr, 0, INTERNET_FLAG_RESYNCHRONIZE, 0);
|
||||
if (hUrlDump)
|
||||
{
|
||||
DWORD dwSize;
|
||||
char urlData[16] = {0};
|
||||
if (InternetReadFile(hUrlDump, (LPVOID)urlData, sizeof(urlData) - 1, &dwSize))
|
||||
{
|
||||
auto parseVersion = [](const WCHAR* str)->int
|
||||
{
|
||||
int version = _wtoi(str) * 1000000;
|
||||
const WCHAR* pos = wcschr(str, L'.');
|
||||
if (pos)
|
||||
{
|
||||
++pos; // Skip .
|
||||
version += _wtoi(pos) * 1000;
|
||||
|
||||
pos = wcschr(pos, '.');
|
||||
if (pos)
|
||||
{
|
||||
++pos; // Skip .
|
||||
version += _wtoi(pos);
|
||||
}
|
||||
}
|
||||
return version;
|
||||
};
|
||||
|
||||
std::wstring tmpSz = StringUtil::Widen(urlData);
|
||||
const WCHAR* version = tmpSz.c_str();
|
||||
|
||||
int availableVersion = parseVersion(version);
|
||||
if (availableVersion > RAINMETER_VERSION ||
|
||||
(revision_beta && availableVersion == RAINMETER_VERSION))
|
||||
{
|
||||
GetRainmeter().SetNewVersion();
|
||||
|
||||
WCHAR buffer[32];
|
||||
const WCHAR* dataFile = GetRainmeter().GetDataFile().c_str();
|
||||
GetPrivateProfileString(L"Rainmeter", L"LastCheck", L"0", buffer, _countof(buffer), dataFile);
|
||||
|
||||
// Show tray notification only once per new version
|
||||
int lastVersion = parseVersion(buffer);
|
||||
if (availableVersion > lastVersion)
|
||||
{
|
||||
GetRainmeter().GetTrayWindow()->ShowUpdateNotification(version);
|
||||
WritePrivateProfileString(L"Rainmeter", L"LastCheck", version, dataFile);
|
||||
}
|
||||
}
|
||||
}
|
||||
InternetCloseHandle(hUrlDump);
|
||||
}
|
||||
|
||||
InternetCloseHandle(hRootHandle);
|
||||
}
|
||||
|
||||
void CheckUpdate()
|
||||
{
|
||||
_beginthread(CheckVersion, 0, nullptr);
|
||||
}
|
@ -1,24 +0,0 @@
|
||||
/*
|
||||
Copyright (C) 2004 Kimmo Pekkola
|
||||
|
||||
This program is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU General Public License
|
||||
as published by the Free Software Foundation; either version 2
|
||||
of the License, or (at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __UPDATE_CHECK_H__
|
||||
#define __UPDATE_CHECK_H__
|
||||
|
||||
void CheckUpdate();
|
||||
|
||||
#endif
|
Loading…
x
Reference in New Issue
Block a user