Skip to content

Commit

Permalink
feat(instwin): init project
Browse files Browse the repository at this point in the history
  • Loading branch information
ilharp committed Aug 9, 2023
1 parent 776f1af commit ee0b911
Show file tree
Hide file tree
Showing 15 changed files with 400 additions and 0 deletions.
1 change: 1 addition & 0 deletions .idea/.gitignore

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

11 changes: 11 additions & 0 deletions .idea/cmake.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

24 changes: 24 additions & 0 deletions .idea/runConfigurations/instwin.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions packages/instwin/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
src/instwin.rc
src/instwin.exe.manifest
131 changes: 131 additions & 0 deletions packages/instwin/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
cmake_minimum_required(VERSION 3.5)

############################################################
# Project
############################################################

project(instwin
VERSION 0.1.0
DESCRIPTION "Koishi Desktop Installer."
HOMEPAGE_URL "https://koishi.chat"
LANGUAGES C CXX
)

set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)

set(CMAKE_C_STANDARD 23)
set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

set(CMAKE_MESSAGE_LOG_LEVEL VERBOSE)

# Use static link
set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>")

############################################################
# Dependencies
############################################################

# Qt Dependencies
find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets LinguistTools)
find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets LinguistTools)

add_subdirectory(../shellcomm lib/shellcomm)

############################################################
# App
############################################################

set(TS_FILES
src/instwin_en_US.ts)

set(PROJECT_SOURCES
src/main.cpp
src/util/errors.cpp
include/instwin/windows/mainwindow.hpp
src/windows/mainwindow.cpp
src/windows/mainwindow.ui
${TS_FILES}
src/instwin.exe.manifest
src/instwin.rc
)

qt_add_executable(instwin
MANUAL_FINALIZATION
${PROJECT_SOURCES}
)

qt_create_translation(
QM_FILES
${CMAKE_SOURCE_DIR}
${TS_FILES}
)

target_link_libraries(instwin
PRIVATE
shellcomm
Qt${QT_VERSION_MAJOR}::Widgets
dwmapi
)

target_include_directories(instwin
PRIVATE
${PROJECT_SOURCE_DIR}/include
)

set_target_properties(instwin
PROPERTIES
${BUNDLE_ID_OPTION}
WIN32_EXECUTABLE TRUE
)

############################################################
# Compile Flags
############################################################

target_compile_definitions(instwin
PRIVATE
UNICODE
_UNICODE
WIN32
_WIN32
WINDOWS
_WINDOWS
)

if (MSVC)
target_compile_options(instwin
PRIVATE
/utf-8
)
else()
target_compile_options(instwin
PRIVATE
-fexec-charset=UTF-8
-finput-charset=UTF-8
)
endif()

############################################################
# Support Visual Studio "Edit and Continue"
############################################################

if (CMAKE_GENERATOR MATCHES "Visual Studio")
target_compile_options(instwin
PRIVATE
/ZI
)

target_link_options(instwin
PRIVATE
/INCREMENTAL
)
endif()

############################################################
# Finalize
############################################################

qt_finalize_executable(instwin)
26 changes: 26 additions & 0 deletions packages/instwin/CMakeSettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"configurations": [
{
"name": "x64-Debug",
"generator": "Ninja",
"configurationType": "Debug",
"inheritEnvironments": ["msvc_x64_x64"],
"buildRoot": "${projectDir}\\out\\build\\${name}",
"installRoot": "${projectDir}\\out\\install\\${name}",
"cmakeCommandArgs": "",
"buildCommandArgs": "",
"ctestCommandArgs": ""
},
{
"name": "x64-MinSizeRel",
"generator": "Ninja",
"configurationType": "MinSizeRel",
"inheritEnvironments": ["msvc_x64_x64"],
"buildRoot": "${projectDir}\\out\\build\\${name}",
"installRoot": "${projectDir}\\out\\install\\${name}",
"cmakeCommandArgs": "",
"buildCommandArgs": "",
"ctestCommandArgs": ""
}
]
}
10 changes: 10 additions & 0 deletions packages/instwin/include/instwin/main.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#ifndef _INSTWIN_MAIN_
#define _INSTWIN_MAIN_

#include "instwin/stdafx.hpp"

#include "instwin/windows/mainwindow.hpp"

int main(int argc, char *argv[]);

#endif /* _INSTWIN_MAIN_ */
10 changes: 10 additions & 0 deletions packages/instwin/include/instwin/stdafx.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#ifndef _INSTWIN_STDAFX_
#define _INSTWIN_STDAFX_

#include <format>

#include <windows.h>

#include <dwmapi.h>

#endif /* _INSTWIN_STDAFX_ */
12 changes: 12 additions & 0 deletions packages/instwin/include/instwin/util/errors.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#ifndef _INSTWIN_UTIL_ERRORS_
#define _INSTWIN_UTIL_ERRORS_

#include "instwin/stdafx.hpp"

namespace InstWin {

void LogAndFailWithLastError(HWND hWnd, const wchar_t *message);

} // namespace InstWin

#endif /* _INSTWIN_UTIL_ERRORS_ */
29 changes: 29 additions & 0 deletions packages/instwin/include/instwin/windows/mainwindow.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
#ifndef _INSTWIN_WINDOWS_MAINWINDOW_
#define _INSTWIN_WINDOWS_MAINWINDOW_

#include "instwin/stdafx.hpp"

#include <QMainWindow>

#include "instwin/util/errors.hpp"

QT_BEGIN_NAMESPACE
namespace Ui {
class MainWindow;
}
QT_END_NAMESPACE

class MainWindow : public QMainWindow {
Q_OBJECT

public:
MainWindow(QWidget *parent = nullptr);
~MainWindow();

private:
Ui::MainWindow *ui;

void InitializeWindowStyle();
};

#endif /* _INSTWIN_WINDOWS_MAINWINDOW_ */
3 changes: 3 additions & 0 deletions packages/instwin/src/instwin_en_US.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS>
<TS version="2.1" language="en_US"></TS>
22 changes: 22 additions & 0 deletions packages/instwin/src/main.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#include "instwin/main.hpp"

#include <QApplication>
#include <QLocale>
#include <QTranslator>

int main(int argc, char *argv[]) {
const QApplication app(argc, argv);

QTranslator translator;
const QStringList uiLanguages = QLocale::system().uiLanguages();
for (const QString &locale : uiLanguages) {
const QString baseName = "QtPlaygroundA_" + QLocale(locale).name();
if (translator.load(":/i18n/" + baseName)) {
app.installTranslator(&translator);
break;
}
}
MainWindow mainWindow;
mainWindow.show();
return app.exec();
}
23 changes: 23 additions & 0 deletions packages/instwin/src/util/errors.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
#include "instwin/util/errors.hpp"

namespace InstWin {

void LogAndFailWithLastError(HWND hWnd, const wchar_t *message) {
wchar_t *errMessage;
unsigned long err = GetLastError();
FormatMessageW(
FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS,
nullptr,
err,
0,
reinterpret_cast<wchar_t *>(&errMessage),
0,
nullptr);
auto errString =
std::format(L"{}\nWinError {}: {}", message, err, errMessage);
MessageBoxW(hWnd, errString.c_str(), L"Error", MB_ICONERROR);
ExitProcess(1);
}

} // namespace InstWin
76 changes: 76 additions & 0 deletions packages/instwin/src/windows/mainwindow.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
#include "instwin/windows/mainwindow.hpp"
#include "ui_mainwindow.h"

MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent), ui(new Ui::MainWindow) {
// Setup UI
ui->setupUi(this);

InitializeWindowStyle();
}

MainWindow::~MainWindow() {
delete ui;
}

void MainWindow::InitializeWindowStyle() {
HWND hWnd = reinterpret_cast<HWND>(winId());

// Fix window
setWindowFlag(Qt::MSWindowsFixedSizeDialogHint);

// Make widget transparent
setAttribute(Qt::WA_TranslucentBackground);

// Enable DWM transparent
OSVERSIONINFOEXW osvi{0};
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEXW);
if (!GetVersionExW(reinterpret_cast<LPOSVERSIONINFOW>(&osvi)))
InstWin::LogAndFailWithLastError(hWnd, L"Failed to get OS version info.");

unsigned char supports = 0;

if (osvi.dwBuildNumber >= 17763)
supports++; // Supports Windows 10 immersive dark mode (19), supports = 1
if (osvi.dwBuildNumber >= 18985)
supports++; // Supports Windows 10 immersive dark mode (20), supports = 2
if (osvi.dwBuildNumber >= 22000)
supports++; // Supports Windows 11 Mica, supports = 3
if (osvi.dwBuildNumber >= 22523)
supports++; // Supports Windows 11 Mica Tabbed, supports = 4

if (supports) {
MARGINS dwmExtendFrameIntoClientAreaMargins = {-1};
DwmExtendFrameIntoClientArea(hWnd, &dwmExtendFrameIntoClientAreaMargins);
int dwmUseDarkMode = 1;
DwmSetWindowAttribute(
hWnd,
supports >= 2 ? 20
: // DWMWINDOWATTRIBUTE::DWMWA_USE_IMMERSIVE_DARK_MODE
// = 20 (starting from 18985)
19, // DWMWINDOWATTRIBUTE::DWMWA_USE_IMMERSIVE_DARK_MODE
// = 19 (before 18985)
&dwmUseDarkMode,
sizeof(dwmUseDarkMode));
unsigned int dwmCornerPreference =
2; // DWM_WINDOW_CORNER_PREFERENCE::DWMWCP_ROUND
DwmSetWindowAttribute(
hWnd,
33, // DWMWINDOWATTRIBUTE::DWMWA_WINDOW_CORNER_PREFERENCE
&dwmCornerPreference,
sizeof(dwmCornerPreference));
int dwmMica = 1;
DwmSetWindowAttribute(
hWnd,
1029, // DWMWINDOWATTRIBUTE::DWMWA_MICA
&dwmMica,
sizeof(dwmMica));
unsigned int dwmSystemBackdropType =
supports >= 4 ? 4 : 2; // DWM_SYSTEMBACKDROP_TYPE::DWMSBT_MAINWINDOW
DwmSetWindowAttribute(
hWnd,
38, // DWMWINDOWATTRIBUTE::DWMWA_SYSTEMBACKDROP_TYPE
&dwmSystemBackdropType,
sizeof(dwmSystemBackdropType));
}
}
Loading

0 comments on commit ee0b911

Please sign in to comment.