dtscreen.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381
  1. /*
  2. * CDE - Common Desktop Environment
  3. *
  4. * Copyright (c) 1993-2012, The Open Group. All rights reserved.
  5. *
  6. * These libraries and programs are free software; you can
  7. * redistribute them and/or modify them under the terms of the GNU
  8. * Lesser General Public License as published by the Free Software
  9. * Foundation; either version 2 of the License, or (at your option)
  10. * any later version.
  11. *
  12. * These libraries and programs are distributed in the hope that
  13. * they will be useful, but WITHOUT ANY WARRANTY; without even the
  14. * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
  15. * PURPOSE. See the GNU Lesser General Public License for more
  16. * details.
  17. *
  18. * You should have received a copy of the GNU Lesser General Public
  19. * License along with these libraries and programs; if not, write
  20. * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
  21. * Floor, Boston, MA 02110-1301 USA
  22. */
  23. /* $TOG: dtscreen.c /main/6 1998/04/20 12:58:46 mgreess $ */
  24. /*
  25. */
  26. /*-
  27. * dtscreen.c - X11 client to lock a display and show a screen saver.
  28. *
  29. * Copyright (c) 1988-91 by Patrick J. Naughton.
  30. *
  31. * Permission to use, copy, modify, and distribute this software and its
  32. * documentation for any purpose and without fee is hereby granted,
  33. * provided that the above copyright notice appear in all copies and that
  34. * both that copyright notice and this permission notice appear in
  35. * supporting documentation.
  36. *
  37. * This file is provided AS IS with no warranties of any kind. The author
  38. * shall have no liability with respect to the infringement of copyrights,
  39. * trade secrets or any patents by this file or any part thereof. In no
  40. * event will the author be liable for any lost revenue or profits or
  41. * other special, indirect and consequential damages.
  42. *
  43. * Comments and additions should be sent to the author:
  44. *
  45. * naughton@eng.sun.com
  46. *
  47. * Patrick J. Naughton
  48. * MS 21-14
  49. * Sun Laboritories, Inc.
  50. * 2550 Garcia Ave
  51. * Mountain View, CA 94043
  52. *
  53. * Revision History:
  54. * 16-May-91: added pyro and random modes.
  55. * ripped big comment block out of all other files.
  56. * 29-Oct-90: added cast to XFree() arg.
  57. * added volume arg to call to XBell().
  58. * 31-Aug-90: added blank mode.
  59. * added swarm mode.
  60. * moved usleep() and seconds() out to usleep.c.
  61. * added SVR4 defines to dtscreen.h
  62. * 29-Jul-90: added support for multiple screens to be locked by one dtscreen.
  63. * moved global defines to dtscreen.h
  64. * removed use of allowsig().
  65. * 07-Jul-90: reworked commandline args and resources to use Xrm.
  66. * moved resource processing out to resource.c
  67. * 02-Jul-90: reworked colors to not use dynamic colormap.
  68. * 23-May-90: added autoraise when obscured.
  69. * 18-Feb-90: added SunOS3.5 fix.
  70. * changed -mono -> -color, and -saver -> -lock.
  71. * allow non-locking screensavers to display on remote machine.
  72. * added -echokeys to disable echoing of '?'s on input.
  73. * cleaned up all of the parameters and defaults.
  74. * 23-Sep-89: Added fix to allow local hostname:0 as a display.
  75. * Put empty case for Enter/Leave events.
  76. * Moved colormap installation later in startup.
  77. * 19-Sep-89: Added '?'s on input.
  78. * 27-Mar-89: Added -qix mode.
  79. * Fixed GContext->GC.
  80. * 08-Mar-89: Added -nice, -mode and -display, built vector for life and hop.
  81. * 24-Feb-89: Replaced hopalong display with life display from SunView1.
  82. * 22-Feb-89: Added fix for color servers with n < 8 planes.
  83. * 16-Feb-89: Updated calling conventions for XCreateHsbColormap();
  84. * Added -count for number of iterations per color.
  85. * Fixed defaulting mechanism.
  86. * Ripped out VMS hacks.
  87. * Sent to expo for X11R3 contrib.
  88. * 19-Jan-89: Fixed monochrome gc bug.
  89. * 19-Sep-88: Changed -color to -mono. (default is color on color displays).
  90. * Added -saver option. (just do display... don't lock.)
  91. * 01-Apr-88: Added XGrabServer/XUngrabServer for more security.
  92. * 27-Mar-88: Rotate fractal by 45 degrees clockwise.
  93. * 24-Mar-88: Added color support. [-color]
  94. * wrote the man page.
  95. * 23-Mar-88: Added HOPALONG routines from Scientific American Sept. 86 p. 14.
  96. * added requirement for display to be "unix:0".
  97. * 22-Mar-88: Recieved Walter Milliken's comp.windows.x posting.
  98. *
  99. */
  100. /* include file for message texts */
  101. #include <limits.h>
  102. #include <nl_types.h>
  103. #define MF_DTSCREEN "dtscreen"
  104. #include <nl_types.h>
  105. #include <locale.h>
  106. nl_catd scmc_catd; /* Cat descriptor for scmc conversion */
  107. #include <stdio.h>
  108. #include <stdlib.h>
  109. #include <signal.h>
  110. #include <string.h>
  111. #include <errno.h>
  112. #include <X11/Intrinsic.h> /* For Boolean */
  113. #include <X11/Shell.h>
  114. #include "dtscreen.h"
  115. #ifdef NEVER
  116. /* We'd like to include DtP.h, but it interferes with dtscreen.h */
  117. # include <Dt/DtP.h>
  118. #endif /* NEVER */
  119. #include <Dt/EnvControlP.h>
  120. #include <Dt/Saver.h>
  121. #if !defined(NL_CAT_LOCALE)
  122. #define NL_CAT_LOCALE 0
  123. #endif
  124. char *ProgramName; /* argv[0] */
  125. Display *dsp = NULL; /* server display connection */
  126. void (*callback) () = NULL;
  127. void (*init) () = NULL;
  128. static perwindow *Win; /* perwindow information */
  129. static int windows; /* number of windows */
  130. static Window *winprop = NULL; /* dtsession cover windows */
  131. /* VARARGS1 */
  132. void
  133. error(char *s1, char *s2)
  134. {
  135. fprintf(stderr, s1, ProgramName, s2);
  136. exit(1);
  137. }
  138. /*
  139. * Restore all grabs, reset screensaver, restore colormap, close connection.
  140. */
  141. static void
  142. finish(void)
  143. {
  144. XSync(dsp, False);
  145. if (winprop)
  146. XFree((char *)winprop);
  147. XFlush(dsp);
  148. XCloseDisplay(dsp);
  149. }
  150. static void
  151. justDisplay(void)
  152. {
  153. XEvent event;
  154. int window;
  155. for (window = 0; window < windows; window++)
  156. init(Win+window);
  157. do {
  158. while (!XPending(dsp)) {
  159. for (window = 0; window < windows; window++)
  160. callback(Win+window);
  161. XSync(dsp, False);
  162. usleep(delay);
  163. }
  164. XNextEvent(dsp, &event);
  165. #ifndef DEBUG
  166. if (event.type == VisibilityNotify)
  167. XRaiseWindow(dsp, event.xany.window);
  168. #endif
  169. } while (1);
  170. }
  171. long
  172. allocpixel(Colormap cmap, char *name, char *def)
  173. {
  174. XColor col;
  175. XColor tmp;
  176. XParseColor(dsp, cmap, name, &col);
  177. if (!XAllocColor(dsp, cmap, &col)) {
  178. #ifdef MIT_R5
  179. fprintf(stderr,
  180. "couldn't allocate: %s, using %s instead\n",
  181. name, def);
  182. #else
  183. fprintf(stderr, catgets(scmc_catd, 2, 35,
  184. "couldn't allocate: %s, using %s instead\n"),
  185. name, def);
  186. #endif
  187. XAllocNamedColor(dsp, cmap, def, &col, &tmp);
  188. }
  189. return col.pixel;
  190. }
  191. int
  192. main(int argc, char *argv[])
  193. {
  194. XSetWindowAttributes xswa;
  195. XGCValues xgcv;
  196. int nitems = 0;
  197. int window;
  198. int i;
  199. /*
  200. * So we can find the app-defaults file.
  201. */
  202. _DtEnvControl(DT_ENV_SET);
  203. /* set locale to what is defined by local environment */
  204. setlocale(LC_ALL,"");
  205. scmc_catd = catopen(MF_DTSCREEN, NL_CAT_LOCALE);
  206. ProgramName = strrchr(argv[0], '/');
  207. if (ProgramName)
  208. ProgramName++;
  209. else
  210. ProgramName = argv[0];
  211. srandom(time((time_t *) 0)); /* random mode needs the seed set. */
  212. GetResources(argc, argv);
  213. CheckResources();
  214. if (!create)
  215. {
  216. /* Make sure DtSvc is initialized properly. */
  217. XtAppContext appContext;
  218. Widget shellWidget;
  219. int dummyArgc = 1;
  220. char *dummyArgv[1];
  221. dummyArgv[0] = ProgramName;
  222. XtToolkitInitialize();
  223. appContext = XtCreateApplicationContext();
  224. XtDisplayInitialize(appContext, dsp, ProgramName, ProgramName,
  225. NULL, 0, &dummyArgc, dummyArgv);
  226. shellWidget = XtAppCreateShell(ProgramName, ProgramName,
  227. applicationShellWidgetClass,
  228. dsp, NULL, 0);
  229. DtAppInitialize(appContext, dsp, shellWidget,
  230. ProgramName, ProgramName);
  231. /*
  232. * Try to get array of window ids from desktop. Also returned is
  233. * a property identifier whose change will tell us when to terminate.
  234. */
  235. if (!DtSaverGetWindows(dsp, &winprop, &nitems))
  236. {
  237. fprintf(stderr, catgets(scmc_catd, 2, 40,
  238. "%s: Cannot locate window in which to draw. Using the -create\n"
  239. "option will cause %s to create its own window.\n"),
  240. ProgramName, ProgramName);
  241. exit(1);
  242. }
  243. Win = (perwindow *)malloc(nitems * sizeof(perwindow));
  244. windows = nitems;
  245. for (window = 0; window < windows; window++)
  246. {
  247. Win[window].w = winprop[window];
  248. Win[window].perscreen = NULL;
  249. Win[window].data = NULL;
  250. }
  251. }
  252. else
  253. {
  254. Screen *scr = ScreenOfDisplay(dsp, 0);
  255. Win = (perwindow *)malloc(sizeof(perwindow));
  256. windows = 1;
  257. xswa.override_redirect = True;
  258. xswa.background_pixel = BlackPixelOfScreen(scr);
  259. xswa.event_mask = VisibilityChangeMask;
  260. Win[0].w = XCreateWindow(
  261. dsp,
  262. RootWindowOfScreen(scr),
  263. 0, 0,
  264. WidthOfScreen(scr) - 100, HeightOfScreen(scr) - 100,
  265. 0, CopyFromParent, InputOutput, CopyFromParent,
  266. CWBackPixel | CWEventMask, &xswa);
  267. Win[0].perscreen = NULL;
  268. Win[0].data = NULL;
  269. XMapWindow(dsp, Win[0].w);
  270. XRaiseWindow(dsp, Win[0].w);
  271. }
  272. for (window = 0; window < windows; window++)
  273. {
  274. XWindowAttributes attr;
  275. XGetWindowAttributes(dsp, Win[window].w, &attr);
  276. for (i = 0; i < window; i++)
  277. {
  278. if (Win[i].perscreen && Win[i].perscreen->screen == attr.screen)
  279. {
  280. Win[window].perscreen = Win[i].perscreen;
  281. break;
  282. }
  283. }
  284. if (Win[window].perscreen == NULL)
  285. {
  286. Colormap cmap;
  287. perscreen *pscreen;
  288. pscreen = (perscreen *)malloc(sizeof(perscreen));
  289. Win[window].perscreen = pscreen;
  290. pscreen->screen = attr.screen;
  291. cmap = DefaultColormapOfScreen(pscreen->screen);
  292. pscreen->pixels[0] = allocpixel(cmap, "White", "White");
  293. pscreen->pixels[1] = allocpixel(cmap, "Black", "Black");
  294. if (mono || CellsOfScreen(pscreen->screen) == 2)
  295. {
  296. pscreen->npixels = 2;
  297. }
  298. else
  299. {
  300. int colorcount = NUMCOLORS;
  301. u_char red[NUMCOLORS];
  302. u_char green[NUMCOLORS];
  303. u_char blue[NUMCOLORS];
  304. hsbramp(0.0, saturation, 1.0, 1.0, saturation, 1.0, colorcount,
  305. red, green, blue);
  306. pscreen->npixels = 0;
  307. for (i = 0; i < colorcount; i++)
  308. {
  309. XColor xcolor;
  310. xcolor.red = red[i] << 8;
  311. xcolor.green = green[i] << 8;
  312. xcolor.blue = blue[i] << 8;
  313. xcolor.flags = DoRed | DoGreen | DoBlue;
  314. if (!XAllocColor(dsp, cmap, &xcolor))
  315. break;
  316. pscreen->pixels[i] = xcolor.pixel;
  317. pscreen->npixels++;
  318. }
  319. }
  320. }
  321. xgcv.foreground = WhitePixelOfScreen(Win[window].perscreen->screen);
  322. xgcv.background = BlackPixelOfScreen(Win[window].perscreen->screen);
  323. Win[window].gc = XCreateGC(dsp, Win[window].w,
  324. GCForeground | GCBackground, &xgcv);
  325. }
  326. if(-1 == nice(nicelevel)) {
  327. fprintf(stderr, "dtscreen: failed to set nice() level '%s'\n", strerror(errno));
  328. }
  329. justDisplay();
  330. finish();
  331. return 0;
  332. }