Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Add copy buttons to all
 blocks\n(function() {\n function addCopyButtons() {\n document.querySelectorAll('pre code').forEach(function(codeBlock) {\n if (codeBlock.parentElement.hasAttribute('data-copy-added')) return;\n codeBlock.parentElement.setAttribute('data-copy-added', 'true');\n \n var btn = document.createElement('button');\n btn.textContent = 'Copy';\n btn.style.cssText = 'position:absolute;top:4px;right:4px;padding:2px 8px;font-size:11px;background:#4ecdc4;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;opacity:0.7;transition:opacity 0.2s;';\n btn.onmouseover = function() { this.style.opacity = '1'; };\n btn.onmouseout = function() { this.style.opacity = '0.7'; };\n btn.onclick = function() {\n navigator.clipboard.writeText(codeBlock.textContent).then(function() {\n btn.textContent = 'Copied!';\n setTimeout(function() { btn.textContent = 'Copy'; }, 1500);\n });\n };\n codeBlock.parentElement.style.position = 'relative';\n codeBlock.parentElement.appendChild(btn);\n });\n }\n \n addCopyButtons();\n \n // Re-run on dynamic content\n var observer = new MutationObserver(addCopyButtons);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Add Copy Buttons to Code Blocks");
}
} catch(__e) { console.warn('[Userscript:Add Copy Buttons to Code Blocks]', __e); }
})();
(function(){
try {
var __m = "github.com";
var __re = new RegExp('^' + "github\\.com" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Force GitHub README to respect dark mode\n(function() {\n var style = document.createElement('style');\n style.textContent = '\n .markdown-body {\n color-scheme: dark light;\n }\n .markdown-body pre { background: #161b22 !important; }\n .markdown-body code { background: rgba(110, 118, 129, 0.4) !important; }\n .markdown-body table th, .markdown-body table td { border-color: #30363d !important; }\n .markdown-body img { background: #0d1117; }\n .markdown-body blockquote { border-left-color: #8b949e; }\n .markdown-body hr { border-color: #30363d; }\n ';\n document.head.appendChild(style);\n})();", "GitHub Dark Mode README Fix"); } } catch(__e) { console.warn('[Userscript:GitHub Dark Mode README Fix]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Highlight search terms from Google/DuckDuckGo/Bing referrer\n(function() {\n var ref = document.referrer;\n var terms = [];\n \n if (ref.includes('google.com') || ref.includes('duckduckgo.com') || ref.includes('bing.com')) {\n var url = new URL(ref);\n var q = url.searchParams.get('q') || url.searchParams.get('p');\n if (q) {\n terms = q.split(/\\s+/).filter(function(t) { return t.length > 2; });\n }\n }\n \n if (terms.length === 0) return;\n \n var style = document.createElement('style');\n style.textContent = '.userscript-highlight { background: #fbbf24; color: #1a1a2e; padding: 1px 3px; border-radius: 2px; }';\n document.head.appendChild(style);\n \n function highlight(node) {\n if (node.nodeType === 3) { // text node\n var text = node.textContent;\n var found = false;\n terms.forEach(function(term) {\n var regex = new RegExp('(' + term.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\') + ')', 'gi');\n if (regex.test(text)) {\n found = true;\n var frag = document.createDocumentFragment();\n var parts = text.split(regex);\n parts.forEach(function(part, i) {\n if (i % 2 === 0) {\n frag.appendChild(document.createTextNode(part));\n } else {\n var span = document.createElement('span');\n span.className = 'userscript-highlight';\n span.textContent = part;\n frag.appendChild(span);\n }\n });\n node.parentNode.replaceChild(frag, node);\n }\n });\n } else if (node.nodeType === 1 && node.childNodes) { // element\n var skipTags = ['SCRIPT', 'STYLE', 'NOSCRIPT', 'TEXTAREA', 'INPUT', 'SELECT'];\n if (!skipTags.includes(node.tagName)) {\n Array.from(node.childNodes).forEach(highlight);\n }\n }\n }\n \n highlight(document.body);\n \n // Re-highlight on dynamic content\n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1 || node.nodeType === 3) highlight(node);\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Highlight Search Terms"); } } catch(__e) { console.warn('[Userscript:Highlight Search Terms]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Strip utm_, fbclid, gclid, etc. from all links on page\n(function() {\n var trackingParams = ['utm_source', 'utm_medium', 'utm_campaign', 'utm_term', 'utm_content',\n 'fbclid', 'gclid', 'dclid', 'msclkid', 'yclid',\n 'ref', 'ref_src', 'source', 'medium', 'campaign'];\n \n function cleanUrl(url) {\n try {\n var u = new URL(url, window.location.origin);\n var changed = false;\n trackingParams.forEach(function(p) {\n if (u.searchParams.has(p)) {\n u.searchParams.delete(p);\n changed = true;\n }\n });\n return changed ? u.toString() : url;\n } catch (e) {\n return url;\n }\n }\n \n function cleanLinks() {\n document.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n \n cleanLinks();\n \n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1) {\n if (node.tagName === 'A') cleanLinks();\n node.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Remove Tracking Parameters from Links"); } } catch(__e) { console.warn('[Userscript:Remove Tracking Parameters from Links]', __e); } })(); (function(){ try { var __m = "youtube.com"; var __re = new RegExp('^' + "youtube\\.com" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Auto-enable theater mode on YouTube\n(function() {\n function tryTheater() {\n var btn = document.querySelector('button[aria-label=\"Theater mode\"], ytd-player #player button[title=\"Theater mode\"]');\n if (btn && !btn.classList.contains('activated')) {\n btn.click();\n }\n }\n \n // Try immediately\n tryTheater();\n \n // Try after navigation (SPA)\n var lastUrl = location.href;\n setInterval(function() {\n if (location.href !== lastUrl) {\n lastUrl = location.href;\n setTimeout(tryTheater, 500);\n }\n }, 1000);\n \n // Also try on player load\n var observer = new MutationObserver(tryTheater);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "YouTube Theater Mode Default"); } } catch(__e) { console.warn('[Userscript:YouTube Theater Mode Default]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Remove or un-stick sticky/fixed headers that block content\n(function() {\n function unstick() {\n document.querySelectorAll('header, nav, [role=\"banner\"], .header, .navbar, .sticky, .fixed-top, [style*=\"position: fixed\"], [style*=\"position:sticky\"]').forEach(function(el) {\n if (el.style.position === 'fixed' || el.style.position === 'sticky' || \n getComputedStyle(el).position === 'fixed' || getComputedStyle(el).position === 'sticky') {\n el.style.position = 'static';\n el.style.top = 'auto';\n el.style.zIndex = 'auto';\n }\n });\n }\n \n unstick();\n \n var observer = new MutationObserver(unstick);\n observer.observe(document.body, { childList: true, subtree: true, attributes: true, attributeFilter: ['style', 'class'] });\n})();", "Kill Sticky Headers"); } } catch(__e) { console.warn('[Userscript:Kill Sticky Headers]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Universal Dark Mode - works on any site\n(function() {\n var enabled = true;\n \n function applyDarkMode() {\n if (!enabled) return;\n \n // Create style element if it doesn't exist\n var style = document.getElementById('universal-dark-mode-style');\n if (!style) {\n style = document.createElement('style');\n style.id = 'universal-dark-mode-style';\n document.head.appendChild(style);\n }\n \n // Dark mode CSS - inverts colors but preserves images/video\n style.textContent = '\n /* Invert everything except media */\n html {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #1a1a2e !important;\n }\n \n /* Restore images, videos, iframes, canvas */\n img, video, iframe, canvas, svg, picture, [style*=\"background-image\"] {\n filter: invert(1) hue-rotate(180deg) !important;\n }\n \n /* Preserve specific elements that should not be inverted */\n .no-dark-mode, .no-dark-mode *,\n [data-theme=\"light\"], [data-theme=\"light\"],\n .ace_editor, .ace_editor *,\n .CodeMirror, .CodeMirror *,\n .monaco-editor, .monaco-editor *,\n .markdown-body pre, .markdown-body pre *,\n .highlight, .highlight *,\n pre code, pre code * {\n filter: none !important;\n }\n \n /* Fix common UI elements */\n .modal, .popup, .dropdown-menu, .tooltip, .popover {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #2d2d44 !important;\n border-color: #444 !important;\n }\n \n /* Scrollbars */\n ::-webkit-scrollbar { background: #1a1a2e !important; }\n ::-webkit-scrollbar-thumb { background: #444 !important; }\n ::-webkit-scrollbar-thumb:hover { background: #555 !important; }\n \n /* Selection */\n ::selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ::-moz-selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ';\n }\n \n function removeDarkMode() {\n var style = document.getElementById('universal-dark-mode-style');\n if (style) style.remove();\n }\n \n // Toggle with Alt+Shift+D\n document.addEventListener('keydown', function(e) {\n if (e.altKey && e.shiftKey && e.key === 'D') {\n e.preventDefault();\n enabled = !enabled;\n if (enabled) {\n applyDarkMode();\n console.log('[Universal Dark Mode] Enabled');\n } else {\n removeDarkMode();\n console.log('[Universal Dark Mode] Disabled');\n }\n }\n });\n \n // Apply on load\n applyDarkMode();\n \n // Re-apply on dynamic content\n var observer = new MutationObserver(function(mutations) {\n if (enabled && !document.getElementById('universal-dark-mode-style')) {\n applyDarkMode();\n }\n });\n observer.observe(document.head, { childList: true });\n \n console.log('[Universal Dark Mode] Loaded - Press Alt+Shift+D to toggle');\n})();", "Universal Dark Mode"); } } catch(__e) { console.warn('[Userscript:Universal Dark Mode]', __e); } })(); })();
Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/windows/include/display_device/windows/settings_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -36,7 +36,7 @@ namespace display_device::win_utils {
* const auto extended_topology { stripTopologyOfUnavailableDevices(*iface) };
* @examples_end
*/
ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd);
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd);

/**
* @brief Get one primary device from the provided topology.
Expand All@@ -49,7 +49,7 @@ namespace display_device::win_utils {
* const auto primary_device_id { getPrimaryDevice(*iface, topology) };
* @examples_end
*/
std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology);

/**
* @brief Compute the new intial state from arbitrary data.
Expand Down
5 changes: 4 additions & 1 deletion src/windows/include/display_device/windows/win_api_layer.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "win_api_layer_interface.h"

Expand DownExpand Up@@ -44,6 +47,6 @@ namespace display_device {
[[nodiscard]] bool setHdrState(const DISPLAYCONFIG_PATH_INFO &path, HdrState state) override;

/** For details @see WinApiLayerInterface::getDisplayScale */
[[nodiscard]] std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
[[nodiscard]] std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const override;
};
} // namespace display_device
Original file line numberDiff line numberDiff line change
Expand Up@@ -4,6 +4,9 @@
*/
#pragma once

// system includes
#include <string_view>

// local includes
#include "types.h"

Expand DownExpand Up@@ -195,6 +198,6 @@ namespace display_device {
* const auto scale = iface->getDisplayScale(iface->getDisplayName(path), source_mode);
* @examples_end
*/
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
[[nodiscard]] virtual std::optional<Rational> getDisplayScale(std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const = 0;
};
} // namespace display_device
8 changes: 2 additions & 6 deletions src/windows/include/display_device/windows/win_api_utils.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -6,6 +6,7 @@

// system includes
#include <set>
#include <string_view>

// local includes
#include "win_api_layer_interface.h"
Expand DownExpand Up@@ -202,12 +203,7 @@ namespace display_device::win_utils {
* const DISPLAYCONFIG_PATH_INFO* active_path = get_active_path(*iface, "MY_DEVICE_ID", paths);
* @examples_end
*/
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @see getActivePath (const version) for the description.
*/
[[nodiscard]] DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths);
[[nodiscard]] const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths);

/**
* @brief Collect arbitrary source data from provided paths.
Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_apply.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -20,6 +20,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
1 change: 1 addition & 0 deletions src/windows/settings_manager_revert.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -19,6 +19,7 @@ namespace display_device {
* @brief Function that does nothing.
*/
void noopFn() {
// Intentionally empty guard callback.
}
} // namespace

Expand Down
4 changes: 2 additions & 2 deletions src/windows/settings_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -137,7 +137,7 @@ namespace display_device::win_utils {
return flattened_topology;
}

ActiveTopology createFullExtendedTopology(WinDisplayDeviceInterface &win_dd) {
ActiveTopology createFullExtendedTopology(const WinDisplayDeviceInterface &win_dd) {
const auto devices {win_dd.enumAvailableDevices()};
if (devices.empty()) {
DD_LOG(error) << "Failed to enumerate available devices for full extended topology!";
Expand All@@ -152,7 +152,7 @@ namespace display_device::win_utils {
return topology;
}

std::string getPrimaryDevice(WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
std::string getPrimaryDevice(const WinDisplayDeviceInterface &win_dd, const ActiveTopology &topology) {
const auto flat_topology {flattenTopology(topology)};
for (const auto &device_id : flat_topology) {
if (win_dd.isPrimary(device_id)) {
Expand Down
9 changes: 5 additions & 4 deletions src/windows/win_api_layer.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,6 +14,7 @@
#include <cmath>
#include <cstdint>
#include <iomanip>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -310,7 +311,7 @@ namespace display_device {
* @param value The UTF-16 wide string.
* @return The converted UTF-8 string.
*/
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring &value) {
std::string toUtf8(const WinApiLayerInterface &w_api, const std::wstring_view value) {
// No conversion needed if the string is empty
if (value.empty()) {
return {};
Expand DownExpand Up@@ -637,18 +638,18 @@ namespace display_device {
return true;
}

std::optional<Rational> WinApiLayer::getDisplayScale(const std::string &display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
std::optional<Rational> WinApiLayer::getDisplayScale(const std::string_view display_name, const DISPLAYCONFIG_SOURCE_MODE &source_mode) const {
// Note: implementation based on https://stackoverflow.com/a/74046173
struct EnumData {
std::string m_display_name;
std::string_view m_display_name;
std::optional<int> m_width;
};

EnumData enum_data {display_name, std::nullopt};
EnumDisplayMonitors(
nullptr,
nullptr,
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) -> BOOL {
[](HMONITOR monitor, HDC, LPRECT, LPARAM user_data) {
auto *data = reinterpret_cast<EnumData *>(user_data);
if (data == nullptr) {
// Sanity check
Expand Down
6 changes: 1 addition & 5 deletions src/windows/win_api_utils.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -204,7 +204,7 @@ namespace display_device::win_utils {
return ValidatedDeviceInfo {device_path, device_id};
}

const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
const DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string_view device_id, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
for (const auto &path : paths) {
const auto device_info {getDeviceInfoForValidPath(w_api, path, ValidatedPathType::Active)};
if (!device_info) {
Expand All@@ -219,10 +219,6 @@ namespace display_device::win_utils {
return nullptr;
}

DISPLAYCONFIG_PATH_INFO *getActivePath(const WinApiLayerInterface &w_api, const std::string &device_id, std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
return const_cast<DISPLAYCONFIG_PATH_INFO *>(getActivePath(w_api, device_id, const_cast<const std::vector<DISPLAYCONFIG_PATH_INFO> &>(paths)));
}

PathSourceIndexDataMap collectSourceDataForMatchingPaths(const WinApiLayerInterface &w_api, const std::vector<DISPLAYCONFIG_PATH_INFO> &paths) {
PathSourceIndexDataMap path_data;

Expand Down
15 changes: 8 additions & 7 deletions src/windows/win_display_device_modes.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -41,7 +41,8 @@ namespace display_device {
return false;
}

const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(*path, display_data->m_modes), display_data->m_modes)};
auto &mutable_path {display_data->m_paths[static_cast<std::size_t>(path - display_data->m_paths.data())]};
const auto source_mode {win_utils::getSourceMode(win_utils::getSourceIndex(mutable_path, display_data->m_modes), display_data->m_modes)};
if (!source_mode) {
DD_LOG(error) << "Active device does not have a source mode: " << device_id << "!";
return false;
Expand All@@ -52,11 +53,11 @@ namespace display_device {

bool refresh_rate_changed;
if (strategy == Strategy::Relaxed) {
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {path->targetInfo.refreshRate.Numerator, path->targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
refresh_rate_changed = !win_utils::fuzzyCompareRefreshRates(Rational {mutable_path.targetInfo.refreshRate.Numerator, mutable_path.targetInfo.refreshRate.Denominator}, mode.m_refresh_rate);
} else {
// Since we are in strict mode, do not fuzzy compare it
refresh_rate_changed = path->targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
path->targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
refresh_rate_changed = mutable_path.targetInfo.refreshRate.Numerator != mode.m_refresh_rate.m_numerator ||
mutable_path.targetInfo.refreshRate.Denominator != mode.m_refresh_rate.m_denominator;
}

if (resolution_changed) {
Expand All@@ -66,14 +67,14 @@ namespace display_device {
}

if (refresh_rate_changed) {
path->targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
mutable_path.targetInfo.refreshRate = {mode.m_refresh_rate.m_numerator, mode.m_refresh_rate.m_denominator};
new_changes = true;
}

if (new_changes) {
// Clear the target index so that Windows has to select/modify the target to best match the requirements.
win_utils::setTargetIndex(*path, std::nullopt);
win_utils::setDesktopIndex(*path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
win_utils::setTargetIndex(mutable_path, std::nullopt);
win_utils::setDesktopIndex(mutable_path, std::nullopt); // Part of struct containing target index and so it needs to be cleared
}

changes_applied = changes_applied || new_changes;
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_comparison.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, TypeComparison, __VA_ARGS__)
} // namespace

TEST_S(Point) {
EXPECT_EQ(display_device::Point({1, 1}), display_device::Point({1, 1}));
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_edid_parsing.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,10 +2,8 @@
#include "display_device/types.h"
#include "fixtures/fixtures.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_S(...) DD_MAKE_TEST(TEST, EdidParsing, __VA_ARGS__)
} // namespace

TEST_S(NoData) {
EXPECT_EQ(display_device::EdidData::parse({}), std::nullopt);
Expand Down
4 changes: 1 addition & 3 deletions tests/unit/general/test_json_converter.cpp
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
// local includes
#include "fixtures/json_converter_test.h"

namespace {
// Specialized TEST macro(s) for this test file
// Specialized TEST macro(s) for this test file
#define TEST_F_S(...) DD_MAKE_TEST(TEST_F, JsonConverterTest, __VA_ARGS__)
} // namespace

TEST_F_S(EdidData) {
display_device::EdidData item {
Expand Down
5 changes: 3 additions & 2 deletions tests/unit/general/test_logging.cpp
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
// system includes
#include <exception>
#include <format>
#include <string_view>

// local includes
#include "display_device/logging.h"
Expand DownExpand Up@@ -106,7 +107,7 @@ TEST_S(DefaultLogger) {
using level = display_device::Logger::LogLevel;
auto &logger {display_device::Logger::get()};

const auto write_and_get_cout {[this, &logger](level level, std::string value) -> std::string {
const auto write_and_get_cout {[this, &logger](level level, std::string value) {
m_cout_buffer.str(std::string {}); // reset the buffer
logger.write(level, std::move(value));
return m_cout_buffer.str();
Expand All@@ -130,7 +131,7 @@ TEST_S(CustomCallback) {

std::string output;
logger.setLogLevel(level::verbose);
logger.setCustomCallback([&output](const level level, const std::string &value) {
logger.setCustomCallback([&output](const level level, const std::string_view value) {
output = std::format("{} {}", static_cast<level_t>(level), value);
});

Expand Down
48 changes: 29 additions & 19 deletions tests/unit/general/test_retry_scheduler.cpp
Original file line numberDiff line numberDiff line change
Expand Up@@ -2,6 +2,8 @@
#include <exception>
#include <gmock/gmock.h>
#include <stdexcept>
#include <string_view>
#include <type_traits>

// local includes
#include "display_device/retry_scheduler.h"
Expand DownExpand Up@@ -106,7 +108,7 @@ TEST_F_S(Schedule, SchedulingDurations) {
std::this_thread::sleep_for(1ms);
}

return m_impl.execute([](TestIface &iface) {
return m_impl.execute([](const TestIface &iface) {
int sum {0};
for (const auto timing : iface.m_durations) {
sum += timing;
Expand DownExpand Up@@ -299,8 +301,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringImmediateCall) {
}

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

EXPECT_TRUE(m_impl.isScheduled());
Expand DownExpand Up@@ -329,8 +331,8 @@ TEST_F_S(Schedule, ExceptionThrown, DuringScheduledCall) {
auto &logger {display_device::Logger::get()};

std::string output;
logger.setCustomCallback([&output](auto, const std::string &value) {
output = value;
logger.setCustomCallback([&output](auto, const std::string_view value) {
output = std::string {value};
});

bool first_call {true};
Expand DownExpand Up@@ -530,7 +532,9 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
const auto const_callback_auto = [](const auto &iface) {
iface.constMethod();
};
const auto non_const_callback_auto = [](auto &iface) {
const auto non_const_callback_auto = []<class Iface>(Iface &iface)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
};

Expand All@@ -541,12 +545,12 @@ TEST_F_S(Execute, ConstVsNonConst, WithoutStopToken) {
non_const_impl.execute(const_callback_auto);
non_const_impl.execute(non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_callback);
// const_impl.execute(non_const_callback);
static_assert(!std::is_invocable_v<decltype(non_const_callback), const TestIface &>);
const_impl.execute(const_callback_auto);
// const_impl.execute(non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(non_const_callback_auto), const TestIface &>);
}

TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
Expand All@@ -570,15 +574,21 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
iface.constMethod();
(void) token.stopRequested();
};
const auto const_non_const_callback_auto = [](const auto &iface, auto &token) {
const auto const_non_const_callback_auto = []<class Iface, class Token>(const Iface &iface, Token &token)
requires(!std::is_const_v<Token>)
{
iface.constMethod();
token.requestStop();
};
const auto non_const_const_callback_auto = [](auto &iface, const auto &token) {
const auto non_const_const_callback_auto = []<class Iface, class Token>(Iface &iface, const Token &token)
requires(!std::is_const_v<Iface>)
{
iface.nonConstMethod();
(void) token.stopRequested();
};
const auto non_const_non_const_callback_auto = [](auto &iface, auto &token) {
const auto non_const_non_const_callback_auto = []<class Iface, class Token>(Iface &iface, Token &token)
requires(!std::is_const_v<Iface> && !std::is_const_v<Token>)
{
iface.nonConstMethod();
token.requestStop();
};
Expand All@@ -594,16 +604,16 @@ TEST_F_S(Execute, ConstVsNonConst, WithStopToken) {
non_const_impl.execute(non_const_const_callback_auto);
non_const_impl.execute(non_const_non_const_callback_auto);

// Verify it compiles with const (commented out code will not compile)
// Verify it compiles with const
const auto &const_impl {m_impl};
const_impl.execute(const_const_callback);
// const_impl.execute(const_non_const_callback);
// const_impl.execute(non_const_const_callback);
// const_impl.execute(non_const_non_const_callback);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback), const TestIface &, const display_device::SchedulerStopToken &>);
const_impl.execute(const_const_callback_auto);
// const_impl.execute(const_non_const_callback_auto);
// const_impl.execute(non_const_const_callback_auto);
// const_impl.execute(non_const_non_const_callback_auto);
static_assert(!std::is_invocable_v<decltype(const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
static_assert(!std::is_invocable_v<decltype(non_const_non_const_callback_auto), const TestIface &, const display_device::SchedulerStopToken &>);
}

TEST_F_S(Stop) {
Expand Down
Loading
Loading