Using colors to paint the rainbow
We finally see now how to draw using colors.
1. Color maps
In the beginning, screen controllers could only support a limited number of colors simultaneously, for example 256. Because of this, an application could not just ask to draw in a "light purple-red" color, and expect that color to be available. Each application allocated the colors it needed, and when all the color entries (256 colors) were in use, the next color allocated would fail.
Thus, the notion of "a color map" was introduced. A color map is a table whose size is the same as the number of simultaneous colors a given screen controller. Each entry contained the RGB values of a different color. When an aaplication wants to draw on the screen, it does not specify which color to use. Rather, it specifies which color entry of some color map to be used during this drawing. Change the value in this color map entry and the drawing will use a different color.
In order to be able to draw using colors that got something to do with what the programmer intended, color map allocation functions are supplied. You could ask to allocate entry for a color with a set of RGB values. If one already existed, you would get its index in the table. If none existed, and the table was not full, a new cell would be allocated to contain the given RGB values, and its index returned. If the table was full, the procedure would fail. You could then ask to get a color map entry with a color that is closest to the one you were asking for. This would mean that the actual drawing on the screen would be done using colors similar to what you wanted, but not the same.
On today's more modern screens where one runs an X server with support for 16 million colors, this limitaion looks a little silly, but remenber that still older computers with older graphics cards out there. Using color map, support for these screen becomes transparent to you. On a display supporting 16 million colors, any color entry allocation request would succeed. On a display supporting a limited number of colors, some color allocation requests would return similar colors. It won't look as good, but your application would still work.
2. Allocating and freeing Color Maps
When you draw using XCB, youcan choose to use the standard color map of the screen your window is displayed on, or you can allocate a new color map and apply it to a window. In the latter case, each time the mouse moves onto your window, the screen color map will be replaced by your window's color map, and you'll see all the other windows on screen change their colors into something quite bizarre.
In XCB, a color map is an ID structure "xcb_colormap_t"
In order to access the screen's default color map, you just have to retrieve the default_colormap field of the xcb_screen_t structure.
Note: an X server may support several different screens, each of which might have its own resouces.
In order to allocate a new colormap, we first ask the X server to give an Id to our color map by using the function "xcb_generate_id", and then create the color map by using "xcb_create_colormap".
To free a color map, it suffices to use the function "xcb_free_colormap".
3. Allocating and freeing a color entry
The informations related to a color are stored in the structure "xcb_alloc_color_reply_t". In order to request a color entry in a color map, the fucntion "xcb_alloc_color" first sent a request to inform the X server about color GRB value, then, the structure "xcb_alloc_color_reply_t" will be fetched by the function "xcb_alloc_color_reply"
X Bitmaps and Pixmaps
An X bitmap is a two-color image stored in a format specific to the X window system. When stored in a file, the bitmap data looks like a C source file. It contains members defining the width and the height of the bitmap, an array containing the bit values of the bitmap with the bit and byte order of LSB, and an optional hot-spot location for mouse cursors.
An X pixmap is a format used to stored images in the memory of an X server. This format can store both black and white images as well as color images. It is the only image format supported by the X protocol, and any image to be drawn on screen should be first translated into this format.
An X pixmap can be thought of as a window that does not appear on the screen, for many graphics oprations that work on windows will als work on pixmaps.
The type of X pixmap in XCB is an Id structure "xcb_pixmap_t".
The operations that work the same on a window or a pixmap take an xcb_drawable_t argument.
While, in Xlib, there is no specific difference between a Drawable, a Pixmap or a Window -- all are 32 bit long integers -- XCB wraps all these different IDs in structures to provide some measure of type-safety.
2. Creating a pixmap
Sometimes we want to create an un-initialized pixmap so that we can later draw into it. This is useful for image drawing programs (creating a new empty canvas will cause the creation of a new pixmap on which the drawing can be stored). It is also useful when reading variou image formats: we load the image data into memory, create a pixmap on the server, and then draw the decoded image data onto that pixmap.
To create a new pixmap, we first ask the X server to give an Id to our pixmap with the function "xcb_generate_id". Then the function "xcb_create_pixmap" is used to create a new pixmap.
3. Drawing a pixmap in a window
Once we got a handle to a pixmap, we can draw it on some window using the function "xcb_copy_area".
As you can see, we could copy the whole pixmap as well as only a given rectangle of the pixmap. This is useful to optimize the drawing speed: we could copy only what we have modified in the pximap.
Note that it is possible to create pixmaps with different depths on the same screen.
When we perform copy operations (a pixmap onto a window, etc), we should make sure that both source and target have the same depth. If they have a different depth, the operation will fail. The exception to this is if we copy s pecific bit plane of the source pixmap using xcb_copy_plane. In such an event, we can copy a specific plane to the target window (in actuality, setting a specific bit in the color of each pixel copied). This can be used to generate strange graphic effects in a window.
4. Freeing a pixmap
Finally, a given pixmap should be freed by the function "xcb_free_pixmap".