Mercurial > hg > xemacs-beta
annotate lwlib/lwlib-colors.c @ 4916:a6c778975d7d
split USE_XFT into HAVE_XFT/USE_XFT
-------------------- ChangeLog entries follow: --------------------
ChangeLog addition:
2010-02-01 Ben Wing <ben@xemacs.org>
* configure:
* configure.ac (TAB):
USE_XFT* -> HAVE_XFT*.
lwlib/ChangeLog addition:
2010-02-01 Ben Wing <ben@xemacs.org>
* lwlib-colors.c:
* lwlib-colors.h:
* lwlib-fonts.c:
* lwlib-fonts.h:
* xlwmenu.c:
* xlwmenu.c (xlwMenuResources):
* xlwmenu.c (x_xft_text_width):
* xlwmenu.c (label_button_draw):
* xlwmenu.c (push_button_size):
* xlwmenu.c (push_button_draw):
* xlwmenu.c (make_drawing_gcs):
* xlwmenu.c (extract_font_extents):
* xlwmenu.c (default_font_of_font_list):
* xlwmenu.c (XlwMenuInitialize):
* xlwmenu.c (XlwMenuDestroy):
* xlwmenu.c (XlwMenuSetValues):
* xlwmenuP.h:
* xlwmenuP.h (_XlwMenu_part):
* xlwtabs.c:
* xlwtabs.c (TabsInit):
* xlwtabs.c (TabsDestroy):
* xlwtabs.c (TabsSetValues):
* xlwtabs.c (DrawTab):
* xlwtabs.c (TabWidth):
* xlwtabs.c (TabsAllocFgGC):
* xlwtabs.c (TabsAllocGreyGC):
* xlwtabsP.h:
USE_XFT* -> HAVE_XFT*.
src/ChangeLog addition:
2010-02-01 Ben Wing <ben@xemacs.org>
* Makefile.in.in:
* compiler.h:
* config.h.in:
* console-x-impl.h:
* console-x-impl.h (struct x_frame):
* console-x-impl.h (FRAME_X_TOTALLY_VISIBLE_P):
* console-x.h:
* console-xlike-inc.h:
* emacs.c (main_1):
* faces.c (complex_vars_of_faces):
* font-mgr.h:
* frame-x.c (x_delete_frame):
* frame-x.c (x_update_frame_external_traits):
* glyphs-x.c (update_widget_face):
* inline.c:
* objects-x-impl.h:
* objects-x-impl.h (struct x_color_instance_data):
* objects-x-impl.h (struct x_font_instance_data):
* objects-x.c:
* objects-x.c (x_initialize_color_instance):
* objects-x.c (x_initialize_font_instance):
* objects-x.c (x_print_font_instance):
* objects-x.c (x_finalize_font_instance):
* objects-x.c (x_font_instance_truename):
* objects-x.c (vars_of_objects_x):
* objects-x.h:
USE_XFT* -> HAVE_XFT*. But in objects-xlike-inc.c and
redisplay-xlike-inc.c, continue to use USE_XFT, and define
it appropriately in console-xlike-inc.h when both HAVE_XFT
and THIS_IS_X -- even if HAVE_XFT, we don't want to enable
XFT code when included in a *-gtk.c file.
author | Ben Wing <ben@xemacs.org> |
---|---|
date | Mon, 01 Feb 2010 22:00:29 -0600 |
parents | ad2f4ae9895b |
children | 308d34e9f07d |
rev | line source |
---|---|
3094 | 1 /* Color data structures for X and Xft. |
2 | |
3 Copyright (C) 2004 Free Software Foundation, Inc. | |
4 | |
5 Author: Stephen J. Turnbull <stephen@xemacs.org> | |
6 Created: 24 Jul 2004 by Stephen J. Turnbull | |
7 | |
8 This file is part of XEmacs. | |
9 | |
10 XEmacs is free software; you can redistribute it and/or modify it | |
11 under the terms of the GNU General Public License as published by the | |
12 Free Software Foundation; either version 2, or (at your option) any | |
13 later version. | |
14 | |
15 XEmacs is distributed in the hope that it will be useful, but WITHOUT | |
16 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
17 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
18 for more details. | |
19 | |
20 You should have received a copy of the GNU General Public License | |
21 along with XEmacs; see the file COPYING. If not, write to | |
22 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | |
23 Boston, MA 02111-1307, USA. */ | |
24 | |
25 /* Synched up with: Not in GNU Emacs. */ | |
26 | |
27 #include <config.h> | |
28 #include <limits.h> /* for ULONG_MAX */ | |
29 #include <stdlib.h> /* for malloc() */ | |
30 #include <stdio.h> | |
31 #include <X11/Xlib.h> | |
32 #include <X11/IntrinsicP.h> | |
33 #include <X11/ShellP.h> /* for ShellWidget */ | |
34 #include "lwlib-colors.h" | |
35 | |
36 static int debug_colors = 1; | |
37 | |
38 #ifdef __cplusplus | |
39 #define X_CLASSFIELD c_class | |
40 #else | |
41 #define X_CLASSFIELD class | |
42 #endif | |
43 | |
44 #define MINL(x,y) ((((unsigned long) (x)) < ((unsigned long) (y))) \ | |
45 ? ((unsigned long) (x)) : ((unsigned long) (y))) | |
46 | |
47 /* WIDGET is an Xt widget, VISUAL and DEPTH are return values */ | |
48 void | |
49 visual_info_from_widget (Widget widget, Visual **visual, int *depth) | |
50 { | |
51 /* grab the visual and depth from the nearest shell ancestor */ | |
52 Widget p = XtParent(widget); | |
53 | |
54 *visual = CopyFromParent; | |
55 *depth = -1; | |
56 while (*visual == CopyFromParent && p) | |
57 { | |
58 if (XtIsShell(p)) | |
59 { | |
60 *visual = ((ShellWidget)p)->shell.visual; | |
61 *depth = p->core.depth; | |
62 } | |
63 p = XtParent(p); | |
64 } | |
65 if (*visual == CopyFromParent || !*visual) | |
66 { | |
67 if (debug_colors > 1) | |
68 fprintf (stderr, "\nvisual_info_from_widget:" | |
69 " failed, using DefaultVisualOfScreen"); | |
70 *visual = DefaultVisualOfScreen (XtScreen (widget)); | |
71 *depth = DefaultDepthOfScreen (XtScreen (widget)); | |
72 } | |
73 else if (debug_colors > 1) | |
74 fprintf (stderr, "\nvisual_info_from_widget: succeeded"); | |
75 } | |
76 | |
77 /* Do we need all this hair on modern hardware? */ | |
78 | |
79 /* Replacement for XAllocColor() that tries to return the nearest | |
80 available color if the colormap is full. Original was from FSFmacs, | |
81 but rewritten by Jareth Hein <jareth@camelot-soft.com> 97/11/25 | |
82 Modified by Lee Kindness <lkindness@csl.co.uk> 31/08/99 to handle previous | |
83 total failure which was due to a read/write colorcell being the nearest | |
84 match - tries the next nearest... | |
85 | |
86 Return value is 1 for normal success, 2 for nearest color success, | |
87 3 for Non-deallocable success. */ | |
88 int | |
89 x_allocate_nearest_color (Display *display, Colormap colormap, | |
90 Visual *visual, XColor *color_def) | |
91 { | |
92 int status; | |
93 | |
94 /* #### [[Apparently this is often called with data derived from a widget | |
95 with no ShellWidget ancestor, or before the shell has a visual. | |
96 Currently this recovery code is in xlwmenu.c and xlwscrollbar.c, but | |
97 likely should come here.]] | |
98 I suspect the problem is that the visual-tracing code was improperly | |
99 written, missing a level of indirection. | |
100 CopyFromParent == NULL in XFree86/Darwin. | |
101 */ | |
102 if (visual == CopyFromParent || !visual) | |
103 { | |
104 Screen *screen = DefaultScreenOfDisplay (display); | |
105 fprintf (stderr, "\nx_allocate_nearest_color: bad visual (%08lx)", | |
106 (unsigned long) visual); | |
107 visual = DefaultVisualOfScreen (screen); | |
108 } | |
109 | |
110 if (visual->X_CLASSFIELD == DirectColor || visual->X_CLASSFIELD == TrueColor) | |
111 { | |
112 if (XAllocColor (display, colormap, color_def) != 0) | |
113 { | |
114 status = 1; | |
115 } | |
116 else | |
117 { | |
118 /* We're dealing with a TrueColor/DirectColor visual, so play games | |
119 with the RGB values in the XColor struct. */ | |
120 /* #### JH: I'm not sure how a call to XAllocColor can fail in a | |
121 TrueColor or DirectColor visual, so I will just reformat the | |
122 request to match the requirements of the visual, and re-issue | |
123 the request. If this fails for anybody, I wanna know about it | |
124 so I can come up with a better plan */ | |
125 | |
126 unsigned long rshift,gshift,bshift,rbits,gbits,bbits,junk; | |
127 junk = visual->red_mask; | |
128 rshift = 0; | |
129 while ((junk & 0x1) == 0) { | |
130 junk = junk >> 1; | |
131 rshift ++; | |
132 } | |
133 rbits = 0; | |
134 while (junk != 0) { | |
135 junk = junk >> 1; | |
136 rbits++; | |
137 } | |
138 junk = visual->green_mask; | |
139 gshift = 0; | |
140 while ((junk & 0x1) == 0) { | |
141 junk = junk >> 1; | |
142 gshift ++; | |
143 } | |
144 gbits = 0; | |
145 while (junk != 0) { | |
146 junk = junk >> 1; | |
147 gbits++; | |
148 } | |
149 junk = visual->blue_mask; | |
150 bshift = 0; | |
151 while ((junk & 0x1) == 0) { | |
152 junk = junk >> 1; | |
153 bshift ++; | |
154 } | |
155 bbits = 0; | |
156 while (junk != 0) { | |
157 junk = junk >> 1; | |
158 bbits++; | |
159 } | |
160 | |
161 color_def->red = color_def->red >> (16 - rbits); | |
162 color_def->green = color_def->green >> (16 - gbits); | |
163 color_def->blue = color_def->blue >> (16 - bbits); | |
164 if (XAllocColor (display, colormap, color_def) != 0) | |
165 status = 1; | |
166 else | |
167 { | |
168 int rd, gr, bl; | |
169 /* #### JH: I'm punting here, knowing that doing this will at | |
170 least draw the color correctly. However, unless we convert | |
171 all of the functions that allocate colors (graphics | |
172 libraries, etc) to use this function doing this is very | |
173 likely to cause problems later... */ | |
174 | |
175 if (rbits > 8) | |
176 rd = color_def->red << (rbits - 8); | |
177 else | |
178 rd = color_def->red >> (8 - rbits); | |
179 if (gbits > 8) | |
180 gr = color_def->green << (gbits - 8); | |
181 else | |
182 gr = color_def->green >> (8 - gbits); | |
183 if (bbits > 8) | |
184 bl = color_def->blue << (bbits - 8); | |
185 else | |
186 bl = color_def->blue >> (8 - bbits); | |
187 color_def->pixel = (rd << rshift) | (gr << gshift) | (bl << | |
188 bshift); | |
189 status = 3; | |
190 } | |
191 } | |
192 } | |
193 else | |
194 { | |
195 XColor *cells = NULL; | |
196 /* JH: I can't believe there's no way to go backwards from a | |
197 colormap ID and get its visual and number of entries, but X | |
198 apparently isn't built that way... */ | |
199 int no_cells = visual->map_entries; | |
200 status = 0; | |
201 | |
202 if (XAllocColor (display, colormap, color_def) != 0) | |
203 status = 1; | |
204 else while( status != 2 ) | |
205 { | |
206 /* If we got to this point, the colormap is full, so we're | |
207 going to try and get the next closest color. The algorithm used | |
208 is a least-squares matching, which is what X uses for closest | |
209 color matching with StaticColor visuals. */ | |
210 int nearest; | |
211 long nearest_delta, trial_delta; | |
212 int x; | |
213 | |
214 if( cells == NULL ) | |
215 { | |
216 /* #### this could be annoyingly slow | |
217 tell me again why lwlib can't use alloca & friends? */ | |
218 cells = (XColor *) malloc (sizeof(XColor)*no_cells); | |
219 for (x = 0; x < no_cells; x++) | |
220 cells[x].pixel = x; | |
221 | |
222 /* read the current colormap */ | |
223 XQueryColors (display, colormap, cells, no_cells); | |
224 } | |
225 | |
226 nearest = 0; | |
227 /* I'm assuming CSE so I'm not going to condense this. */ | |
228 nearest_delta = ((((color_def->red >> 8) - (cells[0].red >> 8)) | |
229 * ((color_def->red >> 8) - (cells[0].red >> 8))) | |
230 + | |
231 (((color_def->green >> 8) - (cells[0].green >> 8)) | |
232 * ((color_def->green >> 8) - (cells[0].green >> | |
233 8))) | |
234 + | |
235 (((color_def->blue >> 8) - (cells[0].blue >> 8)) | |
236 * ((color_def->blue >> 8) - (cells[0].blue >> | |
237 8)))); | |
238 for (x = 1; x < no_cells; x++) | |
239 { | |
240 trial_delta = ((((color_def->red >> 8) - (cells[x].red >> 8)) | |
241 * ((color_def->red >> 8) - (cells[x].red >> 8))) | |
242 + | |
243 (((color_def->green >> 8) - (cells[x].green >> 8)) | |
244 * ((color_def->green >> 8) - (cells[x].green >> | |
245 8))) | |
246 + | |
247 (((color_def->blue >> 8) - (cells[x].blue >> 8)) | |
248 * ((color_def->blue >> 8) - (cells[x].blue >> | |
249 8)))); | |
250 | |
251 /* less? Ignore cells marked as previously failing */ | |
252 if( (trial_delta < nearest_delta) && | |
253 (cells[x].pixel != ULONG_MAX) ) | |
254 { | |
255 nearest = x; | |
256 nearest_delta = trial_delta; | |
257 } | |
258 } | |
259 color_def->red = cells[nearest].red; | |
260 color_def->green = cells[nearest].green; | |
261 color_def->blue = cells[nearest].blue; | |
262 if (XAllocColor (display, colormap, color_def) != 0) | |
263 status = 2; | |
264 else | |
265 /* LSK: Either the colour map has changed since | |
266 * we read it, or the colour is allocated | |
267 * read/write... Mark this cmap entry so it's | |
268 * ignored in the next iteration. | |
269 */ | |
270 cells[nearest].pixel = ULONG_MAX; | |
271 } | |
272 } | |
273 return status; | |
274 } | |
275 | |
276 #if 0 | |
277 /* Replacement for XAllocColor() that tries to return the nearest | |
278 available color if the colormap is full. From GNU Emacs. | |
279 #### Review this to see if there's anything our hairy version could use. */ | |
280 | |
281 int | |
282 FIXME_allocate_nearest_color (Display *display, Colormap screen_colormap, | |
283 XColor *color_def) | |
284 { | |
285 int status = XAllocColor (display, screen_colormap, color_def); | |
286 if (status) | |
287 return status; | |
288 | |
289 { | |
290 /* If we got to this point, the colormap is full, so we're | |
291 going to try to get the next closest color. | |
292 The algorithm used is a least-squares matching, which is | |
293 what X uses for closest color matching with StaticColor visuals. */ | |
294 | |
295 int nearest, x; | |
296 unsigned long nearest_delta = ULONG_MAX; | |
297 | |
298 int no_cells = XDisplayCells (display, XDefaultScreen (display)); | |
299 /* Don't use alloca here because lwlib doesn't have the | |
300 necessary configuration information that src does. */ | |
301 XColor *cells = (XColor *) malloc (sizeof (XColor) * no_cells); | |
302 | |
303 for (x = 0; x < no_cells; x++) | |
304 cells[x].pixel = x; | |
305 | |
306 XQueryColors (display, screen_colormap, cells, no_cells); | |
307 | |
308 for (nearest = 0, x = 0; x < no_cells; x++) | |
309 { | |
310 long dred = (color_def->red >> 8) - (cells[x].red >> 8); | |
311 long dgreen = (color_def->green >> 8) - (cells[x].green >> 8); | |
312 long dblue = (color_def->blue >> 8) - (cells[x].blue >> 8); | |
313 unsigned long delta = dred * dred + dgreen * dgreen + dblue * dblue; | |
314 | |
315 if (delta < nearest_delta) | |
316 { | |
317 nearest = x; | |
318 nearest_delta = delta; | |
319 } | |
320 } | |
321 color_def->red = cells[nearest].red; | |
322 color_def->green = cells[nearest].green; | |
323 color_def->blue = cells[nearest].blue; | |
324 free (cells); | |
325 return XAllocColor (display, screen_colormap, color_def); | |
326 } | |
327 } | |
328 #endif | |
329 | |
330 | |
4916
a6c778975d7d
split USE_XFT into HAVE_XFT/USE_XFT
Ben Wing <ben@xemacs.org>
parents:
3094
diff
changeset
|
331 #ifdef HAVE_XFT |
3094 | 332 |
333 XftColor | |
334 xft_convert_color (Display *dpy, Colormap cmap, Visual *visual, int c, int dim) | |
335 { | |
336 static XColor color; /* #### why is this static ?? */ | |
337 XftColor result; | |
338 | |
339 color.pixel = c; | |
340 XQueryColor(dpy, cmap, &color); | |
341 | |
342 if (dim) | |
343 { | |
344 color.red = MINL (65535, color.red * 1.5); | |
345 color.green = MINL (65535, color.green * 1.5); | |
346 color.blue = MINL (65535, color.blue * 1.5); | |
347 x_allocate_nearest_color (dpy, cmap, visual, &color); | |
348 } | |
349 | |
350 result.pixel = color.pixel; | |
351 result.color.red = color.red; | |
352 result.color.green = color.green; | |
353 result.color.blue = color.blue; | |
354 result.color.alpha = 0xffff; | |
355 | |
356 return result; | |
357 } | |
358 | |
4916
a6c778975d7d
split USE_XFT into HAVE_XFT/USE_XFT
Ben Wing <ben@xemacs.org>
parents:
3094
diff
changeset
|
359 #endif /* HAVE_XFT */ |
3094 | 360 |
361 /* end of lwlib-colors.c */ |