sct

set color temperature
git clone anongit@rnpnr.xyz:sct.git
Log | Files | Refs | Feed | README | LICENSE

Commit: fda7df28bb87af79745ef88af3e7699f5537f0db
Parent: e34ab8280f67a18e5f2ce49a55c666efee1f2635
Author: Fabian Foerg
Date:   Thu,  3 Jan 2019 18:54:05 -0800

Merge pull request #3 from X11-good-tools/master

Rename utilites for X11.

$ ls /usr/bin/x*

/usr/bin/x11copy
...
/usr/bin/xsct
...
/usr/bin/xzoom
Diffstat:
A.gitignore | 1+
ACHANGELOG | 17+++++++++++++++++
ALICENSE | 11+++++++++++
AMakefile | 25+++++++++++++++++++++++++
MREADME.md | 8++++----
Msct.c | 148+++++++++++++++++++++++++++++++++++++++++++------------------------------------
Axsct.1 | 29+++++++++++++++++++++++++++++
7 files changed, 168 insertions(+), 71 deletions(-)

diff --git a/.gitignore b/.gitignore @@ -0,0 +1 @@ +xsct diff --git a/CHANGELOG b/CHANGELOG @@ -0,0 +1,17 @@ +PROJECT: https://github.com/faf0/sct + +1.3: zvezdochiot on 02 Jan 2019 +* Rename utilites for X11 +* Add -h option to print usage information +* Add license documentation +* Add changelog +* Add man + +1.2: faf0 on 31 May 2016 +* Fix crash when DISPLAY env variable is set to an invalid value + +1.1: faf0 on 21 Nov 2015 +* Fix memleak + +1.0: faf0 on 21 Nov 2015 +* Initial diff --git a/LICENSE b/LICENSE @@ -0,0 +1,11 @@ +This project is public domain, do as you wish + +The whitepoints data within sct.c has been released into the public domain +by Ingo Thies: +"I have calculated the table by following mathematical rules of color + integration and conversion from the CIE 1931 color space to sRGB. + + I doubt that a numerically computed color table is copyrightable at all + (in contrast to the actual software implementation). However, if it is + indeed copyrightable, I have no problem with releasing it into the + public domain." diff --git a/Makefile b/Makefile @@ -0,0 +1,25 @@ +PROG = xsct +CC = gcc +CFLAGS = -Wall -std=c99 -O2 -I /usr/X11R6/include +LDFLAGS = -L /usr/X11R6/lib -lX11 -lXrandr +SRCS = sct.c +PREFIX = /usr +BIN = $(PREFIX)/bin +MAN = $(PREFIX)/share/man/man1 +INSTALL = install + +$(PROG): $(SRCS) + $(CC) $(CFLAGS) $^ -o $@ $(LDFLAGS) + +install: $(PROG) $(PROG).1 + $(INSTALL) -d $(BIN) + $(INSTALL) -m 0755 $(PROG) $(BIN) + $(INSTALL) -d $(MAN) + $(INSTALL) -m 0644 $(PROG).1 $(MAN) + +uninstall: + rm -f $(BIN)/$(PROG) + rm -f $(MAN)/$(PROG).1 + +clean: + rm -f $(PROG) diff --git a/README.md b/README.md @@ -1,6 +1,6 @@ # About -Sct (set color temperature) is a UNIX tool which allows you to set the color +Xsct (X11 set color temperature) is a UNIX tool which allows you to set the color temperature of your screen. It is simpler than Redshift and f.lux. Original code was published by Ted Unangst: @@ -20,16 +20,16 @@ Minor modifications were made in order to get sct to: Compile the code using the following command: ~~~ -cc -std=c99 -O2 -I /usr/X11R6/include -o sct sct.c -L /usr/X11R6/lib -lm -lX11 -lXrandr +cc -std=c99 -O2 -I /usr/X11R6/include sct.c -o xsct -L /usr/X11R6/lib -lX11 -lXrandr ~~~ Execute sct using the following command: ~~~ -./sct 3700 +./xsct 3700 ~~~ The first parameter (`3700` above) denotes the color temperature and can be between `1000` and `10000`. -If `sct` is called without parameters, sct sets the color temperature to `6500`. +If `xsct` is called without parameters, sct sets the color temperature to `6500`. diff --git a/sct.c b/sct.c @@ -1,8 +1,8 @@ /* - * sct - set color temperature + * xsct - X11 set color temperature * * Compile the code using the following command: - * cc -std=c99 -O2 -I /usr/X11R6/include -o sct sct.c -L /usr/X11R6/lib -lm -lX11 -lXrandr + * cc -std=c99 -O2 -I /usr/X11R6/include sct.c -o xsct -L /usr/X11R6/lib -lX11 -lXrandr * * Original code published by Ted Unangst: * http://www.tedunangst.com/flak/post/sct-set-color-temperature @@ -18,94 +18,108 @@ * Public domain, do as you wish. */ -#include <math.h> -#include <stdio.h> -#include <stdlib.h> - #include <X11/Xatom.h> #include <X11/Xlib.h> #include <X11/Xproto.h> #include <X11/extensions/Xrandr.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +static void +usage() +{ + printf("Usage: xsct [temperature]\n" + "Temperatures must be in a range from 1000-10000\n" + "If no arguments are passed xsct resets the display to the default temperature (6500K)\n" + "If -h or --help is passed xsct will display this usage information\n"); + exit(0); +} + /* cribbed from redshift, but truncated with 500K steps */ static const struct { float r; float g; float b; } whitepoints[] = { - { 1.00000000, 0.18172716, 0.00000000, }, /* 1000K */ - { 1.00000000, 0.42322816, 0.00000000, }, - { 1.00000000, 0.54360078, 0.08679949, }, - { 1.00000000, 0.64373109, 0.28819679, }, - { 1.00000000, 0.71976951, 0.42860152, }, - { 1.00000000, 0.77987699, 0.54642268, }, - { 1.00000000, 0.82854786, 0.64816570, }, - { 1.00000000, 0.86860704, 0.73688797, }, - { 1.00000000, 0.90198230, 0.81465502, }, - { 1.00000000, 0.93853986, 0.88130458, }, - { 1.00000000, 0.97107439, 0.94305985, }, - { 1.00000000, 1.00000000, 1.00000000, }, /* 6500K */ - { 0.95160805, 0.96983355, 1.00000000, }, - { 0.91194747, 0.94470005, 1.00000000, }, - { 0.87906581, 0.92357340, 1.00000000, }, - { 0.85139976, 0.90559011, 1.00000000, }, - { 0.82782969, 0.89011714, 1.00000000, }, - { 0.80753191, 0.87667891, 1.00000000, }, - { 0.78988728, 0.86491137, 1.00000000, }, /* 10000K */ - { 0.77442176, 0.85453121, 1.00000000, }, + { 1.00000000, 0.18172716, 0.00000000, }, /* 1000K */ + { 1.00000000, 0.42322816, 0.00000000, }, + { 1.00000000, 0.54360078, 0.08679949, }, + { 1.00000000, 0.64373109, 0.28819679, }, + { 1.00000000, 0.71976951, 0.42860152, }, + { 1.00000000, 0.77987699, 0.54642268, }, + { 1.00000000, 0.82854786, 0.64816570, }, + { 1.00000000, 0.86860704, 0.73688797, }, + { 1.00000000, 0.90198230, 0.81465502, }, + { 1.00000000, 0.93853986, 0.88130458, }, + { 1.00000000, 0.97107439, 0.94305985, }, + { 1.00000000, 1.00000000, 1.00000000, }, /* 6500K */ + { 0.95160805, 0.96983355, 1.00000000, }, + { 0.91194747, 0.94470005, 1.00000000, }, + { 0.87906581, 0.92357340, 1.00000000, }, + { 0.85139976, 0.90559011, 1.00000000, }, + { 0.82782969, 0.89011714, 1.00000000, }, + { 0.80753191, 0.87667891, 1.00000000, }, + { 0.78988728, 0.86491137, 1.00000000, }, /* 10000K */ + { 0.77442176, 0.85453121, 1.00000000, }, }; static void sct_for_screen(Display *dpy, int screen, int temp) { - Window root = RootWindow(dpy, screen); - XRRScreenResources *res = XRRGetScreenResourcesCurrent(dpy, root); + Window root = RootWindow(dpy, screen); + XRRScreenResources *res = XRRGetScreenResourcesCurrent(dpy, root); - temp -= 1000; - double ratio = temp % 500 / 500.0; + temp -= 1000; + double ratio = temp % 500 / 500.0; #define AVG(c) whitepoints[temp / 500].c * (1 - ratio) + whitepoints[temp / 500 + 1].c * ratio - double gammar = AVG(r); - double gammag = AVG(g); - double gammab = AVG(b); + double gammar = AVG(r); + double gammag = AVG(g); + double gammab = AVG(b); - for (int c = 0; c < res->ncrtc; c++) { - int crtcxid = res->crtcs[c]; - int size = XRRGetCrtcGammaSize(dpy, crtcxid); + for (int c = 0; c < res->ncrtc; c++) { + int crtcxid = res->crtcs[c]; + int size = XRRGetCrtcGammaSize(dpy, crtcxid); - XRRCrtcGamma *crtc_gamma = XRRAllocGamma(size); + XRRCrtcGamma *crtc_gamma = XRRAllocGamma(size); - for (int i = 0; i < size; i++) { - double g = 65535.0 * i / size; - crtc_gamma->red[i] = g * gammar; - crtc_gamma->green[i] = g * gammag; - crtc_gamma->blue[i] = g * gammab; - } + for (int i = 0; i < size; i++) { + double g = 65535.0 * i / size; + crtc_gamma->red[i] = g * gammar; + crtc_gamma->green[i] = g * gammag; + crtc_gamma->blue[i] = g * gammab; + } - XRRSetCrtcGamma(dpy, crtcxid, crtc_gamma); - XFree(crtc_gamma); - } + XRRSetCrtcGamma(dpy, crtcxid, crtc_gamma); + XFree(crtc_gamma); + } - XFree(res); + XFree(res); } int main(int argc, char **argv) { - Display *dpy = XOpenDisplay(NULL); - if (!dpy) { - perror("XOpenDisplay(NULL) failed"); - fprintf(stderr, "Make sure DISPLAY is set correctly.\n"); - return EXIT_FAILURE; - } - int screens = XScreenCount(dpy); - - int temp = 6500; - if (argc > 1) - temp = atoi(argv[1]); - if (temp < 1000 || temp > 10000) - temp = 6500; - - for (int screen = 0; screen < screens; screen++) - sct_for_screen(dpy, screen, temp); - - XCloseDisplay(dpy); - - return EXIT_SUCCESS; + Display *dpy = XOpenDisplay(NULL); + if (!dpy) { + perror("XOpenDisplay(NULL) failed"); + fprintf(stderr, "Make sure DISPLAY is set correctly.\n"); + return EXIT_FAILURE; + } + int screens = XScreenCount(dpy); + + int temp = 6500; + if (argc > 1) + { + if (!strcmp(argv[1],"-h") || !strcmp(argv[1],"--help")) + usage(); + temp = atoi(argv[1]); + } + if (temp < 1000 || temp > 10000) + temp = 6500; + + for (int screen = 0; screen < screens; screen++) + sct_for_screen(dpy, screen, temp); + + XCloseDisplay(dpy); + + return EXIT_SUCCESS; } diff --git a/xsct.1 b/xsct.1 @@ -0,0 +1,29 @@ +.TH xsct 1 "June 2016" "1.3" "User Manual" +.SH NAME +xsct \- X11 set screen color temperature +.SH SYNOPSIS +.B xsct +[temperature] + +or + +.B xsct +[-h || --help] + + +.SH DESCRIPTION +.B xsct +sets the screen's color temperature in a range from 1000 to 10000 + +.SH OPTIONS +.IP temperature +If passed a value in the correct range (see above) +.B xsct +will set the current screen temperature to this value +.IP -h,--help +Display usage information and exit +.IP none +If no options are passed, xsct sets the color temperature to the default of 6500 + +.SH AUTHOR +xsct was written by Ted Unangst <tedu@openbsd.org>