diff --git a/.gitmodules b/.gitmodules
index 6cbf29c..5d1e6f4 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -1,3 +1,7 @@
+[submodule "third-party/doxygen-awesome-css"]
+ path = third-party/doxygen-awesome-css
+ url = https://github.com/jothepro/doxygen-awesome-css.git
+ branch = main
[submodule "third-party/googletest"]
path = third-party/googletest
url = https://github.com/google/googletest.git
diff --git a/.readthedocs.yaml b/.readthedocs.yaml
new file mode 100644
index 0000000..75bed11
--- /dev/null
+++ b/.readthedocs.yaml
@@ -0,0 +1,32 @@
+---
+# .readthedocs.yaml
+# Read the Docs configuration file
+# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details
+
+version: 2
+
+build:
+ os: ubuntu-24.04
+ tools:
+ python: "miniconda-latest"
+ commands:
+ # because we are overriding the build commands, we need to setup the environment ourselves
+ - cat docs/environment.yml
+ - conda env create --quiet --name ${READTHEDOCS_VERSION} --file docs/environment.yml
+ - mkdir -p ${READTHEDOCS_OUTPUT}
+ - |
+ wget "https://raw.githubusercontent.com/LizardByte/.github/master/branding/logos/favicon.ico" \
+ -O ${READTHEDOCS_OUTPUT}lizardbyte.ico
+ - |
+ wget "https://raw.githubusercontent.com/LizardByte/.github/master/branding/logos/logo-128x128.png" \
+ -O ${READTHEDOCS_OUTPUT}lizardbyte.png
+ - cd docs && doxygen Doxyfile
+
+# using conda, we can get newer doxygen and graphviz than ubuntu provide
+# https://github.com/readthedocs/readthedocs.org/issues/8151#issuecomment-890359661
+conda:
+ environment: docs/environment.yml
+
+submodules:
+ include: all
+ recursive: true
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 1df79fe..e13e7a3 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -1,8 +1,11 @@
+#
+# Project configuration
+#
cmake_minimum_required(VERSION 3.13 FATAL_ERROR) # target_link_directories
-
-project(tray
- LANGUAGES C
- DESCRIPTION "A cross-platform system tray library")
+project(tray VERSION 0.0.0
+ DESCRIPTION "A cross-platform system tray library"
+ HOMEPAGE_URL "https://app.lizardbyte.dev"
+ LANGUAGES C)
set(PROJECT_LICENSE "MIT")
@@ -11,11 +14,22 @@ if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
set(CMAKE_BUILD_TYPE "Release" CACHE STRING "Choose the type of build." FORCE)
endif()
+# Add our custom CMake modules to the global path
set(CMAKE_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake")
-# options
+#
+# Project optional configuration
+#
+option(BUILD_DOCS "Build documentation" ON)
option(BUILD_TESTS "Build tests" ON)
+#
+# Documentation
+#
+if(BUILD_DOCS)
+ add_subdirectory(docs)
+endif()
+
# Generate 'compile_commands.json' for clang_complete
set(CMAKE_COLOR_MAKEFILE ON)
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
diff --git a/README.md b/README.md
index 7359deb..a5c5769 100644
--- a/README.md
+++ b/README.md
@@ -1,44 +1,70 @@
-# Cross-platform Linux/macOS/Windows Tray
+# Overview
-[![codecov](https://img.shields.io/codecov/c/gh/LizardByte/tray?token=HSX66JNEOL&style=for-the-badge&logo=codecov&label=codecov)](https://codecov.io/gh/LizardByte/tray)
+[![GitHub Workflow Status (CI)](https://img.shields.io/github/actions/workflow/status/lizardbyte/tray/ci.yml.svg?branch=master&label=CI%20build&logo=github&style=for-the-badge)](https://github.com/LizardByte/tray/actions/workflows/ci.yml?query=branch%3Amaster)
+[![Codecov](https://img.shields.io/codecov/c/gh/LizardByte/tray?token=HSX66JNEOL&style=for-the-badge&logo=codecov&label=codecov)](https://codecov.io/gh/LizardByte/tray)
+[![GitHub stars](https://img.shields.io/github/stars/lizardbyte/tray.svg?logo=github&style=for-the-badge)](https://github.com/LizardByte/tray)
-
+## About
-
+Cross-platform, super tiny C99 implementation of a system tray icon with a popup menu and notifications.
-
+The code is C++ friendly and will compile fine in C++98 and up. This is a fork of
+[dmikushin/tray](https://github.com/dmikushin/tray) and is intended to add additional features required for our own
+[Sunshine](https://github.com/LizardByte/Sunshine) project.
-Cross-platform, super tiny C99 implementation of a system tray icon with a popup menu.
+This fork adds the following features:
-Works well on:
+- system tray notifications
+- support for both linux appindicator versions
+- unit tests
+- code coverage
+- refactored code, e.g. moved source code into the `src` directory
+- doxygen documentation, and readthedocs configuration
+
+## Screenshots
+
+
+
+## Supported platforms
* Linux/Gtk (libayatana-appindicator3 or libappindicator3)
* Windows XP or newer (shellapi.h)
* MacOS (Cocoa/AppKit)
-The code is C++ friendly and will compile fine in C++98 and up.
+## Prerequisites
+
+* CMake
+* [Ninja](https://ninja-build.org/), in order to have the same build commands on all platforms
-This fork is intended to bring together the [original work of Serge Zaitsev](https://github.com/zserge/tray) and the most interesting forks and PRs of respectable contributors:
+### Linux Dependencies
-* [Only process messages coming from the tray window on Windows](https://github.com/zserge/tray/pull/18)
-* [Become C++-friendly](https://github.com/zserge/tray/pull/16)
-* [Fix all menu items have a check box](https://github.com/zserge/tray/pull/11)
-* [Add support for tooltip](https://github.com/zserge/tray/pull/11)
-* Darwin implementation translated from C to Objective C adapted from [@trevex fork](https://github.com/trevex/tray)
+
-## Prerequisites
+- Arch
+ ```bash
+ sudo pacman -S libayatana-appindicator
+ ```
-* CMake
-* [Ninja](https://ninja-build.org/), in order to have the same build commands on all platforms
-* AppIndicator on Linux:
+- Debian/Ubuntu
+ ```bash
+ sudo apt install libappindicator3-dev
+ ```
-```
-sudo apt install libappindicator3-dev
-```
+- Fedora
+ ```bash
+ sudo dnf install libappindicator-gtk3-devel
+ ```
+
## Building
-```
+```bash
mkdir build
cd build
cmake -G Ninja ..
@@ -49,7 +75,7 @@ ninja
Execute the `tray_example` application:
-```
+```bash
./tray_example
```
@@ -91,4 +117,4 @@ array must have text field set to NULL.
## License
This software is distributed under [MIT license](http://www.opensource.org/licenses/mit-license.php),
- so feel free to integrate it in your commercial products.
+so feel free to integrate it in your commercial products.
diff --git a/docs/CMakeLists.txt b/docs/CMakeLists.txt
new file mode 100644
index 0000000..7f93e1d
--- /dev/null
+++ b/docs/CMakeLists.txt
@@ -0,0 +1,41 @@
+# find doxygen and graphviz
+find_package(Doxygen
+ REQUIRED dot)
+
+# define variables based on whether we are building on readthedocs
+if(DEFINED ENV{READTHEDOCS})
+ set(DOXYGEN_BUILD_DIR_CMAKE $ENV{READTHEDOCS_OUTPUT})
+ set(DOXYGEN_PROJECT_VERSION $ENV{READTHEDOCS_VERSION})
+else()
+ set(DOXYGEN_BUILD_DIR_CMAKE "${CMAKE_CURRENT_BINARY_DIR}/build")
+ set(DOXYGEN_PROJECT_VERSION ${PROJECT_VERSION})
+endif()
+message(STATUS "DOXYGEN_BUILD_DIR_CMAKE: ${DOXYGEN_BUILD_DIR_CMAKE}")
+
+# download icon and logo
+file(DOWNLOAD
+ "https://raw.githubusercontent.com/LizardByte/.github/master/branding/logos/favicon.ico"
+ "${DOXYGEN_BUILD_DIR_CMAKE}/lizardbyte.ico"
+)
+file(DOWNLOAD
+ "https://raw.githubusercontent.com/LizardByte/.github/master/branding/logos/logo-128x128.png"
+ "${DOXYGEN_BUILD_DIR_CMAKE}/lizardbyte.png"
+)
+
+# create build directories, as doxygen fails to create it in some cases?
+file(MAKE_DIRECTORY "${DOXYGEN_BUILD_DIR_CMAKE}/html")
+
+# convert to relative path, so doxygen doesn't get confused on Windows
+file(RELATIVE_PATH DOXYGEN_BUILD_DIR_RELATIVE "${CMAKE_CURRENT_SOURCE_DIR}" "${DOXYGEN_BUILD_DIR_CMAKE}")
+message(STATUS "DOXYGEN_BUILD_DIR_RELATIVE: ${DOXYGEN_BUILD_DIR_RELATIVE}")
+
+# build docs
+add_custom_target(docs ALL
+ WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}"
+ COMMENT "Building Doxygen documentation"
+ COMMAND ${CMAKE_COMMAND} -E env
+ READTHEDOCS_OUTPUT=${DOXYGEN_BUILD_DIR_RELATIVE}
+ READTHEDOCS_VERSION=${DOXYGEN_PROJECT_VERSION}
+ ${DOXYGEN_EXECUTABLE} Doxyfile
+ VERBATIM
+)
diff --git a/docs/Doxyfile b/docs/Doxyfile
new file mode 100644
index 0000000..bea85df
--- /dev/null
+++ b/docs/Doxyfile
@@ -0,0 +1,111 @@
+# This file describes the settings to be used by the documentation system
+# doxygen (www.doxygen.org) for a project.
+#
+# All text after a double hash (##) is considered a comment and is placed in
+# front of the TAG it is preceding.
+#
+# All text after a single hash (#) is considered a comment and will be ignored.
+# The format is:
+# TAG = value [value, ...]
+# For lists, items can also be appended using:
+# TAG += value [value, ...]
+# Values that contain spaces should be placed between quotes (\" \").
+#
+# Note:
+#
+# Use doxygen to compare the used configuration file with the template
+# configuration file:
+# doxygen -x [configFile]
+# Use doxygen to compare the used configuration file with the template
+# configuration file without replacing the environment variables or CMake type
+# replacement variables:
+# doxygen -x_noenv [configFile]
+
+# must be first
+DOXYFILE_ENCODING = UTF-8
+
+# project metadata
+DOCSET_BUNDLE_ID = dev.lizardbyte.tray
+DOCSET_PUBLISHER_ID = dev.lizardbyte.tray.documentation
+DOCSET_PUBLISHER_NAME = LizardByte
+PROJECT_BRIEF = "Cross-platform, super tiny C99 implementation of a system tray icon with a popup menu and notifications."
+PROJECT_ICON = $(READTHEDOCS_OUTPUT)/lizardbyte.ico
+PROJECT_LOGO = $(READTHEDOCS_OUTPUT)/lizardbyte.png
+PROJECT_NAME = tray
+
+# project specific settings
+DOT_GRAPH_MAX_NODES = 50
+IMAGE_PATH = ../docs/images
+INCLUDE_PATH =
+PREDEFINED = DOXYGEN
+PREDEFINED += __APPLE__
+PREDEFINED += linux
+PREDEFINED += __linux
+PREDEFINED += __linux__
+PREDEFINED += __MACH__
+PREDEFINED += _WIN32
+
+# TODO: Enable this when we have complete documentation
+WARN_IF_UNDOCUMENTED = NO
+
+# files and directories to process
+INPUT = ../README.md \
+ ../src
+
+#
+# Common LizardByte settings
+#
+
+# doxygen-awesome-css
+HTML_COLORSTYLE = LIGHT # required with Doxygen >= 1.9.5
+HTML_COPY_CLIPBOARD = NO # required for Doxygen >= 1.10.0
+HTML_EXTRA_FILES = ../third-party/doxygen-awesome-css/doxygen-awesome-darkmode-toggle.js
+HTML_EXTRA_FILES += ../third-party/doxygen-awesome-css/doxygen-awesome-fragment-copy-button.js
+HTML_EXTRA_FILES += ../third-party/doxygen-awesome-css/doxygen-awesome-paragraph-link.js
+HTML_EXTRA_FILES += ../third-party/doxygen-awesome-css/doxygen-awesome-interactive-toc.js
+HTML_EXTRA_STYLESHEET = ../third-party/doxygen-awesome-css/doxygen-awesome.css
+HTML_HEADER = header.html
+
+# custom aliases
+ALIASES = ""
+ALIASES += "examples=^^**Examples**^^@code{.cpp}"
+ALIASES += "examples_end=@endcode^^"
+ALIASES += "rst=^^\verbatim embed:rst:leading-asterisk^^"
+ALIASES += "rst_end=\endverbatim"
+
+# general settings
+CASE_SENSE_NAMES = YES
+CREATE_SUBDIRS = NO
+DISABLE_INDEX = NO
+DOCBOOK_OUTPUT = docbook
+DOT_IMAGE_FORMAT = svg
+DOT_NUM_THREADS = 1
+EXTRACT_ALL = NO
+FULL_SIDEBAR = NO
+GENERATE_HTML = YES
+GENERATE_LATEX = NO
+GENERATE_TREEVIEW = YES
+GENERATE_XML = NO
+HAVE_DOT = YES
+HTML_OUTPUT = html
+INTERACTIVE_SVG = YES
+LATEX_OUTPUT = latex
+MACRO_EXPANSION = YES
+MAN_OUTPUT = man
+MARKDOWN_ID_STYLE = GITHUB
+MARKDOWN_SUPPORT = YES
+NUM_PROC_THREADS = 1
+PROJECT_NUMBER = $(READTHEDOCS_VERSION)
+OUTPUT_DIRECTORY = $(READTHEDOCS_OUTPUT)
+RECURSIVE = YES
+RTF_OUTPUT = rtf
+SORT_BRIEF_DOCS = YES
+STRIP_FROM_INC_PATH = ../
+STRIP_FROM_PATH = ../
+WARN_AS_ERROR = FAIL_ON_WARNINGS
+WARN_IF_DOC_ERROR = YES
+WARN_IF_INCOMPLETE_DOC = YES
+WARN_IF_UNDOC_ENUM_VAL = YES
+WARN_NO_PARAMDOC = YES
+WARNINGS = YES
+XML_OUTPUT = xml
diff --git a/docs/environment.yml b/docs/environment.yml
new file mode 100644
index 0000000..8670795
--- /dev/null
+++ b/docs/environment.yml
@@ -0,0 +1,8 @@
+---
+name: RTD
+channels:
+ - conda-forge
+ - defaults
+dependencies:
+ - doxygen=1.10.0
+ - graphviz=11.0.0
diff --git a/docs/header.html b/docs/header.html
new file mode 100644
index 0000000..849a882
--- /dev/null
+++ b/docs/header.html
@@ -0,0 +1,99 @@
+
+
+
+
+
+
+
+
+$projectname: $title
+$title
+
+
+
+
+
+
+
+
+
+
+$treeview
+$search
+$mathjax
+$darkmode
+
+$extrastylesheet
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
$projectname $projectnumber
+
+
$projectbrief
+
+
+
+
+
+
$projectbrief
+
+
+
+
+
+
+
$searchbox
+
+
+
+
+
+
+
$searchbox
+
+
+
+
+
+
+
diff --git a/docs/images/screenshot_macosx.png b/docs/images/screenshot_macos.png
similarity index 100%
rename from docs/images/screenshot_macosx.png
rename to docs/images/screenshot_macos.png
diff --git a/src/example.c b/src/example.c
index 9d7958d..16f817b 100644
--- a/src/example.c
+++ b/src/example.c
@@ -1,3 +1,7 @@
+/**
+ * @file src/example.c
+ * @brief Example usage of the tray library.
+ */
#include
#include
diff --git a/src/tray.h b/src/tray.h
index c94854e..fd3166d 100644
--- a/src/tray.h
+++ b/src/tray.h
@@ -1,3 +1,7 @@
+/**
+ * @file src/tray.h
+ * @brief Definition of the tray API.
+ */
#ifndef TRAY_H
#define TRAY_H
diff --git a/src/tray_darwin.m b/src/tray_darwin.m
index 9865bd6..2327ae3 100644
--- a/src/tray_darwin.m
+++ b/src/tray_darwin.m
@@ -1,7 +1,16 @@
+/**
+ * @file src/tray_darwin.m
+ * @brief System tray implementation for macOS.
+ */
+// header include
#include "tray.h"
-#include
+
+// system includes
#include
+// lib includes
+#include
+
@interface AppDelegate: NSObject
- (IBAction)menuCallback:(id)sender;
@end
diff --git a/src/tray_linux.c b/src/tray_linux.c
index 7faa3a2..969c17d 100644
--- a/src/tray_linux.c
+++ b/src/tray_linux.c
@@ -1,7 +1,16 @@
+/**
+ * @file src/tray_linux.c
+ * @brief System tray implementation for Linux.
+ */
+// header include
#include "tray.h"
+
+// system includes
#include
#include
#include
+
+// lib includes
#ifdef TRAY_AYATANA_APPINDICATOR
#include
#elif TRAY_LEGACY_APPINDICATOR
@@ -10,7 +19,6 @@
#ifndef IS_APP_INDICATOR
#define IS_APP_INDICATOR APP_IS_INDICATOR
#endif
-
#include
#define TRAY_APPINDICATOR_ID "tray-id"
diff --git a/src/tray_windows.c b/src/tray_windows.c
index cf92da7..c5c269c 100644
--- a/src/tray_windows.c
+++ b/src/tray_windows.c
@@ -1,6 +1,13 @@
+/**
+ * @file src/tray_windows.c
+ * @brief System tray implementation for Windows.
+ */
+// header include
+#include "tray.h"
+
+// system includes
#include
#include
-#include "tray.h"
#define WM_TRAY_CALLBACK_MESSAGE (WM_USER + 1)
#define WC_TRAY_CLASS_NAME "TRAY"
@@ -14,9 +21,9 @@ struct icon_info {
};
enum IconType {
- REGULAR = 1,
- LARGE,
- NOTIFICATION
+ REGULAR = 1, ///< Regular icon
+ LARGE, ///< Large icon
+ NOTIFICATION ///< Notification icon
};
static WNDCLASSEX wc;
diff --git a/third-party/doxygen-awesome-css b/third-party/doxygen-awesome-css
new file mode 160000
index 0000000..40e9b25
--- /dev/null
+++ b/third-party/doxygen-awesome-css
@@ -0,0 +1 @@
+Subproject commit 40e9b25b6174dd3b472d8868f63323a870dfeeb8