
set ::section_color "#93b1e9" 

puts {<html>
	<head>
		<title>Beginner's Xlib Tutorial</title>
	</head>
	<body>
		<H1>Beginner's Xlib Tutorial</H1>

		<i>By George Peter Staplin -- GeorgePS at XMission.com</i>
		<br>
		<i>Reviewed/Improved by: Colin McCormack</i>
		<br>

		<b>This document may be copied and distributed provided that the author is given credit.</b>
		
	<table>
}


proc section {name txt args} {
 regsub -all {@#(.*?)#@} $txt {<li><b>\1</b></li>} txt

 puts "
 <tr>
  <th align=\"left\" bgcolor=\"$::section_color\" id=[lindex $args 0]>$name</th>
 <tr>
 <tr>
  <td>$txt</td>
 </tr>"
}



section "Basic Overview" {<p>The intention of this tutorial is to teach you how to use the Xlib interface for programming X, and how to learn more so that you can write advanced applications that require the speed or power of Xlib.  This tutorial briefly covers the concepts behind:</p>

	<ul type="square">
		@#<a href="#types">fundamental types</a>#@
		@#<a href="#windows">windows</a>#@
		@#<a href="#pixmaps">pixmaps</a>#@
		@#<a href="#xdbebackbuffer">back buffers</a>#@
		@#<a href="#widgets">widgets</a>#@
		@#<a href="#gadgets">gadgets</a>#@
		@#<a href="#toolkits">toolkits</a>#@
		@#<a href="#events">events</a>#@
		@#<a href="#requests">requests</a>#@
		@#<a href="#colors">colors</a>#@
		@#<a href="#contexts">graphics contexts</a>#@
		@#<a href="#images">images</a>#@
		@#<a href="#eventusage">event queue usage</a>#@
		@#<a href="#help">help</a>#@
		@#<a href="#downloads">downloads</a>#@
	</ul>

<p>A simple example is given at the end that uses colors, draws rectangles, and handles events.</p>}


section "The Design of X" {
<p>X was designed to make communication between the application and the drawing layer over a network be abstract.  The user application is known as a client, and the program that draws what the client requests is known as a server.  The client and server can run different operating systems, have different processor types, and be over wide networks.  A client/application connects to a server using <b>XOpenDisplay()</b>.  <b>XOpenDisplay()</b> returns a pointer to a Display structure.  This display structure is passed to most Xlib calls to communicate with the server.
</p>
<p>A goal of X was to provide "mechanism and not policy."  This has allowed for a great deal of flexibility.  This design trait is apparent with window managers, and the fact that unlike some other systems the size of an application's toplevel window is a request, and not an expectation.  The window manager is free to position and resize a window as the user wants, or as the window manager deems best.  A variety of window managers are available with different interaction styles.  
</p>
<p>X only provides the base functionality for drawing widgets by design, so there are various toolkits built on top of <b>Xlib</b>.  This has allowed for a variety of implementations, such as Tk, Xt/Xaw, Motif, Qt, and Gdk/Gtk+.
</p>
}

section "Fundamental Types" {
<p>X has fundamental types that are used to represent drawable surfaces.  The following types are classified as <b>Drawable</b> types:
</p>
	<ul type="square">
		@#Window#@
		@#Pixmap#@
		@#XdbeBackBuffer#@
	</ul>
<p>
The above types and the <b>Drawable</b> type are <b>XID</b>s.  An <b>XID</b> is a unique integer that is usually an 'unsigned long'.  A client's <b>XID</b> is associated with a structure on the server's side.  A <b>Window</b> or <b>Pixmap</b> can generally be used in places where a <b>Drawable</b> is specifed as the argument type for an Xlib function. 
</p>
<p>
For debugging purposes it is often useful to use a pattern of <i>printf ("winid %lu\n", some_window);</i>
</p>
} types



section "Windows and Layers of Windows" {<p>A common misconception is that a window is only what is dragged around on a desktop.  X has layers of windows.  The root window is also known as the background window.  It can have a background image, animation, and other fun things.  Immediate children of the root window are generally reparented into window manager windows with titlebars, and buttons.  Most applications are made up of many windows, and windows within windows.</p>

<p>A client's Window is an <b>XID</b>.  On the server side, the window has a structure associated with it.  That structure contains the bytes for the content of the window.  Eventually the server's window structure content will be copied to the framebuffer of the video card by X, if the window is on screen, mapped, and is not obscured by other windows.</p>

<p>The content of a window is usually lost when it is unmapped or obscured or moved off screen.  Thus, application windows must be redrawn when they are visible again.  X sends an <b>Expose</b> event when a part, or all of a window has become visible again.  Note: a window attribute called backing store can reduce the need for some Expose events, but it increases the amount of memory required to run X applications, so not all X servers use or support it.
</p>
} windows


section "Pixmaps" {
<p>A <b>Pixmap</b> is a <b>Drawable</b> that is offscreen.   Like the <b>Window</b> type it is an <b>XID</b>.  The structure associated with the Pixmap's <b>XID</b> is stored on the X server.  A <b>Pixmap</b> can be drawn on, and then copied to a window.  It's also possible to copy a <b>Pixmap</b> to another <b>Pixmap</b>.  A <b>Pixmap</b> is useful for buffering a drawing.
</p>
} pixmaps

section "XdbeBackBuffer" {
<p>An <b>XdbeBackBuffer</b> is an <b>XID</b> type that is similar to a <b>Pixmap</b>.  The contents of a back buffer are used to implement double-buffering.  Quite often X applications don't use XDBE, so some flicker can occur.  <b>XDBE</b> is generally the best way to implement double-buffering.  The DBE man page documents it fairly well.  You will generally want to copy a <b>Pixmap</b> to an <b>XdbeBackBuffer</b> and then swap the back buffer for the window to achieve a smooth and flicker-free display.
</p>
} xdbebackbuffer

section "Definition of a Widget" {A <b>widget</b> is an object usually associated with a window.  It usually responds to input, and/or displays something.  A few simple examples of widgets are:
	<ul type="square">
		@#buttons#@
		@#menus#@
		@#scrollbars#@
	</ul>
Some of you may know of widgets as "components."} widgets


section "Definition of a Gadget" {A <b>gadget</b> is typically an item that is drawn onto its parent, and doesn't have a window for itself.  Text labels are implemented in some toolkits as <b>gadgets</b>.} gadgets


section "Toolkits" {
<p>An X toolkit is typically a library that is built on top of Xlib.  One of the first toolkits created is called <b>Xt</b> (X toolkit).  It provides handling of events, widget inheritance, geometry management, and numerous other features.  The first widgets built on top of <b>Xt</b> are known as the <b>Xaw</b> widgets or Athena widgets (from project Athena).  Several other widget sets have been created on top of <b>Xt</b>, such as <b>Xaw3D</b>, and <b>Motif</b> to name a few. 
</p>
<p>Some toolkits are synonymous with a widget set, such as <b>Tk</b>, <b>Gtk+</b>, and <b>Qt</b> (to name a few).  <b>Tk</b> is built on top of Xlib.  <b>Gtk+</b> is built on top of a layer called <b>Gdk</b>.  <b>Gdk</b> is built on top of Xlib.
</p>
} toolkits

section "Events and their place in X" {The X server sends messages known as events, to a client so that it may know of:
	<ul type="square">
		@#mouse button presses/releases#@
		@#keyboard key presses/releases#@
		@#a new window#@
		@#exposure of a window through raising it, uncovering it, or creating it#@
		@#the resizing of a window#@
		@#a property changing for a window (for example: the title)#@
	</ul>
The X server doesn't send a client every single event that occurs, unless explicitly told to.  To tell the X server which events an application needs the <b>XSelectInput()</b> function is used.  It takes a mask of OR'd flags.  For example: <i>XSelectInput (dis, win, ExposureMask | KeyPressMask | ButtonPressMask);</i>} events


section "The XEvent Structure" {An <b>XEvent</b> structure contains a union of structures for the various types of events.  Each event type contained, and the root <b>XEvent</b> is documented in a man page.  For example: <i>"man XButtonEvent"</i>}


section "The Event Queue" {When events are generated by user interaction or background tasks, they are placed into a queue that is specific to each display connection.  This queue of events is then processed by the client.  A common function for the purpose of retrieving and removing an item from the queue is <b>XNextEvent()</b>.  There are several other functions that deal with the event queue.  Some check for events without removing them from the queue, others check for specific classes of events.}


section "The Request Buffer" {Xlib functions that send requests are buffered for performance.  In many cases an <i>XFlush (dis);</i> is needed to force the buffered requests to be sent/flushed to the server.  Another related function is <i>XSync</i> which flushes and then waits until the processing of a request is complete.} requests


section "Colors" {<p>X has been ported to dozens of different kinds of machines.  From black and white displays, to 32-bit or higher displays.  Most common displays are now using 16, 24, or 32 bits for each pixel.  Older displays may only allow for 8 bits.  Colors may be represented differently depending on the system.  Some systems may have colormaps that retain a variable array of color cells, while others may have a static map of colors.</p>

<p>
<b>XParseColor()</b> is used to convert a symbolic name to a series of RGB values for an <b>XColor</b> structure.  <b>XAllocColor</b> is used after a color is parsed, and its RGB components stored in a structure.  <b>XAllocColor</b> will allocated a cell in the colormap for the display.</p>} colors

section "Graphics Contexts/GCs" {A graphics context (GC) is a structure that contains an X color, font, and a drawing function.  Drawing requires a <b>GC</b>.  In many cases a <b>GC</b> is also needed for copying drawings to a window or from a drawing to a drawing.  A <b>GC</b> is created with <b>XCreateGC</b>} contexts

section "Images" {<p>X uses an <b>XImage</b> structure for storage of regions of the display, that can be manipulated as sequential bytes of memory in the ->data member of the structure, or via the <b>XPutPixel()</b>/<b>XGetPixel()</b> functions.</p>

<p>The format of the XImage ->data member is dependent on the visual, and byte order of the display.  An X server may run on a Sparc&#153; while the client runs on an Intel Pentium&#153;. This means that the data will need to be reformated, because the byte order is different on these two processors.  If the data is not reformatted then the colors may be incorrect.  There are two formats for the <i>->byte_order</i> member; <b>LSBFirst</b> (least significant byte first), and <b>MSBFirst</b> (most significant byte first).  See <b>XPutImage</b> below.</p>

<p>The <b>XPutPixel</b> and <b>XGetPixel</b> functions properly handle the display's visual formats, and translate as needed.  However, the large number of function calls needed for setting/manipulating an image may cause performance problems if they are used.</p>} images


section "XCreateImage" {The <b>XCreateImage()</b> function is used to create an <b>XImage</b> structure that represents the image data.  This structure is then passed to the <b>XPutImage()</b> function to transfer the content to a <b>Pixmap</b> or <b>Window</b> or <b>XdbeBackBuffer</b>.  By default the <i>->byte_order</i> member of an <b>XImage</b> returned is in the format of the server (MSBFirst or LSBFirst (see above)).}


section "XPutImage" {The <b>XPutImage()</b> function is used to transfer an image to the server.  It also performs byte order conversions if the <i>->byte_order</i> of the <b>XImage</b> is different than the server's byte order.}


section "Finding the Byte Order" {It's probably best to set the byte-order in your configuration system for your software, before your main program is compiled.  A simple function that can be used to find the byte order is:

<pre>
int get_byte_order (void) {
 union {
  char c[sizeof(short)];
  short s;
 } order;
 
 order.s = 1;
 
 if (1 == order.c[0])
  return LSBFirst;
 
 return MSBFirst; 
}
</pre>
<p>
You may also be able to use the &lt;sys/endian.h&gt; header file if it's available.  
</p>
}


section "Mapping/Displaying Windows" {After a window is created it isn't visible on the screen.  To display a window the <b>XMapWindow()</b> function is used.  There are other functions that perform mapping as well, and they are documented in the man page for the <b>XMapWindow()</b> function.}


section "Unmapping/Hiding Windows" {The function <b>XUnmapWindow()</b> is typically used to unmap a window.  The contents of the display will be lost in most cases, and you will need to redraw it, after mapping it again (if you do remap in the future).}


section "XEvent Usage" {
<p>After calling <b>XSelectInput</b> and mapping a window on the screen the events that match the input mask will be queued.  To retrieve those events we can use several functions.  For this example we will use the most common; which is the <b>XNextEvent()</b> function.  Then we must switch on the event's type in order to find what the server has sent our client.  Finally we can find the structure member that has the information we want.
</p>

<p>For example to find which button was pressed in a window, that we have selected input from, we start by doing <i>man XEvent</i>.  We want the <b>XButtonEvent</b>'s member which the manual page says is <i>"xbutton"</i>, so thus far we have a name of: event.xbutton.  Now we need to find which member of the <b>XButtonEvent</b> structure contains the value of the button.  We find it via <i>man XButtonEvent</i> which states that the member is <i>"button"</i>.  Thus, to print the button that was pressed we would use <b>event.xbutton.button</b>.
</p>

<p>For example:</p>

<pre>
XNextEvent(dis, &event);
switch (event.type) {
	case ButtonPress:
		printf ("You pressed button %d\n", event.xbutton.button);
	break;
}
</pre>
In a real application we would loop, and most likely check other events.} eventusage


section "Helping Yourself" {The X man pages are vital when programming with Xlib.  A very common way to help yourself is to run <i>man -k keyword</i> or the apropos command.  The X headers can also be useful as a quick reference.  When the documentation isn't clear you may find it useful to consult the postscript documentation that is available with the X sources.  The X/Xlib sources are also useful when the documentation is unclear.  The Xlib sources can be found in <i>xsrc/xc/lib/X11</i>.  It's very useful to understand how to use grep when finding how a function is implemented, such as which file, and which line.  For example: <i>grep -n 'GC.*XCreateGC' *</i>}


section "Learn by Example" {The various utilities distributed with the X distribution are incredibly useful for learning how to use Xlib features, because they are generally concise and well engineered.  The popular toolkits are also good examples of how to use Xlib, but the complexity of such toolkits may require slow reading.}


section "Help!?  I'm stuck!" {This happens to most X programmers.  Some aspects of X may be confusing you, or you're uncertain of something, or misunderstand a key concept.  If the steps outlined in <b>Helping Yourself</b> above don't help then I suggest you study the Usenet archives for <b>comp.windows.x</b> at <a href="http://groups.google.com">Google Groups</a>  If you are lost amidst the archives, then try posting a question to <b>comp.windows.x</b>} help


section "The Downloadable Example" {The example was written by <i>George Peter Staplin</i> and tested in <a href="http://www.netbsd.org">NetBSD</a>.  It should compile with most systems.  Linux users (and possibly HPUX) may need to add -ldl to the compile target with -lX11 in the makefile, or alternatively use -static before -lX11.

<a href="Xlib_Beginner-4.tar.gz">Xlib_Beginner-4.tar.gz</a>} downloads

puts {
	</table>
	<hr size=1>
	<a href="http://www.xmission.com/~georgeps/"><i>George Peter Staplin's Home Page</i></a>}
puts " -- Last updated [clock format [file mtime [info script]]]"
puts {</body>
</html>}
