1
// TortoiseGit - a Windows shell extension for easy version control
3 // Copyright (C) 2008-2018, 2020-2021, 2024 - TortoiseGit
4 // Copyright (C) 2003-2008, 2020 - TortoiseSVN
6 // This program is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU General Public License
8 // as published by the Free Software Foundation; either version 2
9 // of the License, or (at your option) any later version.
11 // This program is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
16 // You should have received a copy of the GNU General Public License
17 // along with this program; if not, write to the Free Software Foundation,
18 // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21 #include "TortoiseProc.h"
24 #include "MessageBox.h"
25 #include "../../TGitCache\CacheInterface.h"
26 #include "GitAdminDir.h"
29 #include "DarkModeHelper.h"
30 #include "SetMainPage.h"
31 #include "SetProxyPage.h"
32 #include "SetOverlayPage.h"
33 #include "SetOverlayIcons.h"
34 #include "SetOverlayHandlers.h"
35 #include "SettingsProgsDiff.h"
36 #include "SettingsProgsAlternativeEditor.h"
37 #include "SettingsProgsMerge.h"
38 #include "SetLookAndFeelPage.h"
39 #include "SetDialogs.h"
40 #include "SetDialogs2.h"
41 #include "SetDialogs3.h"
42 #include "SettingsColors.h"
43 #include "SettingsColors2.h"
44 #include "SettingsColors3.h"
45 #include "SetSavedDataPage.h"
47 #include "SetBugTraq.h"
48 #include "SettingsTBlame.h"
49 #include "SettingGitConfig.h"
50 #include "SettingGitCredential.h"
51 #include "SettingsBugtraqConfig.h"
52 #include "SetExtMenu.h"
53 #include "SetWin11ContextMenu.h"
54 #include "SettingsAdvanced.h"
55 #include "SettingSMTP.h"
56 #include "SettingsTUDiff.h"
59 IMPLEMENT_DYNAMIC(CSettings
, CTreePropSheet
)
60 CSettings::CSettings(UINT nIDCaption
, CTGitPath
* /*cmdPath*/, CWnd
* pParentWnd
, UINT iSelectPage
)
61 : CTreePropSheet(nIDCaption
, pParentWnd
)
64 SetTheme(CTheme::Instance().IsDarkTheme());
65 SetActivePage(iSelectPage
);
68 CSettings::~CSettings()
73 void CSettings::SetTheme(bool bDark
)
75 __super::SetTheme(bDark
);
76 for (int i
= 0; i
< GetPageCount(); ++i
)
78 auto pPage
= GetPage(i
);
79 if (IsWindow(pPage
->GetSafeHwnd()))
80 CTheme::Instance().SetThemeForDialog(pPage
->GetSafeHwnd(), bDark
);
82 ::RedrawWindow(GetSafeHwnd(), nullptr, nullptr, RDW_FRAME
| RDW_INVALIDATE
| RDW_ERASE
| RDW_INTERNALPAINT
| RDW_ALLCHILDREN
| RDW_UPDATENOW
);
85 ISettingsPropPage
* CSettings::AddPropPage(ISettingsPropPage
* page
, CString pageName
)
87 ASSERT(std::none_of(m_pPages
.cbegin(), m_pPages
.cend(), [&pageName
](auto& settingsPage
) { return settingsPage
.pageName
== pageName
; }) && "pageName must be unique");
89 SetPageIcon(page
, page
->GetIconID());
90 m_pPages
.emplace_back(page
, pageName
);
94 void CSettings::AddPropPage(ISettingsPropPage
* page
, CString pageName
, CPropertyPage
* parentPage
)
96 AddPropPage(page
, pageName
);
97 SetParentPage(parentPage
, page
);
100 void CSettings::AddPropPages()
102 auto pMainPage
= AddPropPage(new CSetMainPage(), L
"main");
103 AddPropPage(new CSetLookAndFeelPage(), L
"look", pMainPage
);
104 AddPropPage(new CSetExtMenu(), L
"extmenu", pMainPage
);
105 if (SysInfo::Instance().IsWin11OrLater())
106 AddPropPage(new CSetWin11ContextMenu(), L
"win11menu", pMainPage
);
107 AddPropPage(new CSetDialogs(), L
"dialog", pMainPage
);
108 AddPropPage(new CSetDialogs2(), L
"dialog2", pMainPage
);
109 AddPropPage(new CSetDialogs3(), L
"dialog3", pMainPage
);
110 AddPropPage(new CSettingsColors(), L
"color1", pMainPage
);
111 AddPropPage(new CSettingsColors2(), L
"color2", pMainPage
);
112 AddPropPage(new CSettingsColors3(), L
"color3", pMainPage
);
113 AddPropPage(new CSettingsProgsAlternativeEditor(), L
"alternativeeditor", pMainPage
);
115 m_pGitConfig
= AddPropPage(new CSettingGitConfig(), L
"gitconfig");
116 CString repo
= g_Git
.m_CurrentDir
;
117 bool hasLocalRepo
= GitAdminDir::IsWorkingTreeOrBareRepo(repo
);
120 m_pGitRemote
= new CSettingGitRemote();
121 AddPropPage(m_pGitRemote
, L
"gitremote", m_pGitConfig
);
123 AddPropPage(new CSettingGitCredential(), L
"gitcredential", m_pGitConfig
);
125 auto pHooksPage
= AddPropPage(new CSetHooks(), L
"hooks");
126 AddPropPage(new CSetBugTraq(), L
"bugtraq", pHooksPage
);
128 AddPropPage(new CSettingsBugtraqConfig(), L
"bugtraqconfig", pHooksPage
);
130 auto pOverlayPage
= AddPropPage(new CSetOverlayPage(), L
"overlay");
131 AddPropPage(new CSetOverlayIcons(), L
"overlays", pOverlayPage
);
132 AddPropPage(new CSetOverlayHandlers(), L
"overlayshandlers", pOverlayPage
);
134 auto pProxyPage
= AddPropPage(new CSetProxyPage(), L
"proxy");
135 AddPropPage(new CSettingSMTP(), L
"smtp", pProxyPage
);
137 auto pProgsDiffPage
= AddPropPage(new CSettingsProgsDiff(), L
"diff");
138 AddPropPage(new CSettingsProgsMerge(), L
"merge", pProgsDiffPage
);
140 AddPropPage(new CSetSavedDataPage(), L
"save");
141 AddPropPage(new CSettingsTBlame(), L
"blame");
142 AddPropPage(new CSettingsUDiff(), L
"udiff");
143 AddPropPage(new CSettingsAdvanced(), L
"advanced");
146 void CSettings::RemovePropPages()
151 void CSettings::HandleRestart()
153 int restart
= ISettingsPropPage::Restart_None
;
154 for (const auto& page
: m_pPages
)
156 restart
|= page
.page
->GetRestart();
159 if (restart
& ISettingsPropPage::Restart_System
)
162 ::SendMessageTimeout(HWND_BROADCAST
, WM_SETTINGCHANGE
, 0, 0, SMTO_ABORTIFHUNG
, 20, &res
);
163 CMessageBox::Show(GetSafeHwnd(), IDS_SETTINGS_RESTARTSYSTEM
, IDS_APPNAME
, MB_ICONINFORMATION
);
165 if (restart
& ISettingsPropPage::Restart_Cache
)
168 ::SendMessageTimeout(HWND_BROADCAST
, WM_SETTINGCHANGE
, 0, 0, SMTO_ABORTIFHUNG
, 20, &res
);
169 // tell the cache to refresh everything
170 SendCacheCommand(TGITCACHECOMMAND_REFRESHALL
);
171 SendCacheCommand(TGITCACHECOMMAND_END
);
175 BEGIN_MESSAGE_MAP(CSettings
, CTreePropSheet
)
178 BOOL
CSettings::OnInitDialog()
180 BOOL bResult
= __super::OnInitDialog();
181 CAppUtils::MarkWindowAsUnpinnable(m_hWnd
);
183 if (GitAdminDir::IsWorkingTreeOrBareRepo(g_Git
.m_CurrentDir
))
184 CAppUtils::SetWindowTitle(*this, g_Git
.m_CurrentDir
);
188 GetWindowText(title
);
189 SetWindowText(title
+ " - " + CString(MAKEINTRESOURCE(IDS_APPNAME
)));
192 DarkModeHelper::Instance().AllowDarkModeForApp(CTheme::Instance().IsDarkTheme());
193 SetTheme(CTheme::Instance().IsDarkTheme());
194 CTheme::Instance().SetThemeForDialog(GetSafeHwnd(), CTheme::Instance().IsDarkTheme());
196 CenterWindow(CWnd::FromHandle(GetExplorerHWND()));
198 bool foundDefaultPage
= false;
199 if (!m_DefaultPage
.IsEmpty())
201 for (const auto& page
: m_pPages
)
203 if (this->m_DefaultPage
== page
.pageName
)
205 if (page
.page
== m_pGitRemote
)
206 m_pGitRemote
->m_bNoFetch
= true;
207 SetActivePage(page
.page
);
208 foundDefaultPage
= true;
213 if (!foundDefaultPage
&& GitAdminDir::IsWorkingTreeOrBareRepo(g_Git
.m_CurrentDir
))
214 SetActivePage(m_pGitConfig
);