21.7 Canvases and Colormaps
When the colormap segment associated with a canvas is changed, the contents of the canvas
must be repainted to reflect the new colors. If the boolean attribute CANVAS_CMS_REPAINT is
set to TRUE, the library automatically calls the canvas’s repaint procedure each time a new
colormap segment is set on the canvas. The damage list passed to the routine contains the
dimensions of the entire paint window.
Note that the application itself must track any changes in the contents of a colormap segment.
CANVAS_CMS_REPAINT enables the library to generate a synthetic repaint event only when
the actual colormap segment is switched.
For dynamic colormap segments, when a color changes, the pixel value remains the same but
the color represented by the index into the colormap segment changes. Therefore, the repaint
routine is not called and the window’s appearance changes automatically. This method of
colormap manipulation is commonly used to implement color animation.
21.8 Multi-visual Support
XView allows you to create windows and colormap segments using arbitrary visuals (See
Chapter 7 of Volume One, Xlib Programming Manual for a description of visuals in X11).
You can use this functionality to access any visual that the X11 server supports. The attri-
butes described in this section allow you to indicate visuals you want associated with your
windows and colormap segments.
The attribute
XV_VISUAL specifies the exact visual that will be used in the creation of a win-
dow or colormap segment. The value is a pointer a Visual structure (available from
XMatchVisualInfo or XGetVisualInfo). This attribute applies only to WINDOW and
CMS objects.
The attribute
XV_VISUAL_CLASS specifies the class of the visual that will be used in the cre-
ation of the window or colormap segment. The value should be one of the following:
StaticGray
GrayScale
StaticColor
PseudoColor
TrueColor
DirectColor
If the server that the window is being created for does not support the visual class specified,
XView uses the default visual. XV_VISUAL_CLASS also only applies to a WINDOW or to a CMS
object.
The attribute WIN_DEPTH specifies the depth of the window that you are creating. If the value
specified by this attribute is not supported by the server, the library uses the default depth
instead. This attribute, like all WIN_* attributes applies only to WINDOW objects.
528 XView Programming Manual
21.8.1 Using the Visual Attributes
Both XV_VISUAL and XV_VISUAL_CLASS do essentially the same thing. XV_VISUAL is more
specific. Use XV_VISUAL_CLASS, optionally in conjunction with WIN_DEPTH, if you have no
preference about the specific visual, but just require a certain visual class. However, if you
want to make sure that you are using a specific visual that the server supports, use XGet-
VisualInfo or XMatchVisualInfo to find the visual and then use the visual as an
argument to XV_VISUAL.
If you are creating your own colormap segment(s), make sure that they are created with the
same visual as the window you will be using with the CMS. For example, if you have a win-
dow that requires a cms, do the following:
cms = (Cms)xv_create(screen, CMS,
XV_VISUAL, (Visual *)xv_get(window, XV_VISUAL),
...
NULL);
Note that you should never assume that creating a window with XV_VISUAL_CLASS or
WIN_DEPTH will use the class and depth you specify. If the server does not have a visual of
the given class and depth, you will not be supplied with the visual you specify. If your appli-
cation depends on using a specific visual, be sure to check the visual class and depth of the
window, using xv_get(), to see if you did indeed get the required visual. Alternatively,
you may query the server before the creating the window, using XGetVisualInfo or
XMatchVisualInfo, to check the visuals that the server supports.
21.9 Another Example
This final example demonstrates just about all of the features discussed in this chapter. It
includes creating a colormap segment, initializing color, using foreground and background
colors, and setting colors on specific XView objects, including panel items.
In Example 21-3, the user selects objects (from the “Objects” item) to be colored by selecting
one of the color tiles from the “Colors” choice item. The callback function for this panel
item calls color_notify(), which sets the currently selected colors on the foreground or
background of the selected objects. Whether to use foreground or background colors is
dependent on the value of the “Fg/Bg” panel item; the items whose colors are affected are
retrieved by getting the value of the “Objects” panel item. Since more than one object can be
selected from this item, the value is a mask of the selected items. We loop through each bit in
the mask identifying which objects should have their colors set.
Example 21-3. The color_objs.c program
/*
* color_objs.c --
* This program demonstrates the use of color in XView. It allows
* the user to choose the foreground and background colors of the
* various objects in an interactive manner.
*/
#include <xview/xview.h>
Color
Color 529
Example 21-3. The color_objs.c program (continued)
#include <xview/svrimage.h>
#include <xview/textsw.h>
#include <xview/panel.h>
#include <xview/cms.h>
#include <xview/notice.h>
#define SELECT_TEXTSW 0
#define SELECT_TEXTSW_VIEW 1
#define SELECT_PANEL 2
#define SELECT_ICON 3
#define NUM_COLORS 8
/* Icon data */
static short icon_bits[ ] = {
#include "cardback.icon"
};
/* solid black square */
static short black_bits[ ] = {
0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF,
0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF, 0xFFFF
};
Panel_item objects;
Textsw textsw;
Panel panel;
Icon icon;
/*
* main()
* Create a panel and panel items. The application uses panel items
* to choose a particular object and change its foreground and
* background colors in an interactive manner. Create a textsw.
* Create an icon. All the objects share the same colormap segment.
*/
main(argc,argv)
int argc;
char *argv[ ];
{
Frame frame;
Panel_item color_choices, panel_fg_bg;
Cms cms;
int i;
Server_image chip, icon_image;
void color_notify();
extern void exit();
static Xv_singlecolor cms_colors[ ] = {
{ 255, 255, 255 }, /* white */
{ 255, 0, 0 }, /* red */
{ 0, 255, 0 }, /* green */
{ 0, 0, 255 }, /* blue */
{ 255, 255, 0 }, /* yellow */
{ 188, 143, 143 }, /* brown */
{ 220, 220, 220 }, /* gray */
{ 0, 0, 0 }, /* black */
530 XView Programming Manual
Example 21-3. The color_objs.c program (continued)
};
xv_init(XV_INIT_ARGC_PTR_ARGV, &argc, argv, NULL);
frame = (Frame)xv_create(NULL, FRAME,
FRAME_LABEL, argv[0 ],
NULL);
cms = (Cms)xv_create(NULL, CMS,
CMS_NAME, "palette",
CMS_CONTROL_CMS, TRUE,
CMS_TYPE, XV_STATIC_CMS,
CMS_SIZE, CMS_CONTROL_COLORS + NUM_COLORS,
CMS_COLORS, cms_colors,
NULL);
/* Create panel and set the colormap segment on the panel */
panel = (Panel)xv_create(frame, PANEL,
PANEL_LAYOUT, PANEL_VERTICAL,
WIN_CMS, cms,
NULL);
/* Create panel items */
objects = (Panel_item)xv_create(panel, PANEL_TOGGLE,
PANEL_LABEL_STRING, "Objects",
PANEL_LAYOUT, PANEL_HORIZONTAL,
PANEL_CHOICE_STRINGS, "Textsw", "Textsw View",
"Panel", "Icon", NULL,
NULL);
panel_fg_bg = (Panel_item)xv_create(panel, PANEL_CHECK_BOX,
PANEL_LABEL_STRING, "Fg/Bg",
PANEL_CHOOSE_ONE, TRUE,
PANEL_LAYOUT, PANEL_HORIZONTAL,
PANEL_CHOICE_STRINGS, "Background", "Foreground", NULL,
NULL);
chip = (Server_image)xv_create(XV_NULL, SERVER_IMAGE,
XV_WIDTH, 16,
XV_HEIGHT, 16,
SERVER_IMAGE_DEPTH, 1,
SERVER_IMAGE_BITS, black_bits,
NULL);
color_choices = (Panel_item)xv_create(panel, PANEL_CHOICE,
PANEL_LAYOUT, PANEL_HORIZONTAL,
PANEL_LABEL_STRING, "Colors",
PANEL_CLIENT_DATA, panel_fg_bg,
XV_X, (int)xv_get(panel_fg_bg, XV_X),
PANEL_NEXT_ROW, 15,
PANEL_CHOICE_IMAGES,
chip, chip, chip, chip, chip, chip, chip, chip, NULL,
PANEL_CHOICE_COLOR, 0, CMS_CONTROL_COLORS + 0,
PANEL_CHOICE_COLOR, 1, CMS_CONTROL_COLORS + 1,
PANEL_CHOICE_COLOR, 2, CMS_CONTROL_COLORS + 2,
PANEL_CHOICE_COLOR, 3, CMS_CONTROL_COLORS + 3,
PANEL_CHOICE_COLOR, 4, CMS_CONTROL_COLORS + 4,
Color
Color 531
Example 21-3. The color_objs.c program (continued)
PANEL_CHOICE_COLOR, 5, CMS_CONTROL_COLORS + 5,
PANEL_CHOICE_COLOR, 6, CMS_CONTROL_COLORS + 6,
PANEL_CHOICE_COLOR, 7, CMS_CONTROL_COLORS + 7,
PANEL_NOTIFY_PROC, color_notify,
NULL);
(void) xv_create(panel, PANEL_BUTTON,
PANEL_LABEL_STRING, "Quit",
PANEL_NOTIFY_PROC, exit,
NULL);
(void)window_fit_height(panel);
/* create textsw and set the colormap segment for it */
textsw = (Textsw)xv_create(frame, TEXTSW,
WIN_CMS, cms,
WIN_BELOW, panel,
WIN_ROWS, 15,
WIN_COLUMNS, 80,
TEXTSW_FILE_CONTENTS, "/etc/motd",
WIN_BACKGROUND_COLOR, CMS_CONTROL_COLORS + 0,
NULL);
/* adjust panel dimensions */
(void)xv_set(panel, WIN_WIDTH, xv_get(textsw, WIN_WIDTH), NULL);
icon_image = (Server_image)xv_create(NULL, SERVER_IMAGE,
XV_WIDTH, 64,
XV_HEIGHT, 64,
SERVER_IMAGE_DEPTH, 1,
SERVER_IMAGE_BITS, icon_bits,
NULL);
/* associate icon with the base frame */
icon = (Icon)xv_create(XV_NULL, ICON,
ICON_IMAGE, icon_image,
WIN_CMS, cms,
WIN_BACKGROUND_COLOR, CMS_CONTROL_COLORS + 0,
NULL);
xv_set(frame, FRAME_ICON, icon, NULL);
window_fit(frame);
xv_main_loop(frame);
}
/*
* This routine gets called when a color selection is made.
* Set the foreground or background on the currently selected object.
* WIN_FOREGROUND_COLOR & WIN_BACKGROUND_COLOR allow the application
* to specify indices into the colormap segment as the foreground
* and background values.
*/
void
color_notify(panel_item, choice, event)
Panel_item panel_item;
int choice;
Event *event;
532 XView Programming Manual
Get Volume 7A: XView Programming Manual now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.