Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add fullscreen bypass support #808

Open
wants to merge 8 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -50,9 +50,10 @@ Dependencies

* autotools, gettext
* intltool, libtool
* libX11
* libdrm (Optional, for DRM support)
* libxcb, libxcb-randr (Optional, for RandR support)
* libX11, libXxf86vm (Optional, for VidMode support)
* libXxf86vm (Optional, for VidMode support)
* Glib 2 (Optional, for GeoClue2 support)

* python3, pygobject, pyxdg (Optional, for GUI support)
Expand Down
1 change: 1 addition & 0 deletions po/POTFILES.in
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ data/applications/redshift-gtk.desktop.in
src/redshift.c
src/options.c
src/config-ini.c
src/fullscreen.c

src/gamma-drm.c
src/gamma-randr.c
Expand Down
3 changes: 2 additions & 1 deletion src/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,8 @@ redshift_SOURCES = \
redshift.c redshift.h \
signals.c signals.h \
solar.c solar.h \
systemtime.c systemtime.h
systemtime.c systemtime.h \
fullscreen.c fullscreen.h

EXTRA_redshift_SOURCES = \
gamma-drm.c gamma-drm.h \
Expand Down
96 changes: 96 additions & 0 deletions src/fullscreen.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
/* fullscreen.h -- Fullscreen detector
This file is part of Redshift.

Redshift is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

Redshift is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with Redshift. If not, see <http://www.gnu.org/licenses/>.

Copyright (c) 2021 Angelo Elias Dalzotto <angelodalzotto97@gmail.com>
*/

#ifdef HAVE_CONFIG_H
# include "config.h"
#endif

#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <string.h>

#ifdef ENABLE_NLS
# include <libintl.h>
# define _(s) gettext(s)
#else
# define _(s) s
#endif

#ifndef _WIN32
# include <X11/Xlib.h>
#endif

#include "fullscreen.h"
#include "redshift.h"

#ifndef _WIN32
static Display *display;
static int screen_width, screen_height;
#endif

static int
fullscreen_init()
{
#ifndef _WIN32
screen_height = -1;
screen_width = -1;
display = XOpenDisplay(NULL);
if (display == NULL) {
fprintf(stderr, _("X request failed: %s\n"), "XOpenDisplay");
return -1;
}

int screen = DefaultScreen(display);
screen_width = DisplayWidth(display, screen);
screen_height = DisplayHeight(display, screen);
#endif

return 0;
}

static int
fullscreen_check()
{
#ifndef _WIN32
Window window;
int revert_to = RevertToParent;
int result = XGetInputFocus(display, &window, &revert_to);

int win_x, win_y, win_w, win_h, win_b, win_d;
if(result) {
Window rootWindow;
result = XGetGeometry(display, window, &rootWindow, &win_x, &win_y, &win_w, &win_h, &win_b, &win_d);
}

if (result && win_w == screen_width && win_h == screen_height) {
return 1;
} else {
#endif
return 0;
#ifndef _WIN32
}
#endif
}

const fullscreen_t fullscreen = {
"fullscreen",
(fullscreen_init_func *)fullscreen_init,
(fullscreen_check_func *)fullscreen_check,
};
28 changes: 28 additions & 0 deletions src/fullscreen.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/* fullscreen.h -- Fullscreen detector header
This file is part of Redshift.

Redshift is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.

Redshift is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with Redshift. If not, see <http://www.gnu.org/licenses/>.

Copyright (c) 2021 Angelo Elias Dalzotto <angelodalzotto97@gmail.com>
*/

#ifndef REDSHIFT_FULLSCREEN_H
#define REDSHIFT_FULLSCREEN_H

#include "redshift.h"

extern const fullscreen_t fullscreen;

#endif /* ! REDSHIFT_FULLSCREEN_H */

7 changes: 6 additions & 1 deletion src/options.c
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,7 @@ print_help(const char *program_name)
no-wrap */
fputs(_(" -b DAY:NIGHT\tScreen brightness to apply (between 0.1 and 1.0)\n"
" -c FILE\tLoad settings from specified configuration file\n"
" -f BOOL\tEnable or disable fullscreen windows bypass\n"
" -g R:G:B\tAdditional gamma correction to apply\n"
" -l LAT:LON\tYour current location\n"
" -l PROVIDER\tSelect provider for automatic"
Expand Down Expand Up @@ -323,6 +324,7 @@ options_init(options_t *options)
options->preserve_gamma = 1;
options->mode = PROGRAM_MODE_CONTINUAL;
options->verbose = 0;
options->fullscreen_check = 1;
}

/* Parse a single option from the command-line. */
Expand All @@ -345,6 +347,9 @@ parse_command_line_option(
free(options->config_filepath);
options->config_filepath = strdup(value);
break;
case 'f':
options->fullscreen_check = atoi(value);
break;
case 'g':
r = parse_gamma_string(value, options->scheme.day.gamma);
if (r < 0) {
Expand Down Expand Up @@ -495,7 +500,7 @@ options_parse_args(
{
const char* program_name = argv[0];
int opt;
while ((opt = getopt(argc, argv, "b:c:g:hl:m:oO:pPrt:vVx")) != -1) {
while ((opt = getopt(argc, argv, "b:c:f:g:hl:m:oO:pPrt:vVx")) != -1) {
char option = opt;
int r = parse_command_line_option(
option, optarg, options, program_name, gamma_methods,
Expand Down
1 change: 1 addition & 0 deletions src/options.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ typedef struct {
transition_scheme_t scheme;
program_mode_t mode;
int verbose;
int fullscreen_check;

/* Temperature to set in manual mode. */
int temp_set;
Expand Down
30 changes: 26 additions & 4 deletions src/redshift.c
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ int poll(struct pollfd *fds, int nfds, int timeout) { abort(); return -1; }
#include "hooks.h"
#include "signals.h"
#include "options.h"
#include "fullscreen.h"

/* pause() is not defined on windows platform but is not needed either.
Use a noop macro instead. */
Expand Down Expand Up @@ -608,7 +609,7 @@ run_continual_mode(const location_provider_t *provider,
const transition_scheme_t *scheme,
const gamma_method_t *method,
gamma_state_t *method_state,
int use_fade, int preserve_gamma, int verbose)
int use_fade, int preserve_gamma, int fullscreen_check, int verbose)
{
int r;

Expand Down Expand Up @@ -662,18 +663,31 @@ run_continual_mode(const location_provider_t *provider,
printf(_("Brightness: %.2f\n"), interp.brightness);
}

if (fullscreen_check) {
fullscreen.init();
}

/* Continuously adjust color temperature */
int done = 0;
int prev_disabled = 1;
int disabled = 0;
int location_available = 1;
int prev_fullscreen = 0;
int is_fullscreen = 0;
int fs_disabled = 0;
while (1) {
/* Check to see if disable signal was caught */
if (disable && !done) {
disabled = !disabled;
disable = 0;
}

/* Check to see if fs_disable signal was caught */
if (fs_disable && !done){
fs_disabled = !fs_disabled;
fs_disable = 0;
}

/* Check to see if exit signal was caught */
if (exiting) {
if (done) {
Expand All @@ -686,13 +700,20 @@ run_continual_mode(const location_provider_t *provider,
exiting = 0;
}

if (fullscreen_check && fullscreen.check() && !done && !fs_disabled) {
is_fullscreen = 1;
} else {
is_fullscreen = 0;
}

/* Print status change */
if (verbose && disabled != prev_disabled) {
printf(_("Status: %s\n"), disabled ?
if (verbose && ((disabled || is_fullscreen) != (prev_disabled || prev_fullscreen))) {
printf(_("Status: %s\n"), (disabled || is_fullscreen) ?
_("Disabled") : _("Enabled"));
}

prev_disabled = disabled;
prev_fullscreen = is_fullscreen;

/* Read timestamp */
double now;
Expand Down Expand Up @@ -727,7 +748,7 @@ run_continual_mode(const location_provider_t *provider,
interpolate_transition_scheme(
scheme, transition_prog, &target_interp);

if (disabled) {
if (disabled || is_fullscreen) {
period = PERIOD_NONE;
color_setting_reset(&target_interp);
}
Expand Down Expand Up @@ -1308,6 +1329,7 @@ main(int argc, char *argv[])
options.provider, location_state, scheme,
options.method, method_state,
options.use_fade, options.preserve_gamma,
options.fullscreen_check,
options.verbose);
if (r < 0) exit(EXIT_FAILURE);
}
Expand Down
14 changes: 14 additions & 0 deletions src/redshift.h
Original file line number Diff line number Diff line change
Expand Up @@ -150,4 +150,18 @@ typedef struct {
} location_provider_t;


/* Fullscreen detector */
typedef int fullscreen_init_func();
typedef int fullscreen_check_func();

typedef struct {
char *name;

/* Initialize display. */
fullscreen_init_func *init;

/* Check if active window is fullscreen. */
fullscreen_check_func *check;
} fullscreen_t;

#endif /* ! REDSHIFT_REDSHIFT_H */
20 changes: 20 additions & 0 deletions src/signals.c
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@

volatile sig_atomic_t exiting = 0;
volatile sig_atomic_t disable = 0;
volatile sig_atomic_t fs_disable = 0;


/* Signal handler for exit signals */
Expand All @@ -50,10 +51,18 @@ sigdisable(int signo)
disable = 1;
}

/* Signal handler for disabling the fullscreen detector signal */
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Redshift is in sore need of a control interface other than signals.

static void
sigfsdisable(int signo)
{
fs_disable = 1;
}

#else /* ! HAVE_SIGNAL_H || __WIN32__ */

int disable = 0;
int exiting = 0;
int fs_disable = 0;

#endif /* ! HAVE_SIGNAL_H || __WIN32__ */

Expand Down Expand Up @@ -95,6 +104,17 @@ signals_install_handlers(void)
return -1;
}

/* Install signal handler for USR2 signal */
sigact.sa_handler = sigfsdisable;
sigact.sa_mask = sigset;
sigact.sa_flags = 0;

r = sigaction(SIGUSR2, &sigact, NULL);
if (r < 0) {
perror("sigaction");
return -1;
}

/* Ignore CHLD signal. This causes child processes
(hooks) to be reaped automatically. */
sigact.sa_handler = SIG_IGN;
Expand Down
2 changes: 2 additions & 0 deletions src/signals.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,10 +25,12 @@

extern volatile sig_atomic_t exiting;
extern volatile sig_atomic_t disable;
extern volatile sig_atomic_t fs_disable;

#else /* ! HAVE_SIGNAL_H || __WIN32__ */
extern int exiting;
extern int disable;
extern int fs_disable;
#endif /* ! HAVE_SIGNAL_H || __WIN32__ */


Expand Down