Mercurial > minori
changeset 236:4d461ef7d424
HUGE UPDATE: convert build system to autotools
why? because cmake sucks :)
line wrap: on
line diff
--- a/.builds/linux.yml Tue Jan 16 15:22:29 2024 -0500 +++ b/.builds/linux.yml Fri Jan 19 00:24:02 2024 -0500 @@ -18,14 +18,22 @@ tasks: - build: | cd minori + autoreconf -i + cd dep/animia + autoreconf -i + cd ../anitomy + autoreconf -i + cd ../pugixml + autoreconf -i + cd ../.. mkdir build cd build - cmake .. -G "Unix Makefiles" -DCMAKE_BUILD_TYPE=Release + ../configure make wget -O linuxdeploy "https://github.com/linuxdeploy/linuxdeploy/releases/download/1-alpha-20231026-1/linuxdeploy-x86_64.AppImage" chmod +x linuxdeploy - ./linuxdeploy --appdir Minori --executable minori -l libanimia.so -l libanitomy.so -l libpugixml.so -d rc/Minori.desktop -i rc/Minori.png --output appimage + ./linuxdeploy --appdir Minori --executable minori -d rc/Minori.desktop -i rc/Minori.png --output appimage artifacts: - minori/build/Minori-x86_64.AppImage triggers:
--- a/.builds/windows.yml Tue Jan 16 15:22:29 2024 -0500 +++ b/.builds/windows.yml Fri Jan 19 00:24:02 2024 -0500 @@ -22,12 +22,10 @@ git clone https://github.com/holyblackcat/quasi-msys2 quasi-msys2-win64 cd quasi-msys2-win64 echo MINGW64 >msystem.txt - make install _gcc _qt5-base _qt5-tools _curl + make install _gcc _qt5-base _qt5-tools _curl _autotools cd ../minori - mkdir build64 - cd build64 sudo bash -c 'echo -n 1 >/proc/sys/fs/binfmt_misc/status' - bash -c 'source ../../quasi-msys2-win64/env/all.src && cmake .. -G "Unix Makefiles" -DCMAKE_AUTOMOC_EXECUTABLE="$(which moc)" -DCMAKE_AUTORCC_EXECUTABLE="$(which rcc)" && make' + bash -c 'source ../../quasi-msys2-win64/env/all.src && autoreconf -i && cd dep/animia && autoreconf -i && cd ../anitomy && autoreconf -i && cd ../pugixml && autoreconf -i && ../.. && mkdir build64 && cd build64 && ../configure && make' - get-wine32: | sudo dpkg --add-architecture i386 sudo apt-get update @@ -43,7 +41,7 @@ mkdir build32 cd build32 sudo bash -c 'echo -n 1 >/proc/sys/fs/binfmt_misc/status' - bash -c 'source ../../quasi-msys2-win32/env/all.src && cmake .. -G "Unix Makefiles" -DCMAKE_AUTOMOC_EXECUTABLE="$(which moc)" -DCMAKE_AUTORCC_EXECUTABLE="$(which rcc)" && make' + bash -c 'source ../../quasi-msys2-win32/env/all.src && autoreconf -i && cd dep/animia && autoreconf -i && cd ../anitomy && autoreconf -i && cd ../pugixml && autoreconf -i && ../.. && mkdir build32 && cd build32 && ../configure && make' triggers: - action: email condition: failure
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Makefile.am Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,157 @@ +bin_PROGRAMS = minori + +minori_qtrc = \ + $(top_srcdir)/rc/dark.qrc \ + $(top_srcdir)/rc/icons.qrc \ + $(top_srcdir)/rc/player_data.qrc + +rc/final_qrc.cc: $(minori_qtrc) + @QT_RCC@ -o $@ $(minori_qtrc) + +minori_qtheaders = \ + include/core/http.h \ + include/gui/dialog/about.h \ + include/gui/dialog/information.h \ + include/gui/dialog/settings.h \ + include/gui/pages/anime_list.h \ + include/gui/pages/history.h \ + include/gui/pages/now_playing.h \ + include/gui/pages/search.h \ + include/gui/pages/seasons.h \ + include/gui/pages/statistics.h \ + include/gui/pages/torrents.h \ + include/gui/translate/anilist.h \ + include/gui/translate/anime.h \ + include/gui/translate/config.h \ + include/gui/widgets/anime_info.h \ + include/gui/widgets/clickable_label.h \ + include/gui/widgets/graph.h \ + include/gui/widgets/optional_date.h \ + include/gui/widgets/poster.h \ + include/gui/widgets/sidebar.h \ + include/gui/widgets/text.h \ + include/gui/locale.h \ + include/gui/theme.h \ + include/gui/window.h + +noinst_HEADERS = \ + include/core/anime_db.h \ + include/core/anime.h \ + include/core/config.h \ + include/core/date.h \ + include/core/filesystem.h \ + include/core/ini.h \ + include/core/json.h \ + include/core/session.h \ + include/core/strings.h \ + include/core/time.h \ + include/core/torrent.h \ + include/library/library.h \ + include/services/anilist.h \ + include/services/services.h \ + include/sys/glib/dark_theme.h \ + include/sys/osx/dark_theme.h \ + include/sys/osx/filesystem.h \ + include/sys/win32/dark_theme.h \ + include/track/media.h \ + $(minori_qtheaders) + +minori_moc_sources = $(minori_qtheaders:.h=_moc.cc) + +if BUILD_GLIB +files_glib = src/sys/glib/dark_theme.cc +cflags_glib = @GIO_CFLAGS@ +libs_glib = @GIO_LIBS@ +endif + +if BUILD_WIN +files_win = src/sys/win32/dark_theme.cc + +if BUILD_WINDRES +# Untested... +wrcflags_version = -DWRC_VERSION=0,`echo '$(PACKAGE_VERSION)' | sed 's/(\d+)\.(\d+)\.(\d+)/\1,\2,\3/'` + +WRCFLAGS = --use-temp-file -I. -I$(srcdir) $(wrcflags_version) +.rc.$(OBJEXT): + $(WINDRES) $(WRCFLAGS) -i $< -o $@ +files_windres=rc/win32/version.rc +endif +endif + +if BUILD_OSX +files_osx = src/sys/osx/dark_theme.cc src/sys/osx/filesystem.cc +libs_osx = Foundation AppKit +endif + +minori_SOURCES = \ + src/core/anime_db.cc \ + src/core/anime.cc \ + src/core/config.cc \ + src/core/date.cc \ + src/core/filesystem.cc \ + src/core/http.cc \ + src/core/json.cc \ + src/core/strings.cc \ + src/core/time.cc \ + src/gui/dialog/settings/application.cc \ + src/gui/dialog/settings/library.cc \ + src/gui/dialog/settings/recognition.cc \ + src/gui/dialog/settings/services.cc \ + src/gui/dialog/settings/torrents.cc \ + src/gui/dialog/about.cc \ + src/gui/dialog/information.cc \ + src/gui/dialog/settings.cc \ + src/gui/pages/anime_list.cc \ + src/gui/pages/history.cc \ + src/gui/pages/now_playing.cc \ + src/gui/pages/search.cc \ + src/gui/pages/seasons.cc \ + src/gui/pages/statistics.cc \ + src/gui/pages/torrents.cc \ + src/gui/translate/anilist.cc \ + src/gui/translate/anime.cc \ + src/gui/translate/config.cc \ + src/gui/widgets/anime_info.cc \ + src/gui/widgets/clickable_label.cc \ + src/gui/widgets/optional_date.cc \ + src/gui/widgets/poster.cc \ + src/gui/widgets/sidebar.cc \ + src/gui/widgets/text.cc \ + src/gui/locale.cc \ + src/gui/theme.cc \ + src/gui/window.cc \ + src/library/library.cc \ + src/services/anilist.cc \ + src/services/services.cc \ + src/track/media.cc \ + src/main.cc \ + $(files_osx) \ + $(files_glib) \ + $(files_win) \ + $(minori_moc_sources) \ + rc/final_qrc.cc \ + $(files_windres) + +minori_includes = \ + -I$(top_srcdir)/include \ + -I$(top_srcdir)/dep/animia/include \ + -I$(top_srcdir)/dep/pugixml/src \ + -I$(top_srcdir)/dep/anitomy \ + -I$(top_srcdir)/dep + +minori_CPPFLAGS = $(minori_includes) @QT_CXXFLAGS@ @LIBCURL_CPPFLAGS@ +minori_CXXFLAGS = $(cflags_glib) $(cflags_win) $(cflags_osx) + +minori_DEPENDENCIES = dep/pugixml/libpugixml.la dep/animia/libanimia.la dep/anitomy/libanitomy.la +minori_LDADD = $(libs_glib) $(libs_osx) @LIBCURL@ @QT_LIBS@ dep/pugixml/libpugixml.la dep/animia/libanimia.la dep/anitomy/libanitomy.la + +.qrc_qrc.cc: + + +.h_moc.cc: + @MKDIR_P@ -- `dirname $@` + @QT_MOC@ -o $@ $(minori_includes) $< + +SUFFIXES = .h _moc.cc .qrc _qrc.cc +SUBDIRS = $(subdirs) +ACLOCAL_AMFLAGS = -I m4
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/configure.ac Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,71 @@ +AC_INIT([minori], [0.1.0-alpha.1]) + +AC_CANONICAL_HOST + +AC_CONFIG_SRCDIR([src/main.cc]) +AC_CONFIG_AUX_DIR([build-aux]) +AC_CONFIG_MACRO_DIRS([m4]) + +AM_INIT_AUTOMAKE([-Wall -Wportability foreign subdir-objects]) + +# Do we have a C++17 compiler +AC_PROG_CXX +AX_CXX_COMPILE_STDCXX(17, noext, mandatory) + +AM_PROG_AR +LT_INIT + +# Qt? +AX_HAVE_QT + +if test "x$have_qt" = "xno"; then + AC_MSG_ERROR([*** Qt not found.]) +fi + +# need this for moc +AC_PROG_MKDIR_P + +# libcurl? +LIBCURL_CHECK_CONFIG(yes, 7.7.2, [have_libcurl=yes], [have_libcurl=no]) + +if test "x$have_libcurl" = "xno"; then + AC_MSG_ERROR([*** libcurl not found.]) +fi + +build_windows=no +build_osx=no +build_glib=no + +case "${host_os}" in + cygwin*|mingw*) + # Windows + build_windows=yes + AC_CHECK_TOOL([WINDRES], [windres]) + AC_SUBST(WINDRES) + AC_DEFINE(WIN32) + ;; + darwin*) + # Mac OS X + build_osx=yes + AC_DEFINE(MACOSX) + ;; + *) + if test "x$host_os" = "xlinux"; then + AC_DEFINE(LINUX) + fi + # Everything else + AC_SUBST([GIO_CFLAGS]) + AC_SUBST([GIO_LIBS]) + PKG_CHECK_MODULES(GIO, gio-2.0, [build_glib=yes], []) + ;; +esac + +AM_CONDITIONAL([BUILD_WIN], [test "x$build_windows" = "xyes"]) +AM_CONDITIONAL([BUILD_OSX], [test "x$build_osx" = "xyes"]) +AM_CONDITIONAL([BUILD_GLIB], [test "x$build_glib" = "xyes"]) +AM_CONDITIONAL([BUILD_WINDRES], [test "x$WINDRES" != "x"]) + +AC_CONFIG_SUBDIRS([dep/pugixml dep/animia dep/anitomy]) + +AC_CONFIG_FILES([Makefile]) +AC_OUTPUT
--- a/dep/animia/CMakeLists.txt Tue Jan 16 15:22:29 2024 -0500 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,125 +0,0 @@ -cmake_minimum_required(VERSION 3.16) -project(animia LANGUAGES CXX) -set(SRC_FILES - # any non-platform-specific files go here - src/animia.cc - src/player.cc - src/util.cc - src/strategist.cc - src/fd.cc - src/win.cc -) - -include(CheckLanguage) - -set(LIBRARIES) -set(INCLUDE_DIRS) -set(DEFINES) - -if(APPLE) - list(APPEND DEFINES MACOSX) - list(APPEND SRC_FILES - # xnu stuff - src/fd/xnu.cc - src/util/osx.cc - ) - - include(CheckIncludeFile) - check_include_file("CoreFoundation/CoreFoundation.h" HAVE_COREFOUNDATION) - # If you're building on OS X, you most likely do have this file, but we - # check anyway. - if(HAVE_COREFOUNDATION) - list(APPEND DEFINES HAVE_COREFOUNDATION) - find_library(OBJC_LIBRARY objc) - - if(NOT OBJC_LIBRARY) - message(STATUS "Found CoreFoundation/CoreFoundation.h, but not the Objective-C runtime. How?") - endif() - - list(APPEND SRC_FILES src/win/quartz.cc) - - find_library(FOUNDATION_LIBRARY Foundation) - find_library(COREGRAPHICS_LIBRARY CoreGraphics) - find_library(APPKIT_LIBRARY AppKit) - list(APPEND LIBRARIES ${FOUNDATION_LIBRARY} ${COREGRAPHICS_LIBRARY} ${APPKIT_LIBRARY} ${OBJC_LIBRARY}) - else() # NOT HAVE_COREFOUNDATION - message(STATUS "You don't have Core Foundation. How? What kind of voodoo magic did you do to cause this?") - message(WARNING "LaunchServices support will not be compiled.") - endif() # HAVE_COREFOUNDATION -elseif(WIN32) - list(APPEND DEFINES WIN32) - list(APPEND SRC_FILES - # win32 - src/fd/win32.cc - src/win/win32.cc - src/util/win32.cc - ) -else() # NOT WIN32 AND NOT APPLE - find_library(LIBUTIL_LIBRARY util) - find_library(LIBKVM_LIBRARY kvm) - - if(LINUX) - list(APPEND DEFINES LINUX) - list(APPEND SRC_FILES src/fd/proc.cc) - elseif(LIBUTIL_LIBRARY) # FreeBSD's libutil - get_filename_component(LIBUTIL_DIR ${LIBUTIL_LIBRARY} DIRECTORY) - - include(CheckLibraryExists) - check_library_exists(util kinfo_getfile ${LIBUTIL_DIR} LIBUTIL_GOOD) - - if(LIBUTIL_GOOD) - list(APPEND LIBRARIES ${LIBUTIL_LIBRARY}) - list(APPEND DEFINES LIBUTIL) - list(APPEND SRC_FILES src/fd/libutil.cc) - endif() # LIBUTIL_GOOD - elseif(LIBKVM_LIBRARY) # OpenBSD kvm - list(APPEND LIBRARIES ${LIBKVM_LIBRARY}) - list(APPEND DEFINES LIBKVM) - list(APPEND SRC_FILES src/fd/kvm.cc) - - get_filename_component(LIBKVM_DIR ${LIBKVM_LIBRARY} DIRECTORY) - - include(CheckLibraryExists) - check_library_exists(kvm kvm_getfiles ${LIBKVM_DIR} LIBKVM_HAS_GETFILES) - - if(LIBKVM_HAS_GETFILES) - list(APPEND DEFINES HAVE_KVM_GETFILES) - endif() # LIBKVM_HAS_GETFILES - endif() # LINUX -endif() # WIN32 AND APPLE - -# X11 -find_package(PkgConfig) -if(PKG_CONFIG_FOUND) - pkg_check_modules(XCB xcb xcb-res) - if (XCB_FOUND) - list(APPEND DEFINES X11) - list(APPEND LIBRARIES ${XCB_LINK_LIBRARIES}) - list(APPEND INCLUDE_DIRS ${XCB_INCLUDE_DIRS}) - list(APPEND SRC_FILES src/win/x11.cc) - endif() # XCB_FOUND - - # Wayland - pkg_check_modules(WAYLAND wayland-client) - if(WAYLAND_FOUND) - enable_language(C) - list(APPEND DEFINES WAYLAND) - list(APPEND SRC_FILES - src/win/wayland.cc - src/win/wayland/ext-foreign-toplevel-list-v1.c - src/win/wayland/wlr-foreign-toplevel-management-unstable-v1.c - ) - list(APPEND INCLUDE_DIRS ${WAYLAND_INCLUDE_DIRS}) - list(APPEND LIBRARIES ${WAYLAND_LINK_LIBRARIES}) - endif() # WAYLAND_FOUND -endif() # PKG_CONFIG_FOUND - -add_library(animia SHARED ${SRC_FILES}) -set_target_properties(animia PROPERTIES - PUBLIC_HEADER include/animia.h - CXX_STANDARD 17 -) - -target_compile_definitions(animia PRIVATE ${DEFINES}) -target_include_directories(animia PUBLIC include PRIVATE ${INCLUDE_DIRS}) -target_link_libraries(animia PUBLIC ${LIBRARIES})
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/animia/Makefile.am Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,66 @@ +lib_LTLIBRARIES = libanimia.la +include_HEADERS = include/animia.h + +if BUILD_WIN +files_win = src/fd/win32.cc src/win/win32.cc src/util/win32.cc +endif + +if BUILD_OSX +files_osx = src/fd/xnu.cc src/win/quartz.cc src/util/osx.cc +cflags_osx = +libs_osx = Foundation CoreGraphics AppKit objc +endif + +if BUILD_LINUX +files_linux = src/fd/proc.cc +endif + +if BUILD_LIBUTIL +files_libutil = src/fd/libutil.cc +libs_libutil = -lutil +endif + +if BUILD_LIBKVM +files_libkvm = src/fd/kvm.cc +libs_libkvm = -lkvm +endif + +if BUILD_XCB +files_x11 = src/win/x11.cc +cflags_x11 = @XCB_CFLAGS@ +libs_x11 = @XCB_LIBS@ +endif + +if BUILD_WAYLAND +files_wayland = \ + src/win/wayland.cc \ + src/win/wayland/ext-foreign-toplevel-list-v1.c \ + src/win/wayland/wlr-foreign-toplevel-management-unstable-v1.c +cflags_wayland = @WAYLAND_CFLAGS@ +libs_wayland = @WAYLAND_LIBS@ +endif + +libanimia_la_SOURCES = \ + src/animia.cc \ + src/fd.cc \ + src/player.cc \ + src/strategist.cc \ + src/util.cc \ + src/win.cc \ + $(files_win) \ + $(files_osx) \ + $(files_linux) \ + $(files_libutil) \ + $(files_libkvm) \ + $(files_x11) \ + $(files_wayland) + +libanimia_la_CPPFLAGS = -I$(top_srcdir)/include @DEFS@ + +libanimia_la_LDFLAGS = -version-info 0:0:0 + +libanimia_la_CXXFLAGS = $(cflags_osx) $(cflags_x11) $(cflags_wayland) + +libanimia_la_LIBADD = $(libs_wayland) $(libs_x11) $(libs_osx) $(libs_libutil) $(libs_libkvm) + +ACLOCAL_AMFLAGS = -I m4
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/animia/configure.ac Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,79 @@ +AC_INIT([animia], [0.1.0-alpha.1]) + +AC_CANONICAL_HOST + +AC_CONFIG_SRCDIR([src/animia.cc]) +AC_CONFIG_AUX_DIR([build-aux]) +AC_CONFIG_MACRO_DIRS([m4]) + +AM_INIT_AUTOMAKE([-Wall -Werror foreign subdir-objects]) + +# Do we have a C++17 compiler +AC_PROG_CXX + +AM_PROG_AR +LT_INIT + +build_win32=no +build_osx=no +build_linux=no +build_libutil=no +build_kvm=no + +build_x11=no +build_wayland=no + +case "${host_os}" in + cygwin*|mingw*) + # Windows + build_windows=yes + AC_CHECK_TOOL([WINDRES], [windres]) + AC_SUBST(WINDRES) + AC_DEFINE([WIN32]) + ;; + darwin*) + # Mac OS X + build_osx=yes + AC_DEFINE([MACOSX]) + ;; + linux*) + build_linux=yes + AC_DEFINE([LINUX]) + ;; + *) + # FreeBSD + AC_CHECK_LIB([util], [kinfo_getfile], [build_libutil=yes], [build_libutil=no]) + if test "x$build_libutil" = "xyes"; then + AC_DEFINE([LIBUTIL]) + else + # OpenBSD + AC_CHECK_LIB([kvm], [kvm_getfiles], [build_kvm=yes], [build_kvm=no]) + if test "x$build_kvm" = "xyes"; then + AC_DEFINE([LIBKVM]) + fi + fi + ;; +esac + +if ! test "x$build_osx" = "xyes" && ! test "x$build_windows" = "xyes"; then + PKG_CHECK_MODULES(XCB, [xcb xcb-res], [build_x11=yes], [build_x11=no]) + if test "x$build_x11" = "xyes"; then + AC_DEFINE([X11]) + fi + PKG_CHECK_MODULES(WAYLAND, [wayland-client], [build_wayland=yes], [build_wayland=no]) + if test "x$build_wayland" = "xyes"; then + AC_DEFINE([WAYLAND]) + fi +fi + +AM_CONDITIONAL([BUILD_WIN], [test "x$build_windows" = "xyes"]) +AM_CONDITIONAL([BUILD_OSX], [test "x$build_osx" = "xyes"]) +AM_CONDITIONAL([BUILD_LINUX], [test "x$build_linux" = "xyes"]) +AM_CONDITIONAL([BUILD_LIBUTIL], [test "x$build_libutil" = "xyes"]) +AM_CONDITIONAL([BUILD_LIBKVM], [test "x$build_kvm" = "xyes"]) + +AM_CONDITIONAL([BUILD_XCB], [test "x$build_x11" = "xyes"]) +AM_CONDITIONAL([BUILD_WAYLAND], [test "x$build_wayland" = "xyes"]) + +AC_CONFIG_FILES([Makefile]) +AC_OUTPUT
--- a/dep/animia/src/animia.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/dep/animia/src/animia.cc Fri Jan 19 00:24:02 2024 -0500 @@ -27,9 +27,12 @@ return false; } -static bool IsWindowInList(const Player& player, const std::string& name) { +static bool IsWindowInList(const Player& player, const Window& window) { +// if (util::CheckPattern(player.window_title_format, window.text)) +// return true; + for (const auto& pattern : player.windows) - if (util::CheckPattern(pattern, name)) + if (util::CheckPattern(pattern, window.class_name)) return true; return false; @@ -65,22 +68,12 @@ if (!internal::EnumerateOpenProcesses(process_proc)) return false; - /* Then add our cool windows. - Note: X11 is stupid and there's no reliable way to get a PID from a given window. - This is because some windows might not even have a process attached to them. - We should set the PID of the process if we can get it, but that'll be for when - I can actually be arsed to implement the X11 backend. */ auto window_proc = [&](const Process& process, const Window& window) -> bool { for (const auto& player : players) { - if (!internal::PlayerHasStrategy(player, Strategy::WindowTitle)) - continue; + if (internal::IsWindowInList(player, window)) + results.push_back({ResultType::Window, player, process, window, {}}); + } - if (!internal::IsWindowInList(player, window.class_name)) - continue; - - results.push_back({ResultType::Window, player, process, window, {}}); - break; - } return true; };
--- a/dep/animia/src/strategist.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/dep/animia/src/strategist.cc Fri Jan 19 00:24:02 2024 -0500 @@ -5,6 +5,8 @@ #include "animia/strategies.h" #include "animia/util.h" +#include <iostream> + namespace animia::internal { class Strategist {
--- a/dep/animia/src/win/x11.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/dep/animia/src/win/x11.cc Fri Jan 19 00:24:02 2024 -0500 @@ -1,11 +1,3 @@ -/* - * win/x11.cc: provides support for X11 clients via XCB - * - * This code is fairly fast (I think...). As a result, - * a lot of it is hard to read if you're unfamiliar with - * asynchronous programming, but it works much better than - * Xlib (which can take much longer). -*/ #include "animia/win/x11.h" #include "animia/win.h" #include "animia.h" @@ -19,6 +11,10 @@ #include <string> #include <set> +#include <chrono> + +#include <iostream> + static size_t str_nlen(const char* s, size_t len) { size_t i = 0; for (; i < len && s[i]; i++); @@ -27,6 +23,32 @@ namespace animia::internal::x11 { +static void GetWindowPID(xcb_connection_t* connection, const std::vector<xcb_window_t>& windows, std::unordered_map<xcb_window_t, pid_t>& result) { + std::vector<xcb_res_query_client_ids_cookie_t> cookies; + cookies.reserve(windows.size()); + + for (const auto& window : windows) { + xcb_res_client_id_spec_t spec = { + .client = window, + .mask = XCB_RES_CLIENT_ID_MASK_LOCAL_CLIENT_PID + }; + + cookies.push_back(::xcb_res_query_client_ids(connection, 1, &spec)); + } + + for (size_t i = 0; i < cookies.size(); i++) { + xcb_res_query_client_ids_reply_t* reply = ::xcb_res_query_client_ids_reply(connection, cookies.at(i), NULL); + + xcb_res_client_id_value_iterator_t it = xcb_res_query_client_ids_ids_iterator(reply); + for (; it.rem; xcb_res_client_id_value_next(&it)) { + if (it.data->spec.mask & XCB_RES_CLIENT_ID_MASK_LOCAL_CLIENT_PID) { + result[windows.at(i)] = *::xcb_res_client_id_value_value(it.data); + continue; + } + } + } +} + static bool GetAllTopLevelWindowsEWMH(xcb_connection_t* connection, const std::vector<xcb_window_t>& roots, std::set<xcb_window_t>& result) { const xcb_atom_t Atom__NET_CLIENT_LIST = [connection]{ static constexpr std::string_view name = "_NET_CLIENT_LIST"; @@ -50,25 +72,23 @@ for (const auto& cookie : cookies) { xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, cookie, NULL); - - if (reply && reply->length == 32) { + if (reply) { xcb_window_t* value = reinterpret_cast<xcb_window_t*>(::xcb_get_property_value(reply)); int len = ::xcb_get_property_value_length(reply); for (size_t i = 0; i < len; i++) result.insert(value[i]); - success = true; } - free(reply); } return success; } +/* I have no idea why this works. */ static bool WalkWindows(xcb_connection_t* connection, const std::vector<xcb_window_t>& roots, std::set<xcb_window_t>& result) { - /* move this somewhere else pl0x */ + /* move this somewhere */ xcb_atom_t Atom_WM_STATE = [connection]{ static constexpr std::string_view name = "WM_STATE"; xcb_intern_atom_cookie_t cookie = ::xcb_intern_atom(connection, true, name.size(), name.data()); @@ -81,98 +101,49 @@ if (Atom_WM_STATE == XCB_ATOM_NONE) return false; - /* for each toplevel: search recursively for */ - std::function<bool(const xcb_window_t*, const int, xcb_window_t&)> find_wm_state_window = [&](const xcb_window_t* wins, const int wins_len, xcb_window_t& out) { - /* Check for wm_state */ - { - std::vector<xcb_get_property_cookie_t> property_cookies; - property_cookies.reserve(wins_len); - - for (size_t j = 0; j < wins_len; j++) - property_cookies.push_back(::xcb_get_property(connection, 0, wins[j], Atom_WM_STATE, Atom_WM_STATE, 0, 0)); - - for (size_t j = 0; j < property_cookies.size(); j++) { - xcb_generic_error_t* err = NULL; - xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, property_cookies.at(j), &err); - - if (reply->format || reply->type || reply->length) { - out = wins[j]; - free(reply); - return true; - } - - free(reply); - } - } - - /* Query tree for recursion */ - { - std::vector<xcb_query_tree_cookie_t> cookies; - cookies.reserve(wins_len); - - for (size_t j = 0; j < wins_len; j++) - cookies.push_back(::xcb_query_tree(connection, wins[j])); - - for (const auto& cookie : cookies) { - xcb_query_tree_reply_t* reply = ::xcb_query_tree_reply(connection, cookie, NULL); - - xcb_window_t* windows = ::xcb_query_tree_children(reply); - int len = ::xcb_query_tree_children_length(reply); - - if (find_wm_state_window(windows, len, out)) { - free(reply); - return true; - } - - free(reply); - } - } - - return false; - }; - - /* Get the tree for each root */ std::vector<xcb_query_tree_cookie_t> cookies; cookies.reserve(roots.size()); for (const auto& root : roots) cookies.push_back(::xcb_query_tree(connection, root)); - for (size_t i = 0; i < cookies.size(); i++) { - xcb_query_tree_reply_t* reply = ::xcb_query_tree_reply(connection, cookies.at(i), NULL); + for (const auto& cookie : cookies) { + xcb_query_tree_reply_t* reply = ::xcb_query_tree_reply(connection, cookie, NULL); - xcb_window_t* windows = ::xcb_query_tree_children(reply); - int len = ::xcb_query_tree_children_length(reply); - if (len < 1) - continue; + std::vector<xcb_window_t> windows = [reply]{ + xcb_window_t* windows = ::xcb_query_tree_children(reply); + int len = ::xcb_query_tree_children_length(reply); - /* Then get the tree of each child window. */ - std::vector<xcb_query_tree_cookie_t> cookies; - cookies.reserve(len); + std::vector<xcb_window_t> w; + w.reserve(len); + + for (int i = 0; i < len; i++) + w.push_back(windows[i]); - for (size_t j = 0; j < len; j++) - cookies.push_back(::xcb_query_tree(connection, windows[j])); + return w; + }(); + + std::vector<xcb_get_property_cookie_t> state_property_cookies; + state_property_cookies.reserve(windows.size()); - /* For each child window... */ - for (size_t j = 0; j < cookies.size(); j++) { - xcb_query_tree_reply_t* reply = ::xcb_query_tree_reply(connection, cookies.at(j), NULL); + for (int i = 0; i < windows.size(); i++) + state_property_cookies.push_back(::xcb_get_property(connection, 0, windows[i], Atom_WM_STATE, Atom_WM_STATE, 0, 0)); - xcb_window_t* children = ::xcb_query_tree_children(reply); - int children_len = ::xcb_query_tree_children_length(reply); - if (children_len < 1) { - result.insert(windows[j]); + for (size_t i = 0; i < state_property_cookies.size(); i++) { + xcb_generic_error_t* err = NULL; + xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, state_property_cookies.at(i), &err); + + if (reply->format || reply->type || reply->length) { + result.insert(windows[i]); + free(reply); continue; } - xcb_window_t out = windows[j]; - /* Search recursively for a window with WM_STATE. If we don't, - * just add the toplevel. - */ - find_wm_state_window(children, children_len, out); - result.insert(out); + free(reply); } - free(reply); + if (WalkWindows(connection, windows, result)) + continue; } return false; @@ -186,27 +157,23 @@ if (!connection) return false; - std::vector<xcb_screen_t> screens; - + std::set<xcb_window_t> windows; { - xcb_screen_iterator_t iter = ::xcb_setup_roots_iterator(xcb_get_setup(connection)); - for (; iter.rem; ::xcb_screen_next(&iter)) - screens.push_back(*iter.data); - } + std::vector<xcb_window_t> roots; + { + xcb_screen_iterator_t iter = ::xcb_setup_roots_iterator(xcb_get_setup(connection)); + for (; iter.rem; ::xcb_screen_next(&iter)) + roots.push_back(iter.data->root); + } - std::vector<xcb_window_t> roots; - roots.reserve(screens.size()); - - for (const auto& screen : screens) - roots.push_back(screen.root); - - std::set<xcb_window_t> windows; - if (!GetAllTopLevelWindowsEWMH(connection, roots, windows)) - WalkWindows(connection, roots, windows); + + if (!GetAllTopLevelWindowsEWMH(connection, roots, windows)) + WalkWindows(connection, roots, windows); + } std::vector<xcb_get_property_cookie_t> class_property_cookies; std::vector<xcb_get_property_cookie_t> name_property_cookies; - std::vector<xcb_res_query_client_ids_cookie_t> pid_property_cookies; + std::vector<xcb_get_property_cookie_t> pid_property_cookies; class_property_cookies.reserve(windows.size()); name_property_cookies.reserve(windows.size()); pid_property_cookies.reserve(windows.size()); @@ -214,13 +181,7 @@ for (const auto& window : windows) { class_property_cookies.push_back(::xcb_get_property(connection, 0, window, XCB_ATOM_WM_CLASS, XCB_ATOM_STRING, 0L, 2048L)); name_property_cookies.push_back(::xcb_get_property(connection, 0, window, XCB_ATOM_WM_NAME, XCB_ATOM_STRING, 0L, UINT_MAX)); - - xcb_res_client_id_spec_t spec = { - .client = window, - .mask = XCB_RES_CLIENT_ID_MASK_LOCAL_CLIENT_PID - }; - - pid_property_cookies.push_back(::xcb_res_query_client_ids(connection, 1, &spec)); + pid_property_cookies.push_back(::xcb_get_property(connection, 0, window, XCB_ATOM_WM_NAME, XCB_ATOM_CARDINAL, 0L, 1L)); } size_t i = 0; @@ -229,7 +190,6 @@ win.id = window; { xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, class_property_cookies.at(i), NULL); - if (reply && reply->format == 8) { const char* data = reinterpret_cast<char*>(::xcb_get_property_value(reply)); const int data_len = ::xcb_get_property_value_length(reply); @@ -239,38 +199,26 @@ win.class_name = std::string(class_name, str_nlen(class_name, data_len - (instance_len + 1))); } - free(reply); } { xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, name_property_cookies.at(i), NULL); - - if (reply && reply->format == 8) { + if (reply) { const char* data = reinterpret_cast<char*>(::xcb_get_property_value(reply)); int len = ::xcb_get_property_value_length(reply); - win.text = std::string(data, len); + win.text = std::string((char*)data, len); } - free(reply); } Process proc = {0}; { - xcb_res_query_client_ids_reply_t* reply = ::xcb_res_query_client_ids_reply(connection, pid_property_cookies.at(i), NULL); - - if (reply->length) { - xcb_res_client_id_value_iterator_t it = ::xcb_res_query_client_ids_ids_iterator(reply); - for (; it.rem; ::xcb_res_client_id_value_next(&it)) { - if (it.data->spec.mask & XCB_RES_CLIENT_ID_MASK_LOCAL_CLIENT_PID) { - proc.pid = *::xcb_res_client_id_value_value(it.data); - break; - } - } - } + xcb_get_property_reply_t* reply = ::xcb_get_property_reply(connection, pid_property_cookies.at(i), NULL); + if (reply) + proc.pid = *reinterpret_cast<uint32_t*>(::xcb_get_property_value(reply)); free(reply); } - if (!window_proc(proc, win)) { ::xcb_disconnect(connection); return false;
--- a/dep/anitomy/CMakeLists.txt Tue Jan 16 15:22:29 2024 -0500 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,16 +0,0 @@ -cmake_minimum_required(VERSION 3.9) -project(anitomy) -add_library(anitomy SHARED - anitomy/anitomy.cpp - anitomy/element.cpp - anitomy/keyword.cpp - anitomy/parser.cpp - anitomy/parser_helper.cpp - anitomy/parser_number.cpp - anitomy/string.cpp - anitomy/token.cpp - anitomy/tokenizer.cpp -) -set_target_properties(anitomy PROPERTIES - PUBLIC_HEADER anitomy/anitomy.h CXX_STANDARD 17) -target_include_directories(anitomy PRIVATE src)
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/anitomy/Makefile.am Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,22 @@ +lib_LTLIBRARIES = libanitomy.la +libanitomy_la_SOURCES = \ + anitomy/anitomy.cpp \ + anitomy/element.cpp \ + anitomy/keyword.cpp \ + anitomy/parser.cpp \ + anitomy/parser_helper.cpp \ + anitomy/parser_number.cpp \ + anitomy/string.cpp \ + anitomy/token.cpp \ + anitomy/tokenizer.cpp + +include_HEADERS = \ + anitomy/anitomy.h \ + anitomy/element.h \ + anitomy/keyword.h \ + anitomy/parser.h \ + anitomy/string.h \ + anitomy/token.h \ + anitomy/tokenizer.h + +ACLOCAL_AMFLAGS = -I m4 \ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/anitomy/configure.ac Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,18 @@ +AC_INIT([anitomy], [1.0]) + +AC_CONFIG_SRCDIR([anitomy/anitomy.cpp]) +AC_CONFIG_AUX_DIR([build-aux]) +AC_CONFIG_MACRO_DIRS([m4]) + +AM_INIT_AUTOMAKE([-Wall -Werror foreign subdir-objects]) + +# Check for a C compiler +AC_PROG_CXX + +# Need this because libtool is weird +AM_PROG_AR + +LT_INIT + +AC_CONFIG_FILES([Makefile]) +AC_OUTPUT \ No newline at end of file
--- a/dep/pugixml/CMakeLists.txt Tue Jan 16 15:22:29 2024 -0500 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,264 +0,0 @@ -cmake_minimum_required(VERSION 3.5) - -# Policy configuration; this *MUST* be specified before project is defined -if(POLICY CMP0091) - cmake_policy(SET CMP0091 NEW) # Enables use of MSVC_RUNTIME_LIBRARY -endif() - -project(pugixml VERSION 1.14 LANGUAGES CXX) - -include(CMakePackageConfigHelpers) -include(CMakeDependentOption) -include(GNUInstallDirs) -include(CTest) - -cmake_dependent_option(PUGIXML_USE_VERSIONED_LIBDIR - "Use a private subdirectory to install the headers and libraries" OFF - "CMAKE_SOURCE_DIR STREQUAL PROJECT_SOURCE_DIR" OFF) - -cmake_dependent_option(PUGIXML_USE_POSTFIX - "Use separate postfix for each configuration to make sure you can install multiple build outputs" OFF - "CMAKE_SOURCE_DIR STREQUAL PROJECT_SOURCE_DIR" OFF) - -cmake_dependent_option(PUGIXML_STATIC_CRT - "Use static MSVC RT libraries" OFF - "MSVC" OFF) - -cmake_dependent_option(PUGIXML_BUILD_TESTS - "Build pugixml tests" OFF - "BUILD_TESTING;CMAKE_SOURCE_DIR STREQUAL PROJECT_SOURCE_DIR" OFF) - -# Custom build defines -set(PUGIXML_BUILD_DEFINES CACHE STRING "Build defines for custom options") -separate_arguments(PUGIXML_BUILD_DEFINES) - -# Technically not needed for this file. This is builtin CMAKE global variable. -option(BUILD_SHARED_LIBS "Build shared instead of static library" OFF) - -# Expose option to build PUGIXML as static as well when the global BUILD_SHARED_LIBS variable is set -cmake_dependent_option(PUGIXML_BUILD_SHARED_AND_STATIC_LIBS - "Build both shared and static libraries" OFF - "BUILD_SHARED_LIBS" OFF) - -# Expose options from the pugiconfig.hpp -option(PUGIXML_WCHAR_MODE "Enable wchar_t mode" OFF) -option(PUGIXML_COMPACT "Enable compact mode" OFF) - -# Advanced options from pugiconfig.hpp -option(PUGIXML_NO_XPATH "Disable XPath" OFF) -option(PUGIXML_NO_STL "Disable STL" OFF) -option(PUGIXML_NO_EXCEPTIONS "Disable Exceptions" OFF) -mark_as_advanced(PUGIXML_NO_XPATH PUGIXML_NO_STL PUGIXML_NO_EXCEPTIONS) - -set(PUGIXML_PUBLIC_DEFINITIONS - $<$<BOOL:${PUGIXML_WCHAR_MODE}>:PUGIXML_WCHAR_MODE> - $<$<BOOL:${PUGIXML_COMPACT}>:PUGIXML_COMPACT> - $<$<BOOL:${PUGIXML_NO_XPATH}>:PUGIXML_NO_XPATH> - $<$<BOOL:${PUGIXML_NO_STL}>:PUGIXML_NO_STL> - $<$<BOOL:${PUGIXML_NO_EXCEPTIONS}>:PUGIXML_NO_EXCEPTIONS>) - -# This is used to backport a CMake 3.15 feature, but is also forwards compatible -if (NOT DEFINED CMAKE_MSVC_RUNTIME_LIBRARY) - set(CMAKE_MSVC_RUNTIME_LIBRARY - MultiThreaded$<$<CONFIG:Debug>:Debug>$<$<NOT:$<BOOL:${PUGIXML_STATIC_CRT}>>:DLL>) -endif() - -if (NOT DEFINED CMAKE_CXX_STANDARD_REQUIRED) - set(CMAKE_CXX_STANDARD_REQUIRED ON) -endif() - -if (NOT DEFINED CMAKE_CXX_STANDARD) - set(CMAKE_CXX_STANDARD 11) -endif() - -if (PUGIXML_USE_POSTFIX) - set(CMAKE_RELWITHDEBINFO_POSTFIX _r) - set(CMAKE_MINSIZEREL_POSTFIX _m) - set(CMAKE_DEBUG_POSTFIX _d) -endif() - -if (CMAKE_VERSION VERSION_LESS 3.15) - set(msvc-rt $<TARGET_PROPERTY:MSVC_RUNTIME_LIBRARY>) - - set(msvc-rt-mtd-shared $<STREQUAL:${msvc-rt},MultiThreadedDebugDLL>) - set(msvc-rt-mtd-static $<STREQUAL:${msvc-rt},MultiThreadedDebug>) - set(msvc-rt-mt-shared $<STREQUAL:${msvc-rt},MultiThreadedDLL>) - set(msvc-rt-mt-static $<STREQUAL:${msvc-rt},MultiThreaded>) - unset(msvc-rt) - - set(msvc-rt-mtd-shared $<${msvc-rt-mtd-shared}:-MDd>) - set(msvc-rt-mtd-static $<${msvc-rt-mtd-static}:-MTd>) - set(msvc-rt-mt-shared $<${msvc-rt-mt-shared}:-MD>) - set(msvc-rt-mt-static $<${msvc-rt-mt-static}:-MT>) -endif() - -set(versioned-dir $<$<BOOL:${PUGIXML_USE_VERSIONED_LIBDIR}>:/pugixml-${PROJECT_VERSION}>) - -set(libs) - -if (BUILD_SHARED_LIBS) - add_library(pugixml-shared SHARED - ${PROJECT_SOURCE_DIR}/scripts/pugixml_dll.rc - ${PROJECT_SOURCE_DIR}/src/pugixml.cpp) - add_library(pugixml::shared ALIAS pugixml-shared) - list(APPEND libs pugixml-shared) - string(CONCAT pugixml.msvc $<OR: - $<STREQUAL:${CMAKE_CXX_COMPILER_FRONTEND_VARIANT},MSVC>, - $<CXX_COMPILER_ID:MSVC> - >) - - set_property(TARGET pugixml-shared PROPERTY EXPORT_NAME shared) - target_include_directories(pugixml-shared - PUBLIC - $<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/src>) - target_compile_definitions(pugixml-shared - PUBLIC - ${PUGIXML_BUILD_DEFINES} - ${PUGIXML_PUBLIC_DEFINITIONS} - PRIVATE - PUGIXML_API=$<IF:${pugixml.msvc},__declspec\(dllexport\),__attribute__\(\(visibility\("default"\)\)\)> - ) - target_compile_options(pugixml-shared - PRIVATE - ${msvc-rt-mtd-shared} - ${msvc-rt-mtd-static} - ${msvc-rt-mt-shared} - ${msvc-rt-mt-static}) -endif() - -if (NOT BUILD_SHARED_LIBS OR PUGIXML_BUILD_SHARED_AND_STATIC_LIBS) - add_library(pugixml-static STATIC - ${PROJECT_SOURCE_DIR}/src/pugixml.cpp) - add_library(pugixml::static ALIAS pugixml-static) - list(APPEND libs pugixml-static) - - set_property(TARGET pugixml-static PROPERTY EXPORT_NAME static) - target_include_directories(pugixml-static - PUBLIC - $<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/src>) - target_compile_definitions(pugixml-static - PUBLIC - ${PUGIXML_BUILD_DEFINES} - ${PUGIXML_PUBLIC_DEFINITIONS}) - target_compile_options(pugixml-static - PRIVATE - ${msvc-rt-mtd-shared} - ${msvc-rt-mtd-static} - ${msvc-rt-mt-shared} - ${msvc-rt-mt-static}) -endif() - -if (BUILD_SHARED_LIBS) - set(pugixml-alias pugixml-shared) -else() - set(pugixml-alias pugixml-static) -endif() -add_library(pugixml INTERFACE) -target_link_libraries(pugixml INTERFACE ${pugixml-alias}) -add_library(pugixml::pugixml ALIAS pugixml) - -set_target_properties(${libs} - PROPERTIES - MSVC_RUNTIME_LIBRARY ${CMAKE_MSVC_RUNTIME_LIBRARY} - EXCLUDE_FROM_ALL ON - POSITION_INDEPENDENT_CODE ON - SOVERSION ${PROJECT_VERSION_MAJOR} - VERSION ${PROJECT_VERSION} - OUTPUT_NAME pugixml) - -set_target_properties(${libs} - PROPERTIES - EXCLUDE_FROM_ALL OFF) -set(install-targets pugixml ${libs}) - -configure_package_config_file( - "${PROJECT_SOURCE_DIR}/scripts/pugixml-config.cmake.in" - "${PROJECT_BINARY_DIR}/pugixml-config.cmake" - INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR} - NO_CHECK_REQUIRED_COMPONENTS_MACRO - NO_SET_AND_CHECK_MACRO) - -write_basic_package_version_file( - "${PROJECT_BINARY_DIR}/pugixml-config-version.cmake" - COMPATIBILITY SameMajorVersion) - -if (PUGIXML_USE_POSTFIX) - if(CMAKE_BUILD_TYPE MATCHES RelWithDebInfo) - set(LIB_POSTFIX ${CMAKE_RELWITHDEBINFO_POSTFIX}) - elseif(CMAKE_BUILD_TYPE MATCHES MinSizeRel) - set(LIB_POSTFIX ${CMAKE_MINSIZEREL_POSTFIX}) - elseif(CMAKE_BUILD_TYPE MATCHES Debug) - set(LIB_POSTFIX ${CMAKE_DEBUG_POSTFIX}) - endif() -endif() - -configure_file(scripts/pugixml.pc.in pugixml.pc @ONLY) - -if (NOT DEFINED PUGIXML_RUNTIME_COMPONENT) - set(PUGIXML_RUNTIME_COMPONENT Runtime) -endif() - -if (NOT DEFINED PUGIXML_LIBRARY_COMPONENT) - set(PUGIXML_LIBRARY_COMPONENT Library) -endif() - -if (NOT DEFINED PUGIXML_DEVELOPMENT_COMPONENT) - set(PUGIXML_DEVELOPMENT_COMPONENT Development) -endif() - -set(namelink-component) -if (NOT CMAKE_VERSION VERSION_LESS 3.12) - set(namelink-component NAMELINK_COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT}) -endif() -install(TARGETS ${install-targets} - EXPORT pugixml-targets - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} COMPONENT ${PUGIXML_RUNTIME_COMPONENT} - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT ${PUGIXML_LIBRARY_COMPONENT} ${namelink-component} - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT} - INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}${versioned-dir}) - -install(EXPORT pugixml-targets - NAMESPACE pugixml:: - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/pugixml COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT}) - -export(EXPORT pugixml-targets - NAMESPACE pugixml::) - -install(FILES - "${PROJECT_BINARY_DIR}/pugixml-config-version.cmake" - "${PROJECT_BINARY_DIR}/pugixml-config.cmake" - DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/pugixml COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT}) - -install(FILES ${PROJECT_BINARY_DIR}/pugixml.pc - DESTINATION ${CMAKE_INSTALL_LIBDIR}/pkgconfig COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT}) - -install( - FILES - "${PROJECT_SOURCE_DIR}/src/pugiconfig.hpp" - "${PROJECT_SOURCE_DIR}/src/pugixml.hpp" - DESTINATION - ${CMAKE_INSTALL_INCLUDEDIR}${versioned-dir} COMPONENT ${PUGIXML_DEVELOPMENT_COMPONENT}) - -if (PUGIXML_BUILD_TESTS) - set(fuzz-pattern "tests/fuzz_*.cpp") - set(test-pattern "tests/*.cpp") - if (CMAKE_VERSION VERSION_GREATER 3.11) - list(INSERT fuzz-pattern 0 CONFIGURE_DEPENDS) - list(INSERT test-pattern 0 CONFIGURE_DEPENDS) - endif() - file(GLOB test-sources ${test-pattern}) - file(GLOB fuzz-sources ${fuzz-pattern}) - list(REMOVE_ITEM test-sources ${fuzz-sources}) - - add_custom_target(check - COMMAND ${CMAKE_CTEST_COMMAND} --output-on-failure) - - add_executable(pugixml-check ${test-sources}) - add_test(NAME pugixml::test - COMMAND pugixml-check - WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}) - add_dependencies(check pugixml-check) - target_link_libraries(pugixml-check - PRIVATE - pugixml::pugixml) -endif()
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/pugixml/Makefile.am Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,5 @@ +lib_LTLIBRARIES = libpugixml.la +libpugixml_la_SOURCES = src/pugixml.cpp +include_HEADERS = src/pugixml.hpp + +ACLOCAL_AMFLAGS = -I m4
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dep/pugixml/configure.ac Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,18 @@ +AC_INIT([pugixml], [1.14]) + +AC_CONFIG_SRCDIR([src/pugixml.cpp]) +AC_CONFIG_AUX_DIR([build-aux]) +AC_CONFIG_MACRO_DIRS([m4]) + +AM_INIT_AUTOMAKE([-Wall -Werror foreign subdir-objects]) + +# Check for a C compiler +AC_PROG_CXX + +# Need this because libtool is weird +AM_PROG_AR + +LT_INIT + +AC_CONFIG_FILES([Makefile]) +AC_OUTPUT
--- a/include/core/http.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/core/http.h Fri Jan 19 00:24:02 2024 -0500 @@ -15,7 +15,7 @@ Q_OBJECT public: - GetThread(const std::string& u, const std::vector<std::string>& h = {}) { + GetThread(const std::string& u, const std::vector<std::string>& h = {}, QObject* parent = nullptr) : QThread(parent) { url = u; headers = h; } @@ -36,7 +36,7 @@ Q_OBJECT public: - PostThread(const std::string& u, const std::string& d, const std::vector<std::string>& h = {}) { + PostThread(const std::string& u, const std::string& d, const std::vector<std::string>& h = {}, QObject* parent = nullptr) : QThread(parent) { url = u; data = d; headers = h;
--- a/include/core/session.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/core/session.h Fri Jan 19 00:24:02 2024 -0500 @@ -16,7 +16,7 @@ int uptime() { return timer.elapsed(); } Config config; - static constexpr semver::version version{0, 1, 0, semver::prerelease::alpha, 1}; + static constexpr semver::version version{PACKAGE_VERSION}; private: unsigned int requests = 0;
--- a/include/core/torrent.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/core/torrent.h Fri Jan 19 00:24:02 2024 -0500 @@ -5,9 +5,10 @@ #include <QDateTime> /* this is really just a fancy struct... - - this will be moved into its own namespace if - it's deemed necessary */ + * + * this will be moved into its own namespace if + * it's deemed necessary +*/ class Torrent { public: std::string GetTitle() const { return _title; }; @@ -18,7 +19,7 @@ std::string GetResolution() const { return _resolution; }; int GetSeeders() const { return _seeders; }; int GetLeechers() const { return _leechers; }; - int GetDownloaders() const { return _downloaders; }; + int GetDownloads() const { return _downloads; }; std::string GetDescription() const { return _description; }; std::string GetFilename() const { return _filename; }; std::string GetLink() const { return _link; }; @@ -33,7 +34,7 @@ void SetResolution(const std::string& resolution) { _resolution = resolution; }; void SetSeeders(const int seeders) { _seeders = seeders; }; void SetLeechers(const int leechers) { _leechers = leechers; }; - void SetDownloaders(const int downloaders) { _downloaders = downloaders; }; + void SetDownloads(const int downloads) { _downloads = downloads; }; void SetDescription(const std::string& description) { _description = description; }; void SetFilename(const std::string& filename) { _filename = filename; }; void SetLink(const std::string& link) { _link = link; }; @@ -50,7 +51,7 @@ but std::string is more useful */ int _seeders = 0; int _leechers = 0; - int _downloaders = 0; + int _downloads = 0; std::string _description; std::string _filename; std::string _link;
--- a/include/gui/dialog/settings.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/gui/dialog/settings.h Fri Jan 19 00:24:02 2024 -0500 @@ -7,12 +7,29 @@ #include <QDialog> #include <QWidget> #include <QLocale> +#include <QListWidget> class QLabel; class QTabWidget; class QStackedWidget; class SideBar; +/* !!! MOVE THIS ELSEWHERE! */ +class DroppableListWidget : public QListWidget { + Q_OBJECT + +public: + explicit DroppableListWidget(QWidget* parent); + +signals: + void FilesDropped(QStringList list); + +protected: + void dragEnterEvent(QDragEnterEvent* event) override; + void dragMoveEvent(QDragMoveEvent* event) override; + void dropEvent(QDropEvent* event) override; +}; + class SettingsPage : public QWidget { Q_OBJECT
--- a/include/gui/pages/now_playing.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/gui/pages/now_playing.h Fri Jan 19 00:24:02 2024 -0500 @@ -1,8 +1,13 @@ #ifndef __gui__pages__now_playing_h #define __gui__pages__now_playing_h +#include "gui/widgets/anime_info.h" +#include "gui/widgets/poster.h" +#include "gui/widgets/text.h" + #include <QFrame> #include <unordered_map> +#include <memory> class QStackedWidget; @@ -14,6 +19,35 @@ class Elements; } +namespace NowPlayingPages { + +class Default : public QWidget { + Q_OBJECT + + public: + Default(QWidget* parent = nullptr); +}; + +class Playing : public QWidget { + Q_OBJECT + + public: + Playing(QWidget* parent = nullptr); + void SetPlayingAnime(const Anime::Anime& anime, const anitomy::Elements& info); + int GetPlayingAnime(); + + private: + int _id = 0; + int _episode = 0; + std::unique_ptr<QWidget> _main = nullptr; + std::unique_ptr<TextWidgets::Title> _title = nullptr; + std::unique_ptr<AnimeInfoWidget> _info = nullptr; + std::unique_ptr<QWidget> _sidebar = nullptr; + std::unique_ptr<Poster> _poster = nullptr; +}; + +} + class NowPlayingPage final : public QFrame { Q_OBJECT
--- a/include/gui/pages/torrents.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/gui/pages/torrents.h Fri Jan 19 00:24:02 2024 -0500 @@ -31,7 +31,7 @@ TL_RESOLUTION, TL_SEEDERS, TL_LEECHERS, - TL_DOWNLOADERS, + TL_DOWNLOADS, TL_DESCRIPTION, TL_FILENAME, TL_RELEASEDATE,
--- a/include/gui/window.h Tue Jan 16 15:22:29 2024 -0500 +++ b/include/gui/window.h Fri Jan 19 00:24:02 2024 -0500 @@ -37,7 +37,7 @@ void CreateBars(); void AddMainWidgets(); void RetranslateUI(); - void AsyncSynchronize(QStackedWidget* stack); + void AsyncSynchronize(QAction* action, QStackedWidget* stack); void changeEvent(QEvent* event) override; void showEvent(QShowEvent* event) override; void closeEvent(QCloseEvent* event) override;
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/m4/libcurl.m4 Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,274 @@ +#*************************************************************************** +# _ _ ____ _ +# Project ___| | | | _ \| | +# / __| | | | |_) | | +# | (__| |_| | _ <| |___ +# \___|\___/|_| \_\_____| +# +# Copyright (C) David Shaw <dshaw@jabberwocky.com> +# +# This software is licensed as described in the file COPYING, which +# you should have received as part of this distribution. The terms +# are also available at https://curl.se/docs/copyright.html. +# +# You may opt to use, copy, modify, merge, publish, distribute and/or sell +# copies of the Software, and permit persons to whom the Software is +# furnished to do so, under the terms of the COPYING file. +# +# This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY +# KIND, either express or implied. +# +# SPDX-License-Identifier: curl +# +########################################################################### +# LIBCURL_CHECK_CONFIG ([DEFAULT-ACTION], [MINIMUM-VERSION], +# [ACTION-IF-YES], [ACTION-IF-NO]) +# ---------------------------------------------------------- +# David Shaw <dshaw@jabberwocky.com> May-09-2006 +# +# Checks for libcurl. DEFAULT-ACTION is the string yes or no to +# specify whether to default to --with-libcurl or --without-libcurl. +# If not supplied, DEFAULT-ACTION is yes. MINIMUM-VERSION is the +# minimum version of libcurl to accept. Pass the version as a regular +# version number like 7.10.1. If not supplied, any version is +# accepted. ACTION-IF-YES is a list of shell commands to run if +# libcurl was successfully found and passed the various tests. +# ACTION-IF-NO is a list of shell commands that are run otherwise. +# Note that using --without-libcurl does run ACTION-IF-NO. +# +# This macro #defines HAVE_LIBCURL if a working libcurl setup is +# found, and sets @LIBCURL@ and @LIBCURL_CPPFLAGS@ to the necessary +# values. Other useful defines are LIBCURL_FEATURE_xxx where xxx are +# the various features supported by libcurl, and LIBCURL_PROTOCOL_yyy +# where yyy are the various protocols supported by libcurl. Both xxx +# and yyy are capitalized. See the list of AH_TEMPLATEs at the top of +# the macro for the complete list of possible defines. Shell +# variables $libcurl_feature_xxx and $libcurl_protocol_yyy are also +# defined to 'yes' for those features and protocols that were found. +# Note that xxx and yyy keep the same capitalization as in the +# curl-config list (e.g. it's "HTTP" and not "http"). +# +# Users may override the detected values by doing something like: +# LIBCURL="-lcurl" LIBCURL_CPPFLAGS="-I/usr/myinclude" ./configure +# +# For the sake of sanity, this macro assumes that any libcurl that is found is +# after version 7.7.2, the first version that included the curl-config script. +# Note that it is important for people packaging binary versions of libcurl to +# include this script! Without curl-config, we can only guess what protocols +# are available, or use curl_version_info to figure it out at runtime. + +AC_DEFUN([LIBCURL_CHECK_CONFIG], +[ + AH_TEMPLATE([LIBCURL_FEATURE_SSL],[Defined if libcurl supports SSL]) + AH_TEMPLATE([LIBCURL_FEATURE_KRB4],[Defined if libcurl supports KRB4]) + AH_TEMPLATE([LIBCURL_FEATURE_IPV6],[Defined if libcurl supports IPv6]) + AH_TEMPLATE([LIBCURL_FEATURE_LIBZ],[Defined if libcurl supports libz]) + AH_TEMPLATE([LIBCURL_FEATURE_ASYNCHDNS],[Defined if libcurl supports AsynchDNS]) + AH_TEMPLATE([LIBCURL_FEATURE_IDN],[Defined if libcurl supports IDN]) + AH_TEMPLATE([LIBCURL_FEATURE_SSPI],[Defined if libcurl supports SSPI]) + AH_TEMPLATE([LIBCURL_FEATURE_NTLM],[Defined if libcurl supports NTLM]) + + AH_TEMPLATE([LIBCURL_PROTOCOL_HTTP],[Defined if libcurl supports HTTP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_HTTPS],[Defined if libcurl supports HTTPS]) + AH_TEMPLATE([LIBCURL_PROTOCOL_FTP],[Defined if libcurl supports FTP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_FTPS],[Defined if libcurl supports FTPS]) + AH_TEMPLATE([LIBCURL_PROTOCOL_FILE],[Defined if libcurl supports FILE]) + AH_TEMPLATE([LIBCURL_PROTOCOL_TELNET],[Defined if libcurl supports TELNET]) + AH_TEMPLATE([LIBCURL_PROTOCOL_LDAP],[Defined if libcurl supports LDAP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_DICT],[Defined if libcurl supports DICT]) + AH_TEMPLATE([LIBCURL_PROTOCOL_TFTP],[Defined if libcurl supports TFTP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_RTSP],[Defined if libcurl supports RTSP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_POP3],[Defined if libcurl supports POP3]) + AH_TEMPLATE([LIBCURL_PROTOCOL_IMAP],[Defined if libcurl supports IMAP]) + AH_TEMPLATE([LIBCURL_PROTOCOL_SMTP],[Defined if libcurl supports SMTP]) + + AC_ARG_WITH(libcurl, + AS_HELP_STRING([--with-libcurl=PREFIX],[look for the curl library in PREFIX/lib and headers in PREFIX/include]), + [_libcurl_with=$withval],[_libcurl_with=ifelse([$1],,[yes],[$1])]) + + if test "$_libcurl_with" != "no" ; then + + AC_PROG_AWK + + _libcurl_version_parse="eval $AWK '{split(\$NF,A,\".\"); X=256*256*A[[1]]+256*A[[2]]+A[[3]]; print X;}'" + + _libcurl_try_link=yes + + if test -d "$_libcurl_with" ; then + LIBCURL_CPPFLAGS="-I$withval/include" + _libcurl_ldflags="-L$withval/lib" + AC_PATH_PROG([_libcurl_config],[curl-config],[], + ["$withval/bin"]) + else + AC_PATH_PROG([_libcurl_config],[curl-config],[],[$PATH]) + fi + + if test x$_libcurl_config != "x" ; then + AC_CACHE_CHECK([for the version of libcurl], + [libcurl_cv_lib_curl_version], + [libcurl_cv_lib_curl_version=`$_libcurl_config --version | $AWK '{print $[]2}'`]) + + _libcurl_version=`echo $libcurl_cv_lib_curl_version | $_libcurl_version_parse` + _libcurl_wanted=`echo ifelse([$2],,[0],[$2]) | $_libcurl_version_parse` + + if test $_libcurl_wanted -gt 0 ; then + AC_CACHE_CHECK([for libcurl >= version $2], + [libcurl_cv_lib_version_ok], + [ + if test $_libcurl_version -ge $_libcurl_wanted ; then + libcurl_cv_lib_version_ok=yes + else + libcurl_cv_lib_version_ok=no + fi + ]) + fi + + if test $_libcurl_wanted -eq 0 || test x$libcurl_cv_lib_version_ok = xyes ; then + if test x"$LIBCURL_CPPFLAGS" = "x" ; then + LIBCURL_CPPFLAGS=`$_libcurl_config --cflags` + fi + if test x"$LIBCURL" = "x" ; then + LIBCURL=`$_libcurl_config --libs` + + # This is so silly, but Apple actually has a bug in their + # curl-config script. Fixed in Tiger, but there are still + # lots of Panther installs around. + case "${host}" in + powerpc-apple-darwin7*) + LIBCURL=`echo $LIBCURL | sed -e 's|-arch i386||g'` + ;; + esac + fi + + # All curl-config scripts support --feature + _libcurl_features=`$_libcurl_config --feature` + + # Is it modern enough to have --protocols? (7.12.4) + if test $_libcurl_version -ge 461828 ; then + _libcurl_protocols=`$_libcurl_config --protocols` + fi + else + _libcurl_try_link=no + fi + + unset _libcurl_wanted + fi + + if test $_libcurl_try_link = yes ; then + + # we did not find curl-config, so let's see if the user-supplied + # link line (or failing that, "-lcurl") is enough. + LIBCURL=${LIBCURL-"$_libcurl_ldflags -lcurl"} + + AC_CACHE_CHECK([whether libcurl is usable], + [libcurl_cv_lib_curl_usable], + [ + _libcurl_save_cppflags=$CPPFLAGS + CPPFLAGS="$LIBCURL_CPPFLAGS $CPPFLAGS" + _libcurl_save_libs=$LIBS + LIBS="$LIBCURL $LIBS" + + AC_LINK_IFELSE([AC_LANG_PROGRAM([[#include <curl/curl.h>]],[[ +/* Try and use a few common options to force a failure if we are + missing symbols or cannot link. */ +int x; +curl_easy_setopt(NULL,CURLOPT_URL,NULL); +x=CURL_ERROR_SIZE; +x=CURLOPT_WRITEFUNCTION; +x=CURLOPT_WRITEDATA; +x=CURLOPT_ERRORBUFFER; +x=CURLOPT_STDERR; +x=CURLOPT_VERBOSE; +if (x) {;} +]])],libcurl_cv_lib_curl_usable=yes,libcurl_cv_lib_curl_usable=no) + + CPPFLAGS=$_libcurl_save_cppflags + LIBS=$_libcurl_save_libs + unset _libcurl_save_cppflags + unset _libcurl_save_libs + ]) + + if test $libcurl_cv_lib_curl_usable = yes ; then + + # Does curl_free() exist in this version of libcurl? + # If not, fake it with free() + + _libcurl_save_cppflags=$CPPFLAGS + CPPFLAGS="$CPPFLAGS $LIBCURL_CPPFLAGS" + _libcurl_save_libs=$LIBS + LIBS="$LIBS $LIBCURL" + + AC_CHECK_DECL([curl_free],[], + [AC_DEFINE([curl_free],[free], + [Define curl_free() as free() if our version of curl lacks curl_free.])], + [[#include <curl/curl.h>]]) + + CPPFLAGS=$_libcurl_save_cppflags + LIBS=$_libcurl_save_libs + unset _libcurl_save_cppflags + unset _libcurl_save_libs + + AC_DEFINE(HAVE_LIBCURL,1, + [Define to 1 if you have a functional curl library.]) + AC_SUBST(LIBCURL_CPPFLAGS) + AC_SUBST(LIBCURL) + + for _libcurl_feature in $_libcurl_features ; do + AC_DEFINE_UNQUOTED(AS_TR_CPP(libcurl_feature_$_libcurl_feature),[1]) + eval AS_TR_SH(libcurl_feature_$_libcurl_feature)=yes + done + + if test "x$_libcurl_protocols" = "x" ; then + + # We do not have --protocols, so just assume that all + # protocols are available + _libcurl_protocols="HTTP FTP FILE TELNET LDAP DICT TFTP" + + if test x$libcurl_feature_SSL = xyes ; then + _libcurl_protocols="$_libcurl_protocols HTTPS" + + # FTPS was not standards-compliant until version + # 7.11.0 (0x070b00 == 461568) + if test $_libcurl_version -ge 461568; then + _libcurl_protocols="$_libcurl_protocols FTPS" + fi + fi + + # RTSP, IMAP, POP3 and SMTP were added in + # 7.20.0 (0x071400 == 463872) + if test $_libcurl_version -ge 463872; then + _libcurl_protocols="$_libcurl_protocols RTSP IMAP POP3 SMTP" + fi + fi + + for _libcurl_protocol in $_libcurl_protocols ; do + AC_DEFINE_UNQUOTED(AS_TR_CPP(libcurl_protocol_$_libcurl_protocol),[1]) + eval AS_TR_SH(libcurl_protocol_$_libcurl_protocol)=yes + done + else + unset LIBCURL + unset LIBCURL_CPPFLAGS + fi + fi + + unset _libcurl_try_link + unset _libcurl_version_parse + unset _libcurl_config + unset _libcurl_feature + unset _libcurl_features + unset _libcurl_protocol + unset _libcurl_protocols + unset _libcurl_version + unset _libcurl_ldflags + fi + + if test x$_libcurl_with = xno || test x$libcurl_cv_lib_curl_usable != xyes ; then + # This is the IF-NO path + ifelse([$4],,:,[$4]) + else + # This is the IF-YES path + ifelse([$3],,:,[$3]) + fi + + unset _libcurl_with +])
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/m4/m4_ax_cxx_compile_stdcxx.m4 Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,1018 @@ +# =========================================================================== +# https://www.gnu.org/software/autoconf-archive/ax_cxx_compile_stdcxx.html +# =========================================================================== +# +# SYNOPSIS +# +# AX_CXX_COMPILE_STDCXX(VERSION, [ext|noext], [mandatory|optional]) +# +# DESCRIPTION +# +# Check for baseline language coverage in the compiler for the specified +# version of the C++ standard. If necessary, add switches to CXX and +# CXXCPP to enable support. VERSION may be '11', '14', '17', or '20' for +# the respective C++ standard version. +# +# The second argument, if specified, indicates whether you insist on an +# extended mode (e.g. -std=gnu++11) or a strict conformance mode (e.g. +# -std=c++11). If neither is specified, you get whatever works, with +# preference for no added switch, and then for an extended mode. +# +# The third argument, if specified 'mandatory' or if left unspecified, +# indicates that baseline support for the specified C++ standard is +# required and that the macro should error out if no mode with that +# support is found. If specified 'optional', then configuration proceeds +# regardless, after defining HAVE_CXX${VERSION} if and only if a +# supporting mode is found. +# +# LICENSE +# +# Copyright (c) 2008 Benjamin Kosnik <bkoz@redhat.com> +# Copyright (c) 2012 Zack Weinberg <zackw@panix.com> +# Copyright (c) 2013 Roy Stogner <roystgnr@ices.utexas.edu> +# Copyright (c) 2014, 2015 Google Inc.; contributed by Alexey Sokolov <sokolov@google.com> +# Copyright (c) 2015 Paul Norman <penorman@mac.com> +# Copyright (c) 2015 Moritz Klammler <moritz@klammler.eu> +# Copyright (c) 2016, 2018 Krzesimir Nowak <qdlacz@gmail.com> +# Copyright (c) 2019 Enji Cooper <yaneurabeya@gmail.com> +# Copyright (c) 2020 Jason Merrill <jason@redhat.com> +# Copyright (c) 2021 Jörn Heusipp <osmanx@problemloesungsmaschine.de> +# +# Copying and distribution of this file, with or without modification, are +# permitted in any medium without royalty provided the copyright notice +# and this notice are preserved. This file is offered as-is, without any +# warranty. + +#serial 18 + +dnl This macro is based on the code from the AX_CXX_COMPILE_STDCXX_11 macro +dnl (serial version number 13). + +AC_DEFUN([AX_CXX_COMPILE_STDCXX], [dnl + m4_if([$1], [11], [ax_cxx_compile_alternatives="11 0x"], + [$1], [14], [ax_cxx_compile_alternatives="14 1y"], + [$1], [17], [ax_cxx_compile_alternatives="17 1z"], + [$1], [20], [ax_cxx_compile_alternatives="20"], + [m4_fatal([invalid first argument `$1' to AX_CXX_COMPILE_STDCXX])])dnl + m4_if([$2], [], [], + [$2], [ext], [], + [$2], [noext], [], + [m4_fatal([invalid second argument `$2' to AX_CXX_COMPILE_STDCXX])])dnl + m4_if([$3], [], [ax_cxx_compile_cxx$1_required=true], + [$3], [mandatory], [ax_cxx_compile_cxx$1_required=true], + [$3], [optional], [ax_cxx_compile_cxx$1_required=false], + [m4_fatal([invalid third argument `$3' to AX_CXX_COMPILE_STDCXX])]) + AC_LANG_PUSH([C++])dnl + ac_success=no + + m4_if([$2], [], [dnl + AC_CACHE_CHECK(whether $CXX supports C++$1 features by default, + ax_cv_cxx_compile_cxx$1, + [AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_testbody_$1])], + [ax_cv_cxx_compile_cxx$1=yes], + [ax_cv_cxx_compile_cxx$1=no])]) + if test x$ax_cv_cxx_compile_cxx$1 = xyes; then + ac_success=yes + fi]) + + m4_if([$2], [noext], [], [dnl + if test x$ac_success = xno; then + for alternative in ${ax_cxx_compile_alternatives}; do + switch="-std=gnu++${alternative}" + cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx$1_$switch]) + AC_CACHE_CHECK(whether $CXX supports C++$1 features with $switch, + $cachevar, + [ac_save_CXX="$CXX" + CXX="$CXX $switch" + AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_testbody_$1])], + [eval $cachevar=yes], + [eval $cachevar=no]) + CXX="$ac_save_CXX"]) + if eval test x\$$cachevar = xyes; then + CXX="$CXX $switch" + if test -n "$CXXCPP" ; then + CXXCPP="$CXXCPP $switch" + fi + ac_success=yes + break + fi + done + fi]) + + m4_if([$2], [ext], [], [dnl + if test x$ac_success = xno; then + dnl HP's aCC needs +std=c++11 according to: + dnl http://h21007.www2.hp.com/portal/download/files/unprot/aCxx/PDF_Release_Notes/769149-001.pdf + dnl Cray's crayCC needs "-h std=c++11" + dnl MSVC needs -std:c++NN for C++17 and later (default is C++14) + for alternative in ${ax_cxx_compile_alternatives}; do + for switch in -std=c++${alternative} +std=c++${alternative} "-h std=c++${alternative}" MSVC; do + if test x"$switch" = xMSVC; then + dnl AS_TR_SH maps both `:` and `=` to `_` so -std:c++17 would collide + dnl with -std=c++17. We suffix the cache variable name with _MSVC to + dnl avoid this. + switch=-std:c++${alternative} + cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx$1_${switch}_MSVC]) + else + cachevar=AS_TR_SH([ax_cv_cxx_compile_cxx$1_$switch]) + fi + AC_CACHE_CHECK(whether $CXX supports C++$1 features with $switch, + $cachevar, + [ac_save_CXX="$CXX" + CXX="$CXX $switch" + AC_COMPILE_IFELSE([AC_LANG_SOURCE([_AX_CXX_COMPILE_STDCXX_testbody_$1])], + [eval $cachevar=yes], + [eval $cachevar=no]) + CXX="$ac_save_CXX"]) + if eval test x\$$cachevar = xyes; then + CXX="$CXX $switch" + if test -n "$CXXCPP" ; then + CXXCPP="$CXXCPP $switch" + fi + ac_success=yes + break + fi + done + if test x$ac_success = xyes; then + break + fi + done + fi]) + AC_LANG_POP([C++]) + if test x$ax_cxx_compile_cxx$1_required = xtrue; then + if test x$ac_success = xno; then + AC_MSG_ERROR([*** A compiler with support for C++$1 language features is required.]) + fi + fi + if test x$ac_success = xno; then + HAVE_CXX$1=0 + AC_MSG_NOTICE([No compiler with C++$1 support was found]) + else + HAVE_CXX$1=1 + AC_DEFINE(HAVE_CXX$1,1, + [define if the compiler supports basic C++$1 syntax]) + fi + AC_SUBST(HAVE_CXX$1) +]) + + +dnl Test body for checking C++11 support + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_11], + _AX_CXX_COMPILE_STDCXX_testbody_new_in_11 +) + +dnl Test body for checking C++14 support + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_14], + _AX_CXX_COMPILE_STDCXX_testbody_new_in_11 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_14 +) + +dnl Test body for checking C++17 support + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_17], + _AX_CXX_COMPILE_STDCXX_testbody_new_in_11 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_14 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_17 +) + +dnl Test body for checking C++20 support + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_20], + _AX_CXX_COMPILE_STDCXX_testbody_new_in_11 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_14 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_17 + _AX_CXX_COMPILE_STDCXX_testbody_new_in_20 +) + + +dnl Tests for new features in C++11 + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_11], [[ + +// If the compiler admits that it is not ready for C++11, why torture it? +// Hopefully, this will speed up the test. + +#ifndef __cplusplus + +#error "This is not a C++ compiler" + +// MSVC always sets __cplusplus to 199711L in older versions; newer versions +// only set it correctly if /Zc:__cplusplus is specified as well as a +// /std:c++NN switch: +// https://devblogs.microsoft.com/cppblog/msvc-now-correctly-reports-__cplusplus/ +#elif __cplusplus < 201103L && !defined _MSC_VER + +#error "This is not a C++11 compiler" + +#else + +namespace cxx11 +{ + + namespace test_static_assert + { + + template <typename T> + struct check + { + static_assert(sizeof(int) <= sizeof(T), "not big enough"); + }; + + } + + namespace test_final_override + { + + struct Base + { + virtual ~Base() {} + virtual void f() {} + }; + + struct Derived : public Base + { + virtual ~Derived() override {} + virtual void f() override {} + }; + + } + + namespace test_double_right_angle_brackets + { + + template < typename T > + struct check {}; + + typedef check<void> single_type; + typedef check<check<void>> double_type; + typedef check<check<check<void>>> triple_type; + typedef check<check<check<check<void>>>> quadruple_type; + + } + + namespace test_decltype + { + + int + f() + { + int a = 1; + decltype(a) b = 2; + return a + b; + } + + } + + namespace test_type_deduction + { + + template < typename T1, typename T2 > + struct is_same + { + static const bool value = false; + }; + + template < typename T > + struct is_same<T, T> + { + static const bool value = true; + }; + + template < typename T1, typename T2 > + auto + add(T1 a1, T2 a2) -> decltype(a1 + a2) + { + return a1 + a2; + } + + int + test(const int c, volatile int v) + { + static_assert(is_same<int, decltype(0)>::value == true, ""); + static_assert(is_same<int, decltype(c)>::value == false, ""); + static_assert(is_same<int, decltype(v)>::value == false, ""); + auto ac = c; + auto av = v; + auto sumi = ac + av + 'x'; + auto sumf = ac + av + 1.0; + static_assert(is_same<int, decltype(ac)>::value == true, ""); + static_assert(is_same<int, decltype(av)>::value == true, ""); + static_assert(is_same<int, decltype(sumi)>::value == true, ""); + static_assert(is_same<int, decltype(sumf)>::value == false, ""); + static_assert(is_same<int, decltype(add(c, v))>::value == true, ""); + return (sumf > 0.0) ? sumi : add(c, v); + } + + } + + namespace test_noexcept + { + + int f() { return 0; } + int g() noexcept { return 0; } + + static_assert(noexcept(f()) == false, ""); + static_assert(noexcept(g()) == true, ""); + + } + + namespace test_constexpr + { + + template < typename CharT > + unsigned long constexpr + strlen_c_r(const CharT *const s, const unsigned long acc) noexcept + { + return *s ? strlen_c_r(s + 1, acc + 1) : acc; + } + + template < typename CharT > + unsigned long constexpr + strlen_c(const CharT *const s) noexcept + { + return strlen_c_r(s, 0UL); + } + + static_assert(strlen_c("") == 0UL, ""); + static_assert(strlen_c("1") == 1UL, ""); + static_assert(strlen_c("example") == 7UL, ""); + static_assert(strlen_c("another\0example") == 7UL, ""); + + } + + namespace test_rvalue_references + { + + template < int N > + struct answer + { + static constexpr int value = N; + }; + + answer<1> f(int&) { return answer<1>(); } + answer<2> f(const int&) { return answer<2>(); } + answer<3> f(int&&) { return answer<3>(); } + + void + test() + { + int i = 0; + const int c = 0; + static_assert(decltype(f(i))::value == 1, ""); + static_assert(decltype(f(c))::value == 2, ""); + static_assert(decltype(f(0))::value == 3, ""); + } + + } + + namespace test_uniform_initialization + { + + struct test + { + static const int zero {}; + static const int one {1}; + }; + + static_assert(test::zero == 0, ""); + static_assert(test::one == 1, ""); + + } + + namespace test_lambdas + { + + void + test1() + { + auto lambda1 = [](){}; + auto lambda2 = lambda1; + lambda1(); + lambda2(); + } + + int + test2() + { + auto a = [](int i, int j){ return i + j; }(1, 2); + auto b = []() -> int { return '0'; }(); + auto c = [=](){ return a + b; }(); + auto d = [&](){ return c; }(); + auto e = [a, &b](int x) mutable { + const auto identity = [](int y){ return y; }; + for (auto i = 0; i < a; ++i) + a += b--; + return x + identity(a + b); + }(0); + return a + b + c + d + e; + } + + int + test3() + { + const auto nullary = [](){ return 0; }; + const auto unary = [](int x){ return x; }; + using nullary_t = decltype(nullary); + using unary_t = decltype(unary); + const auto higher1st = [](nullary_t f){ return f(); }; + const auto higher2nd = [unary](nullary_t f1){ + return [unary, f1](unary_t f2){ return f2(unary(f1())); }; + }; + return higher1st(nullary) + higher2nd(nullary)(unary); + } + + } + + namespace test_variadic_templates + { + + template <int...> + struct sum; + + template <int N0, int... N1toN> + struct sum<N0, N1toN...> + { + static constexpr auto value = N0 + sum<N1toN...>::value; + }; + + template <> + struct sum<> + { + static constexpr auto value = 0; + }; + + static_assert(sum<>::value == 0, ""); + static_assert(sum<1>::value == 1, ""); + static_assert(sum<23>::value == 23, ""); + static_assert(sum<1, 2>::value == 3, ""); + static_assert(sum<5, 5, 11>::value == 21, ""); + static_assert(sum<2, 3, 5, 7, 11, 13>::value == 41, ""); + + } + + // http://stackoverflow.com/questions/13728184/template-aliases-and-sfinae + // Clang 3.1 fails with headers of libstd++ 4.8.3 when using std::function + // because of this. + namespace test_template_alias_sfinae + { + + struct foo {}; + + template<typename T> + using member = typename T::member_type; + + template<typename T> + void func(...) {} + + template<typename T> + void func(member<T>*) {} + + void test(); + + void test() { func<foo>(0); } + + } + +} // namespace cxx11 + +#endif // __cplusplus >= 201103L + +]]) + + +dnl Tests for new features in C++14 + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_14], [[ + +// If the compiler admits that it is not ready for C++14, why torture it? +// Hopefully, this will speed up the test. + +#ifndef __cplusplus + +#error "This is not a C++ compiler" + +#elif __cplusplus < 201402L && !defined _MSC_VER + +#error "This is not a C++14 compiler" + +#else + +namespace cxx14 +{ + + namespace test_polymorphic_lambdas + { + + int + test() + { + const auto lambda = [](auto&&... args){ + const auto istiny = [](auto x){ + return (sizeof(x) == 1UL) ? 1 : 0; + }; + const int aretiny[] = { istiny(args)... }; + return aretiny[0]; + }; + return lambda(1, 1L, 1.0f, '1'); + } + + } + + namespace test_binary_literals + { + + constexpr auto ivii = 0b0000000000101010; + static_assert(ivii == 42, "wrong value"); + + } + + namespace test_generalized_constexpr + { + + template < typename CharT > + constexpr unsigned long + strlen_c(const CharT *const s) noexcept + { + auto length = 0UL; + for (auto p = s; *p; ++p) + ++length; + return length; + } + + static_assert(strlen_c("") == 0UL, ""); + static_assert(strlen_c("x") == 1UL, ""); + static_assert(strlen_c("test") == 4UL, ""); + static_assert(strlen_c("another\0test") == 7UL, ""); + + } + + namespace test_lambda_init_capture + { + + int + test() + { + auto x = 0; + const auto lambda1 = [a = x](int b){ return a + b; }; + const auto lambda2 = [a = lambda1(x)](){ return a; }; + return lambda2(); + } + + } + + namespace test_digit_separators + { + + constexpr auto ten_million = 100'000'000; + static_assert(ten_million == 100000000, ""); + + } + + namespace test_return_type_deduction + { + + auto f(int& x) { return x; } + decltype(auto) g(int& x) { return x; } + + template < typename T1, typename T2 > + struct is_same + { + static constexpr auto value = false; + }; + + template < typename T > + struct is_same<T, T> + { + static constexpr auto value = true; + }; + + int + test() + { + auto x = 0; + static_assert(is_same<int, decltype(f(x))>::value, ""); + static_assert(is_same<int&, decltype(g(x))>::value, ""); + return x; + } + + } + +} // namespace cxx14 + +#endif // __cplusplus >= 201402L + +]]) + + +dnl Tests for new features in C++17 + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_17], [[ + +// If the compiler admits that it is not ready for C++17, why torture it? +// Hopefully, this will speed up the test. + +#ifndef __cplusplus + +#error "This is not a C++ compiler" + +#elif __cplusplus < 201703L && !defined _MSC_VER + +#error "This is not a C++17 compiler" + +#else + +#include <initializer_list> +#include <utility> +#include <type_traits> + +namespace cxx17 +{ + + namespace test_constexpr_lambdas + { + + constexpr int foo = [](){return 42;}(); + + } + + namespace test::nested_namespace::definitions + { + + } + + namespace test_fold_expression + { + + template<typename... Args> + int multiply(Args... args) + { + return (args * ... * 1); + } + + template<typename... Args> + bool all(Args... args) + { + return (args && ...); + } + + } + + namespace test_extended_static_assert + { + + static_assert (true); + + } + + namespace test_auto_brace_init_list + { + + auto foo = {5}; + auto bar {5}; + + static_assert(std::is_same<std::initializer_list<int>, decltype(foo)>::value); + static_assert(std::is_same<int, decltype(bar)>::value); + } + + namespace test_typename_in_template_template_parameter + { + + template<template<typename> typename X> struct D; + + } + + namespace test_fallthrough_nodiscard_maybe_unused_attributes + { + + int f1() + { + return 42; + } + + [[nodiscard]] int f2() + { + [[maybe_unused]] auto unused = f1(); + + switch (f1()) + { + case 17: + f1(); + [[fallthrough]]; + case 42: + f1(); + } + return f1(); + } + + } + + namespace test_extended_aggregate_initialization + { + + struct base1 + { + int b1, b2 = 42; + }; + + struct base2 + { + base2() { + b3 = 42; + } + int b3; + }; + + struct derived : base1, base2 + { + int d; + }; + + derived d1 {{1, 2}, {}, 4}; // full initialization + derived d2 {{}, {}, 4}; // value-initialized bases + + } + + namespace test_general_range_based_for_loop + { + + struct iter + { + int i; + + int& operator* () + { + return i; + } + + const int& operator* () const + { + return i; + } + + iter& operator++() + { + ++i; + return *this; + } + }; + + struct sentinel + { + int i; + }; + + bool operator== (const iter& i, const sentinel& s) + { + return i.i == s.i; + } + + bool operator!= (const iter& i, const sentinel& s) + { + return !(i == s); + } + + struct range + { + iter begin() const + { + return {0}; + } + + sentinel end() const + { + return {5}; + } + }; + + void f() + { + range r {}; + + for (auto i : r) + { + [[maybe_unused]] auto v = i; + } + } + + } + + namespace test_lambda_capture_asterisk_this_by_value + { + + struct t + { + int i; + int foo() + { + return [*this]() + { + return i; + }(); + } + }; + + } + + namespace test_enum_class_construction + { + + enum class byte : unsigned char + {}; + + byte foo {42}; + + } + + namespace test_constexpr_if + { + + template <bool cond> + int f () + { + if constexpr(cond) + { + return 13; + } + else + { + return 42; + } + } + + } + + namespace test_selection_statement_with_initializer + { + + int f() + { + return 13; + } + + int f2() + { + if (auto i = f(); i > 0) + { + return 3; + } + + switch (auto i = f(); i + 4) + { + case 17: + return 2; + + default: + return 1; + } + } + + } + + namespace test_template_argument_deduction_for_class_templates + { + + template <typename T1, typename T2> + struct pair + { + pair (T1 p1, T2 p2) + : m1 {p1}, + m2 {p2} + {} + + T1 m1; + T2 m2; + }; + + void f() + { + [[maybe_unused]] auto p = pair{13, 42u}; + } + + } + + namespace test_non_type_auto_template_parameters + { + + template <auto n> + struct B + {}; + + B<5> b1; + B<'a'> b2; + + } + + namespace test_structured_bindings + { + + int arr[2] = { 1, 2 }; + std::pair<int, int> pr = { 1, 2 }; + + auto f1() -> int(&)[2] + { + return arr; + } + + auto f2() -> std::pair<int, int>& + { + return pr; + } + + struct S + { + int x1 : 2; + volatile double y1; + }; + + S f3() + { + return {}; + } + + auto [ x1, y1 ] = f1(); + auto& [ xr1, yr1 ] = f1(); + auto [ x2, y2 ] = f2(); + auto& [ xr2, yr2 ] = f2(); + const auto [ x3, y3 ] = f3(); + + } + + namespace test_exception_spec_type_system + { + + struct Good {}; + struct Bad {}; + + void g1() noexcept; + void g2(); + + template<typename T> + Bad + f(T*, T*); + + template<typename T1, typename T2> + Good + f(T1*, T2*); + + static_assert (std::is_same_v<Good, decltype(f(g1, g2))>); + + } + + namespace test_inline_variables + { + + template<class T> void f(T) + {} + + template<class T> inline T g(T) + { + return T{}; + } + + template<> inline void f<>(int) + {} + + template<> int g<>(int) + { + return 5; + } + + } + +} // namespace cxx17 + +#endif // __cplusplus < 201703L && !defined _MSC_VER + +]]) + + +dnl Tests for new features in C++20 + +m4_define([_AX_CXX_COMPILE_STDCXX_testbody_new_in_20], [[ + +#ifndef __cplusplus + +#error "This is not a C++ compiler" + +#elif __cplusplus < 202002L && !defined _MSC_VER + +#error "This is not a C++20 compiler" + +#else + +#include <version> + +namespace cxx20 +{ + +// As C++20 supports feature test macros in the standard, there is no +// immediate need to actually test for feature availability on the +// Autoconf side. + +} // namespace cxx20 + +#endif // __cplusplus < 202002L && !defined _MSC_VER + +]])
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/m4/m4_ax_have_qt.m4 Fri Jan 19 00:24:02 2024 -0500 @@ -0,0 +1,246 @@ +# =========================================================================== +# https://www.gnu.org/software/autoconf-archive/ax_have_qt.html +# =========================================================================== +# +# SYNOPSIS +# +# AX_HAVE_QT +# +# DESCRIPTION +# +# Searches $PATH and queries qmake for Qt include files, libraries and Qt +# binary utilities. The macro only supports Qt5 or later. +# +# The following shell variable is set to either "yes" or "no": +# +# have_qt +# +# Additionally, the following variables are exported: +# +# QT_CXXFLAGS +# QT_LIBS +# QT_MOC +# QT_UIC +# QT_RCC +# QT_LRELEASE +# QT_LUPDATE +# QT_DIR +# QMAKE +# +# which respectively contain an "-I" flag pointing to the Qt include +# directory, link flags necessary to link with Qt and X, the full path to +# the meta object compiler and the user interface compiler both, and +# finally the variable QTDIR as Qt likes to see it defined. +# +# Example lines for Makefile.in: +# +# CXXFLAGS = @QT_CXXFLAGS@ +# MOC = @QT_MOC@ +# +# After the variables have been set, a trial compile and link is performed +# to check the correct functioning of the meta object compiler. This test +# may fail when the different detected elements stem from different +# releases of the Qt framework. In that case, an error message is emitted +# and configure stops. +# +# No common variables such as $LIBS or $CFLAGS are polluted. +# +# LICENSE +# +# Copyright (c) 2008 Bastiaan Veelo <Bastiaan@Veelo.net> +# Copyright (c) 2014 Alex Henrie <alexhenrie24@gmail.com> +# +# Copying and distribution of this file, with or without modification, are +# permitted in any medium without royalty provided the copyright notice +# and this notice are preserved. This file is offered as-is, without any +# warranty. + +#serial 25 + +AU_ALIAS([BNV_HAVE_QT], [AX_HAVE_QT]) +AC_DEFUN([AX_HAVE_QT], +[ + AC_REQUIRE([AC_PROG_CXX]) + AC_REQUIRE([AC_PATH_X]) + AC_REQUIRE([AC_PATH_XTRA]) + # openSUSE leap 15.3 installs qmake-qt5, not qmake, for example. + # Store the full name (like qmake-qt5) into QMAKE + # and the specifier (like -qt5 or empty) into am_have_qt_qmexe_suff. + AC_ARG_VAR([QMAKE],"Qt make tool") + AC_CHECK_TOOLS([QMAKE],[qmake qmake-qt6 qmake-qt5],[false]) + + AC_MSG_CHECKING(for Qt) + am_have_qt_qmexe_suff=`echo $QMAKE | sed 's,^.*qmake,,'` + # If we have Qt5 or later in the path, we're golden + ver=`$QMAKE --version | grep -o "Qt version ."` + + if test "$ver" ">" "Qt version 4"; then + have_qt=yes + # This pro file dumps qmake's variables, but it only works on Qt 5 or later + am_have_qt_dir=`mktemp -d` + am_have_qt_pro="$am_have_qt_dir/test.pro" + am_have_qt_stash="$am_have_qt_dir/.qmake.stash" + am_have_qt_makefile="$am_have_qt_dir/Makefile" + # http://qt-project.org/doc/qt-5/qmake-variable-reference.html#qt + cat > $am_have_qt_pro << EOF +win32 { + CONFIG -= debug_and_release + CONFIG += release +} +qtHaveModule(axcontainer): QT += axcontainer +qtHaveModule(axserver): QT += axserver +qtHaveModule(concurrent): QT += concurrent +qtHaveModule(core): QT += core +qtHaveModule(dbus): QT += dbus +qtHaveModule(declarative): QT += declarative +qtHaveModule(designer): QT += designer +qtHaveModule(gui): QT += gui +qtHaveModule(help): QT += help +qtHaveModule(multimedia): QT += multimedia +qtHaveModule(multimediawidgets): QT += multimediawidgets +qtHaveModule(network): QT += network +qtHaveModule(opengl): QT += opengl +qtHaveModule(printsupport): QT += printsupport +qtHaveModule(qml): QT += qml +qtHaveModule(qmltest): QT += qmltest +qtHaveModule(x11extras): QT += x11extras +qtHaveModule(script): QT += script +qtHaveModule(scripttools): QT += scripttools +qtHaveModule(sensors): QT += sensors +qtHaveModule(serialport): QT += serialport +qtHaveModule(sql): QT += sql +qtHaveModule(svg): QT += svg +qtHaveModule(testlib): QT += testlib +qtHaveModule(uitools): QT += uitools +qtHaveModule(webkit): QT += webkit +qtHaveModule(webkitwidgets): QT += webkitwidgets +qtHaveModule(xml): QT += xml +qtHaveModule(xmlpatterns): QT += xmlpatterns +percent.target = % +percent.commands = @echo -n "\$(\$(@))\ " +QMAKE_EXTRA_TARGETS += percent +EOF + $QMAKE $am_have_qt_pro -o $am_have_qt_makefile + QT_CXXFLAGS=`cd $am_have_qt_dir; make -s -f $am_have_qt_makefile CXXFLAGS INCPATH` + QT_LIBS=`cd $am_have_qt_dir; make -s -f $am_have_qt_makefile LIBS` + rm $am_have_qt_pro $am_have_qt_stash $am_have_qt_makefile + rmdir $am_have_qt_dir + + # Look for specific tools in $PATH + QT_MOC=`which moc$am_have_qt_qmexe_suff` + QT_UIC=`which uic$am_have_qt_qmexe_suff` + QT_RCC=`which rcc$am_have_qt_qmexe_suff` + QT_LRELEASE=`which lrelease$am_have_qt_qmexe_suff` + QT_LUPDATE=`which lupdate$am_have_qt_qmexe_suff` + + # Get Qt version from qmake + QT_DIR=`$QMAKE --version | grep -o -E /.+` + + # All variables are defined, report the result + AC_MSG_RESULT([$have_qt: + QT_CXXFLAGS=$QT_CXXFLAGS + QT_DIR=$QT_DIR + QT_LIBS=$QT_LIBS + QT_UIC=$QT_UIC + QT_MOC=$QT_MOC + QT_RCC=$QT_RCC + QT_LRELEASE=$QT_LRELEASE + QT_LUPDATE=$QT_LUPDATE]) + else + # Qt was not found + have_qt=no + QT_CXXFLAGS= + QT_DIR= + QT_LIBS= + QT_UIC= + QT_MOC= + QT_RCC= + QT_LRELEASE= + QT_LUPDATE= + AC_MSG_RESULT($have_qt) + fi + AC_SUBST(QT_CXXFLAGS) + AC_SUBST(QT_DIR) + AC_SUBST(QT_LIBS) + AC_SUBST(QT_UIC) + AC_SUBST(QT_MOC) + AC_SUBST(QT_RCC) + AC_SUBST(QT_LRELEASE) + AC_SUBST(QT_LUPDATE) + AC_SUBST(QMAKE) + + #### Being paranoid: + if test x"$have_qt" = xyes; then + AC_MSG_CHECKING(correct functioning of Qt installation) + AC_CACHE_VAL(ax_cv_qt_test_result, + [ + cat > ax_qt_test.h << EOF +#include <qobject.h> +class Test : public QObject +{ +Q_OBJECT +public: + Test() {} + ~Test() {} +public slots: + void receive() {} +signals: + void send(); +}; +EOF + + cat > ax_qt_main.$ac_ext << EOF +#include "ax_qt_test.h" +#include <qapplication.h> +int main( int argc, char **argv ) +{ + QApplication app( argc, argv ); + Test t; + QObject::connect( &t, SIGNAL(send()), &t, SLOT(receive()) ); +} +EOF + + ax_cv_qt_test_result="failure" + ax_try_1="$QT_MOC ax_qt_test.h -o moc_ax_qt_test.$ac_ext >/dev/null 2>/dev/null" + AC_TRY_EVAL(ax_try_1) + if test x"$ac_status" != x0; then + echo "$ax_err_1" >&AS_MESSAGE_LOG_FD + echo "configure: could not run $QT_MOC on:" >&AS_MESSAGE_LOG_FD + cat ax_qt_test.h >&AS_MESSAGE_LOG_FD + else + ax_try_2="$CXX $QT_CXXFLAGS -c $CXXFLAGS -o moc_ax_qt_test.o moc_ax_qt_test.$ac_ext >/dev/null 2>/dev/null" + AC_TRY_EVAL(ax_try_2) + if test x"$ac_status" != x0; then + echo "$ax_err_2" >&AS_MESSAGE_LOG_FD + echo "configure: could not compile:" >&AS_MESSAGE_LOG_FD + cat moc_ax_qt_test.$ac_ext >&AS_MESSAGE_LOG_FD + else + ax_try_3="$CXX $QT_CXXFLAGS -c $CXXFLAGS -o ax_qt_main.o ax_qt_main.$ac_ext >/dev/null 2>/dev/null" + AC_TRY_EVAL(ax_try_3) + if test x"$ac_status" != x0; then + echo "$ax_err_3" >&AS_MESSAGE_LOG_FD + echo "configure: could not compile:" >&AS_MESSAGE_LOG_FD + cat ax_qt_main.$ac_ext >&AS_MESSAGE_LOG_FD + else + ax_try_4="$CXX -o ax_qt_main ax_qt_main.o moc_ax_qt_test.o $QT_LIBS $LIBS >/dev/null 2>/dev/null" + AC_TRY_EVAL(ax_try_4) + if test x"$ac_status" != x0; then + echo "$ax_err_4" >&AS_MESSAGE_LOG_FD + else + ax_cv_qt_test_result="success" + fi + fi + fi + fi + ])dnl AC_CACHE_VAL ax_cv_qt_test_result + AC_MSG_RESULT([$ax_cv_qt_test_result]) + if test x"$ax_cv_qt_test_result" = "xfailure"; then + AC_MSG_ERROR([Failed to find matching components of a complete + Qt installation. Try using more options, + see ./configure --help.]) + fi + + rm -f ax_qt_test.h moc_ax_qt_test.$ac_ext moc_ax_qt_test.o \ + ax_qt_main.$ac_ext ax_qt_main.o ax_qt_main + fi +])
--- a/rc/win32/version.rc.in Tue Jan 16 15:22:29 2024 -0500 +++ b/rc/win32/version.rc.in Fri Jan 19 00:24:02 2024 -0500 @@ -1,16 +1,14 @@ #include "winver.h" -#define VER_FILEVERSION @minori_VERSION_MAJOR@,@minori_VERSION_MINOR@,@minori_VERSION_PATCH@,0 -#define VER_FILEVERSION_STR "@minori_VERSION_MAJOR@.@minori_VERSION_MINOR@.@minori_VERSION_PATCH@.0\0" - -#define VER_PRODUCTVERSION @minori_VERSION_MAJOR@,@minori_VERSION_MINOR@,@minori_VERSION_PATCH@,0 -#define VER_PRODUCTVERSION_STR "@minori_VERSION_MAJOR@.@minori_VERSION_MINOR@.@minori_VERSION_PATCH@\0" +#ifndef WRC_VERSION +# define WRC_VERSION 0,0,0,0 +#endif #define RC_INFO_STRING "@RC_INFO_STRING@\0" VS_VERSION_INFO VERSIONINFO - FILEVERSION VER_FILEVERSION - PRODUCTVERSION VER_PRODUCTVERSION + FILEVERSION WRC_VERSION + PRODUCTVERSION WRC_VERSION FILEFLAGS 0x0L FILEFLAGSMASK 0x3fL FILEOS 0x00040004L
--- a/src/core/anime_db.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/core/anime_db.cc Fri Jan 19 00:24:02 2024 -0500 @@ -145,7 +145,8 @@ std::unordered_map<int, size_t> map; static const auto process_title = [&map](const Anime& anime, const std::string& title, const std::string& needle) -> bool { - size_t ret = title.find(needle); + const std::string title_l = Strings::ToLower(title), needle_l = Strings::ToLower(needle); + size_t ret = title_l.find(needle_l); if (ret == std::string::npos) return false;
--- a/src/core/http.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/core/http.cc Fri Jan 19 00:24:02 2024 -0500 @@ -65,5 +65,3 @@ } } // namespace HTTP - -#include "core/moc_http.cpp"
--- a/src/gui/dialog/about.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/dialog/about.cc Fri Jan 19 00:24:02 2024 -0500 @@ -107,5 +107,3 @@ win32::SetTitleBarsToBlack(session.config.theme.IsInDarkTheme()); #endif } - -#include "gui/dialog/moc_about.cpp"
--- a/src/gui/dialog/information.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/dialog/information.cc Fri Jan 19 00:24:02 2024 -0500 @@ -307,5 +307,3 @@ win32::SetTitleBarsToBlack(session.config.theme.IsInDarkTheme()); #endif } - -#include "gui/dialog/moc_information.cpp"
--- a/src/gui/dialog/settings.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/dialog/settings.cc Fri Jan 19 00:24:02 2024 -0500 @@ -131,5 +131,3 @@ full_layout->addWidget(button_box); } } - -#include "gui/dialog/moc_settings.cpp"
--- a/src/gui/dialog/settings/library.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/dialog/settings/library.cc Fri Jan 19 00:24:02 2024 -0500 @@ -19,21 +19,6 @@ #include <algorithm> #include <iostream> -class DroppableListWidget : public QListWidget { - Q_OBJECT - -public: - explicit DroppableListWidget(QWidget* parent); - -signals: - void FilesDropped(QStringList list); - -protected: - void dragEnterEvent(QDragEnterEvent* event) override; - void dragMoveEvent(QDragMoveEvent* event) override; - void dropEvent(QDropEvent* event) override; -}; - DroppableListWidget::DroppableListWidget(QWidget* parent) : QListWidget(parent) { setAcceptDrops(true); } @@ -129,9 +114,11 @@ QDir::homePath(), QFileDialog::ShowDirsOnly | QFileDialog::DontResolveSymlinks); - if (dir.isEmpty()) + const std::string s_dir = Strings::ToUtf8String(dir); + if (dir.isEmpty() || paths.count(s_dir)) return; - paths.insert(Strings::ToUtf8String(dir)); + + paths.insert(s_dir); QListWidgetItem* item = new QListWidgetItem(listwidget); item->setText(dir); }); @@ -202,5 +189,3 @@ real_time_monitor = session.config.library.real_time_monitor; AddTab(CreateFoldersWidget(), tr("Folder")); } - -#include "gui/dialog/settings/library.moc"
--- a/src/gui/pages/anime_list.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/anime_list.cc Fri Jan 19 00:24:02 2024 -0500 @@ -455,8 +455,21 @@ sort_models[i]->setSortRole(Qt::UserRole); sort_models[i]->setSortCaseSensitivity(Qt::CaseInsensitive); } + tree_view->setModel(sort_models[0]); + /* Set column widths */ + tree_view->setColumnWidth(AnimeListPageModel::AL_TITLE, 300); + tree_view->setColumnWidth(AnimeListPageModel::AL_PROGRESS, 200); + tree_view->setColumnWidth(AnimeListPageModel::AL_SCORE, 50); + tree_view->setColumnWidth(AnimeListPageModel::AL_AVG_SCORE, 55); + tree_view->setColumnWidth(AnimeListPageModel::AL_TYPE, 65); + tree_view->setColumnWidth(AnimeListPageModel::AL_SEASON, 95); + tree_view->setColumnWidth(AnimeListPageModel::AL_STARTED, 90); + tree_view->setColumnWidth(AnimeListPageModel::AL_COMPLETED, 90); + tree_view->setColumnWidth(AnimeListPageModel::AL_UPDATED, 100); + tree_view->setColumnWidth(AnimeListPageModel::AL_NOTES, 100); + QHBoxLayout* layout = new QHBoxLayout(tree_widget); layout->addWidget(tree_view); layout->setContentsMargins(0, 0, 0, 0); @@ -487,5 +500,3 @@ Refresh(); } - -#include "gui/pages/moc_anime_list.cpp"
--- a/src/gui/pages/history.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/history.cc Fri Jan 19 00:24:02 2024 -0500 @@ -2,5 +2,3 @@ HistoryPage::HistoryPage(QWidget* parent) : QWidget(parent) { } - -#include "gui/pages/moc_history.cpp"
--- a/src/gui/pages/now_playing.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/now_playing.cc Fri Jan 19 00:24:02 2024 -0500 @@ -15,31 +15,6 @@ namespace NowPlayingPages { -class Default : public QWidget { - Q_OBJECT - - public: - Default(QWidget* parent = nullptr); -}; - -class Playing : public QWidget { - Q_OBJECT - - public: - Playing(QWidget* parent = nullptr); - void SetPlayingAnime(const Anime::Anime& anime, const anitomy::Elements& info); - int GetPlayingAnime(); - - private: - int _id = 0; - int _episode = 0; - std::unique_ptr<QWidget> _main = nullptr; - std::unique_ptr<TextWidgets::Title> _title = nullptr; - std::unique_ptr<AnimeInfoWidget> _info = nullptr; - std::unique_ptr<QWidget> _sidebar = nullptr; - std::unique_ptr<Poster> _poster = nullptr; -}; - Default::Default(QWidget* parent) : QWidget(parent) { QVBoxLayout* layout = new QVBoxLayout(this); layout->setContentsMargins(0, 0, 0, 0); @@ -129,6 +104,3 @@ stack->setCurrentIndex(1); updateGeometry(); } - -#include "gui/pages/moc_now_playing.cpp" -#include "now_playing.moc"
--- a/src/gui/pages/search.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/search.cc Fri Jan 19 00:24:02 2024 -0500 @@ -2,5 +2,3 @@ SearchPage::SearchPage(QWidget* parent) : QWidget(parent) { } - -#include "gui/pages/moc_search.cpp"
--- a/src/gui/pages/seasons.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/seasons.cc Fri Jan 19 00:24:02 2024 -0500 @@ -2,5 +2,3 @@ SeasonsPage::SeasonsPage(QWidget* parent) : QWidget(parent) { } - -#include "gui/pages/moc_seasons.cpp"
--- a/src/gui/pages/statistics.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/statistics.cc Fri Jan 19 00:24:02 2024 -0500 @@ -148,5 +148,3 @@ // UiUtils::SetPlainTextEditData(application_data, QString::number(session.uptime() / 1000)); _application->GetParagraph()->SetText(string); } - -#include "gui/pages/moc_statistics.cpp"
--- a/src/gui/pages/torrents.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/pages/torrents.cc Fri Jan 19 00:24:02 2024 -0500 @@ -63,14 +63,19 @@ const std::filesystem::path torrents_dir = Filesystem::GetTorrentsPath(); std::filesystem::create_directories(torrents_dir); - std::ofstream file(torrents_dir / filename, std::ofstream::out | std::ofstream::trunc); - if (!file) - return; // wat + HTTP::GetThread* thread = new HTTP::GetThread(link, {}, this); + + connect(thread, &HTTP::GetThread::ReceivedData, this, [this, torrents_dir, filename](const QByteArray& data) { + std::ofstream file(torrents_dir / filename, std::ofstream::out | std::ofstream::trunc); + if (!file) + return; // wat - const QByteArray data = HTTP::Get(link); - file.write(data.data(), data.size()); + file.write(data.data(), data.size()); + file.close(); + }); + connect(thread, &HTTP::GetThread::finished, thread, &HTTP::GetThread::deleteLater); - file.close(); + thread->start(); } } @@ -186,10 +191,10 @@ case TL_EPISODE: return tr("Episode"); case TL_GROUP: return tr("Group"); case TL_SIZE: return tr("Size"); - case TL_RESOLUTION: return tr("Resolution"); /* this is named "Video" in Taiga */ - case TL_SEEDERS: return tr("Seeding"); /* named "S" in Taiga */ - case TL_LEECHERS: return tr("Leeching"); /* named "L" in Taiga */ - case TL_DOWNLOADERS: return tr("Downloading"); /* named "D" in Taiga */ + case TL_RESOLUTION: return tr("Resolution"); /* "Video" in Taiga */ + case TL_SEEDERS: return tr("S"); + case TL_LEECHERS: return tr("L"); + case TL_DOWNLOADS: return tr("D"); case TL_DESCRIPTION: return tr("Description"); case TL_FILENAME: return tr("Filename"); case TL_RELEASEDATE: return tr("Release date"); @@ -206,7 +211,7 @@ case TL_TITLE: return QVariant(Qt::AlignLeft | Qt::AlignVCenter); case TL_SEEDERS: case TL_LEECHERS: - case TL_DOWNLOADERS: + case TL_DOWNLOADS: case TL_SIZE: case TL_EPISODE: case TL_RELEASEDATE: return QVariant(Qt::AlignRight | Qt::AlignVCenter); @@ -251,7 +256,7 @@ case TL_RESOLUTION: return Strings::ToQString(item.GetResolution()); case TL_SEEDERS: return item.GetSeeders(); case TL_LEECHERS: return item.GetLeechers(); - case TL_DOWNLOADERS: return item.GetDownloaders(); + case TL_DOWNLOADS: return item.GetDownloads(); case TL_DESCRIPTION: return Strings::ToQString(item.GetDescription()); case TL_FILENAME: return Strings::ToQString(item.GetFilename()); case TL_RELEASEDATE: return item.GetDate(); @@ -289,7 +294,7 @@ case TL_TITLE: return QVariant(Qt::AlignLeft | Qt::AlignVCenter); case TL_SEEDERS: case TL_LEECHERS: - case TL_DOWNLOADERS: + case TL_DOWNLOADS: case TL_SIZE: case TL_EPISODE: case TL_RELEASEDATE: return QVariant(Qt::AlignRight | Qt::AlignVCenter); @@ -380,29 +385,30 @@ treeview->setModel(sort_model); } + // set column sizes + treeview->setColumnWidth(TorrentsPageListModel::TL_TITLE, 240); + treeview->setColumnWidth(TorrentsPageListModel::TL_EPISODE, 60); + treeview->setColumnWidth(TorrentsPageListModel::TL_GROUP, 100); + treeview->setColumnWidth(TorrentsPageListModel::TL_SIZE, 70); + treeview->setColumnWidth(TorrentsPageListModel::TL_RESOLUTION, 100); + treeview->setColumnWidth(TorrentsPageListModel::TL_SEEDERS, 20); + treeview->setColumnWidth(TorrentsPageListModel::TL_LEECHERS, 20); + treeview->setColumnWidth(TorrentsPageListModel::TL_DOWNLOADS, 20); + treeview->setColumnWidth(TorrentsPageListModel::TL_DESCRIPTION, 200); + treeview->setColumnWidth(TorrentsPageListModel::TL_FILENAME, 200); + treeview->setColumnWidth(TorrentsPageListModel::TL_RELEASEDATE, 190); + layout->addWidget(treeview); } } void TorrentsPage::DownloadSelection() { - /* we only want one of these at a time, because if we don't - * we have the possibility of going into Multithreading Hell - */ - static QThread* thread = nullptr; - - if (!model || thread) + if (!model) return; const QItemSelection selection = sort_model->mapSelectionToSource(treeview->selectionModel()->selection()); - thread = QThread::create([this, selection] { - model->DownloadTorrents(selection); - }); - - connect(thread, &QThread::finished, thread, &QThread::deleteLater); - connect(thread, &QThread::finished, this, [&] { thread = nullptr; }); - - thread->start(); + model->DownloadTorrents(selection); } void TorrentsPage::Refresh() { @@ -423,5 +429,3 @@ thread->start(); } - -#include "gui/pages/moc_torrents.cpp"
--- a/src/gui/theme.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/theme.cc Fri Jan 19 00:24:02 2024 -0500 @@ -133,10 +133,6 @@ #ifdef WIN32 /* fuck you Qt 6 */ pal.setColor(QPalette::Window, QColor(0xF0, 0xF0, 0xF0)); #endif - pal.setColor(QPalette::WindowText, Qt::black); - pal.setColor(QPalette::ToolTipText, Qt::black); - pal.setColor(QPalette::Text, Qt::black); - pal.setColor(QPalette::ButtonText, Qt::black); qApp->setPalette(pal); qApp->setStyleSheet("");
--- a/src/gui/widgets/anime_info.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/anime_info.cc Fri Jan 19 00:24:02 2024 -0500 @@ -48,5 +48,3 @@ updateGeometry(); } - -#include "gui/widgets/moc_anime_info.cpp"
--- a/src/gui/widgets/clickable_label.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/clickable_label.cc Fri Jan 19 00:24:02 2024 -0500 @@ -12,5 +12,3 @@ void ClickableLabel::mousePressEvent(QMouseEvent*) { emit clicked(); } - -#include "gui/widgets/moc_clickable_label.cpp"
--- a/src/gui/widgets/optional_date.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/optional_date.cc Fri Jan 19 00:24:02 2024 -0500 @@ -62,5 +62,3 @@ QCheckBox* OptionalDate::GetCheckBox() { return _checkbox; } - -#include "gui/widgets/moc_optional_date.cpp"
--- a/src/gui/widgets/poster.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/poster.cc Fri Jan 19 00:24:02 2024 -0500 @@ -36,16 +36,10 @@ void Poster::SetAnime(const Anime::Anime& anime) { { - QByteArray* ba = new QByteArray; + HTTP::GetThread* thread = new HTTP::GetThread(anime.GetPosterUrl(), {}, this); - QThread* thread = QThread::create([ba, anime] { - *ba = HTTP::Get(anime.GetPosterUrl(), {}); - }); - - connect(thread, &QThread::finished, this, [this, ba] { - ImageDownloadFinished(*ba); - delete ba; - }); + connect(thread, &HTTP::GetThread::ReceivedData, this, &Poster::ImageDownloadFinished); + connect(thread, &HTTP::GetThread::finished, thread, &HTTP::GetThread::deleteLater); thread->start(); } @@ -70,5 +64,3 @@ void Poster::resizeEvent(QResizeEvent*) { RenderToLabel(); } - -#include "gui/widgets/moc_poster.cpp"
--- a/src/gui/widgets/sidebar.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/sidebar.cc Fri Jan 19 00:24:02 2024 -0500 @@ -101,5 +101,3 @@ unsetCursor(); QListView::mouseMoveEvent(event); } - -#include "gui/widgets/moc_sidebar.cpp"
--- a/src/gui/widgets/text.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/widgets/text.cc Fri Jan 19 00:24:02 2024 -0500 @@ -248,5 +248,3 @@ } } // namespace TextWidgets - -#include "gui/widgets/moc_text.cpp"
--- a/src/gui/window.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/gui/window.cc Fri Jan 19 00:24:02 2024 -0500 @@ -93,8 +93,10 @@ anitomy.Parse(Strings::ToWstring(file)); const auto& elements = anitomy.elements(); + const std::string title = Strings::ToUtf8String(elements.get(anitomy::kElementAnimeTitle)); + std::cout << title << std::endl; - int id = Anime::db.GetAnimeFromTitle(Strings::ToUtf8String(elements.get(anitomy::kElementAnimeTitle))); + int id = Anime::db.GetAnimeFromTitle(title); if (id <= 0) continue; @@ -160,6 +162,7 @@ void MainWindow::CreateBars() { QMenuBar* menubar = new QMenuBar(this); QMenu* folder_menu; /* this is used twice, so we declare it here */ + QAction* sync_action; { /* File */ @@ -231,8 +234,14 @@ QMenu* menu = menubar->addMenu(tr("&Services")); { { - QAction* action = menu->addAction(tr("Synchronize &list"), [this] { AsyncSynchronize(stack.get()); }); - action->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_S)); + sync_action = menu->addAction(tr("Synchronize &list")); + + connect(sync_action, &QAction::triggered, this, [this, sync_action]{ + AsyncSynchronize(sync_action, stack.get()); + }); + + sync_action->setIcon(QIcon(":/icons/24x24/arrow-circle-double-135.png")); + sync_action->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_S)); } // menu->addSeparator(); @@ -300,6 +309,7 @@ QAction* action = menu->addAction(tr("&Settings"), [this] { SettingsDialog dialog(this); dialog.exec(); + CreateBars(); }); action->setMenuRole(QAction::PreferencesRole); } @@ -408,8 +418,7 @@ { /* Toolbar */ QToolBar* toolbar = new QToolBar(this); - toolbar->addAction(QIcon(":/icons/24x24/arrow-circle-double-135.png"), tr("&Synchronize"), - [this] { AsyncSynchronize(stack.get()); }); + toolbar->addAction(sync_action); toolbar->addSeparator(); @@ -465,6 +474,7 @@ toolbar->addAction(QIcon(":/icons/24x24/gear.png"), tr("S&ettings"), [this] { SettingsDialog dialog(this); dialog.exec(); + CreateBars(); }); addToolBar(toolbar); } @@ -474,7 +484,7 @@ this->setCentralWidget(page); } -void MainWindow::AsyncSynchronize(QStackedWidget* stack) { +void MainWindow::AsyncSynchronize(QAction* action, QStackedWidget* stack) { if (session.config.service == Anime::Services::NONE) { QMessageBox msg; msg.setWindowTitle(tr("Error synchronizing with service!")); @@ -488,9 +498,12 @@ dialog.exec(); } } - QThreadPool::globalInstance()->start([stack] { + + QThreadPool::globalInstance()->start([stack, action] { + action->setEnabled(false); Services::Synchronize(); reinterpret_cast<AnimeListPage*>(stack->widget(static_cast<int>(Pages::ANIME_LIST)))->Refresh(); + action->setEnabled(true); }); } @@ -534,5 +547,3 @@ Anime::db.SaveDatabaseToDisk(); event->accept(); } - -#include "gui/moc_window.cpp"
--- a/src/main.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/main.cc Fri Jan 19 00:24:02 2024 -0500 @@ -1,19 +1,19 @@ #include "core/session.h" #include "core/anime_db.h" +#include "core/strings.h" #include "gui/window.h" #include <QApplication> #include <QStyleFactory> #include <QTranslator> #include <QLocale> +#include <iostream> + Session session; int main(int argc, char** argv) { QApplication app(argc, argv); -#if !(defined(WIN32) || defined(MACOSX)) - /* force Fusion */ - app.setStyle("Fusion"); -#endif + app.setAttribute(Qt::AA_DontShowIconsInMenus, true); session.config.Load(); session.config.locale.RefreshAvailableLocales();
--- a/src/sys/glib/dark_theme.cc Tue Jan 16 15:22:29 2024 -0500 +++ b/src/sys/glib/dark_theme.cc Fri Jan 19 00:24:02 2024 -0500 @@ -6,24 +6,24 @@ namespace glib { bool IsInDarkTheme() { - GSettings* settings = g_settings_new("org.gnome.desktop.interface"); + GSettings* settings = ::g_settings_new("org.gnome.desktop.interface"); if (!settings) return false; - GVariant* val = g_settings_get_value(settings, "color-scheme"); + GVariant* val = ::g_settings_get_value(settings, "color-scheme"); if (!val) return false; const gchar* str; - g_variant_get(val, "&s", &str); /* should not be freed */ + ::g_variant_get(val, "&s", &str); /* should not be freed */ if (!str) /* how */ return false; bool success = !std::strcmp(str, "prefer-dark"); /* unref these */ - g_variant_unref(val); - g_object_unref(settings); + ::g_variant_unref(val); + ::g_object_unref(settings); return success; }