Graphics are an important feature of Xconq. Although not every interface needs it -- for instance the curses interface is limited to drawing two ASCII characters for each cell, and its "graphics" code just has to choose which two to draw -- nearly all players prefer a graphically rich display.
Xconq graphics basically consists of the drawing of a number of small images into a map or view window, along with some geometric shapes (lines, rectangles, etc) and text.
Most of a map's layout can be handled by common code found in
`kernel/ui.c' and `kernel/ui.h'. The common code does the
tricky computations, and the platform-specific drawing code just needs
to do the rendering proper. For instance, xform_cell
takes the
location of a hex cell and returns the pixel coordinates of its upper
left corner. The main structure defined by `ui.h' is the viewport
type VP
, which is a complete description of a viewport into
the world.
While the layout code decides placement and ordering, the images contain the actual pixels that will go onto the screen. The Xconq image machinery is somewhat complicated, since the game designer is only required to specify an image by name; it's up to the program to locate the image data, to process the images into a form that may be efficiently rendered, and to choose the best image for the view's magnification.
Image data may come either from a standard image format file, such as a GIF, or from Xconq's own GDL-based format, which was designed to handle large numbers of small images efficiently. You may also add platform-specific file format handling, such as resource files for Mac and XPMs for Unix.
Internally, each image family is a list of images of different sizes. Each image may include an array of subimages, of a size depending on the image's type. For instance, a connection image type has 64 subimages, one for each combination of connections around the six edges of a hexagon.
Platform-specific handling should come as late as possible, ideally just before the display needs an image. It may be that a player never needs a particular unit type, or that the player never uses a particular magnification; so you can save some startup type and memory consumption by only doing conversion when absolutely necessary.
If a requested image family cannot be found, the standard image setup code in `ui.c' will create a substitute family (usually by doing a sort of "bar code" of the unit or terrain type number), and mark it as ersatz. The interface should still warn that the image family could not be found though. In the case of terrain, where solid colors may be used, the interface should warn if neither color nor image is available.
No graphical icon should be drawn smaller than about 8x8, unless it's a text character drawn in two contrasting colors.
Interfaces should cache optimal displays for each mag, not search for best image each time.
Imaging variations can be randomly selected by UI, but must be maintained so redraws are consistent.
Draw partial cells around edges of a window, to indicate that the world continues on in that direction.
Interface needs to draw only the terrain (but including connections and borders) in edge cells.
Could draw grid by blitting large light pattern over world, do by inverting so is easy to turn on/off. Do grids by changing hex size only in unpatterned color?
Draw large hexagon or rect in unseen-color after clearing window to bg stipple (if unseen-color different). Polygon should be inside area covered by edge hexes, so unseen area more obvious. Make large unseen-pattern that includes question marks?
If picture not defined for a game, use some sort of nondescript image instead of leaving blank. (small "no picture available" for instance, like in yearbooks)
To display night, overlay a black mask on the terrain, both cell and linear. World is totally lit if dimensions < half of world circumference and all six corners of hexagon have same lighting. If world totally dark, can draw darkening mask once for entire map.
To display elevation, use deep blue -> light gray -> dark brown progression, and/or contour lines.
If multiple connection or border types, the interface should draw them offset slightly from each other.