diff options
Diffstat (limited to 'vendor/x11iraf/xgterm/NOTES')
-rw-r--r-- | vendor/x11iraf/xgterm/NOTES | 959 |
1 files changed, 959 insertions, 0 deletions
diff --git a/vendor/x11iraf/xgterm/NOTES b/vendor/x11iraf/xgterm/NOTES new file mode 100644 index 00000000..f14fa19d --- /dev/null +++ b/vendor/x11iraf/xgterm/NOTES @@ -0,0 +1,959 @@ +xgterm.NOTES -- Some random design notes made while writing this code. Not +intended to be useful to anyone reading this code. + + +To do: + Object manager + add bitmap support + add event handling support + Gterm widget + add cell array + pixrect operations? + minor odds and ends + Gtermio + modify to use object manager + add messaging capability + GIO + add messaging capability + modify cell array support as needed + + +Pixmaps + cache by name + new entry replaces old + entries are never freed unless overwritten + for lookup, check cache first then look for file (normal resource + translation) + + typical bitmap: + + #define opendot_width 16 + #define opendot_height 16 + #define opendot_x_hot 7 + #define opendot_y_hot 7 + static char opendot_bits[] = { + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xc0,0x01, + 0x60,0x03,0x20,0x02,0x60,0x03,0xc0,0x01,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; + + types of bitmaps - bitmap, pixmap, cursor + + createBitmap name width height data + createPixmap name width height depth fg_color bg_color data + createCursor name source mask fg_color bg_color x_hot y_hot + + +Event handling + + addEventHandler <procname> <event-mask> [<event-mask>...] + userEventHandler {widget event-type time wx wy rx ry other} + where "other" is a event-specific list of fields + +Event structs + + event masks, event names are numerous + most events have these fields: + type, time, x_win, y_win, x_root, y_root other + other fields: + key: state (key or button mask), keycode + button: state (key or button mask), button code + motion: state (key or button mask), is_hint + crossing: mode (normal, grab, ungrab) + focus: mode (normal, grab, ungrab) + visibility: state + error: error_code, request_code, minor_code + + keycode|button|mode|state + +Event masks + + Button1MotionMask + Button2MotionMask + Button3MotionMask + Button4MotionMask + Button5MotionMask + ButtonMotionMask + ButtonPressMask + ButtonReleaseMask + ColormapChangeMask + EnterWindowMask + ExposureMask + FocusChangeMask + KeyPressMask + KeyReleaseMask + KeymapStateMask + LeaveWindowMask + NoEventMask + OwnerGrabButtonMask + PointerMotionHintMask + PointerMotionMask + PropertyChangeMask + ResizeRedirectMask + StructureNotifyMask + SubstructureNotifyMask + SubstructureRedirectMask + VisibilityChangeMask + +Event names + + ButtonPress + ButtonRelease + CirculateNotify + CirculateRequest + ClientMessage + ColormapNotify + ConfigureNotify + ConfigureRequest + CreateNotify + DestroyNotify + EnterNotify + Expose + FocusIn + FocusOut + GraphicsExpose + GravityNotify + KeyPress + KeyRelease + KeymapNotify + LeaveNotify + MapNotify + MapRequest + MappingNotify + MotionNotify + NoExpose + PropertyNotify + ReparentNotify + ResizeRequest + SelectionClear + SelectionNotify + SelectionRequest + UnmapNotify + VisibilityNotify + + +GTERM CELL ARRAY + + Colormap + use pseudocolor visual if possible + a fixed number of well defined sharable, read-only cells + a variable number of private read-write cells + the private cells are allocated at runtime when the + application allocates a colormap + the graphcap entry specifies the maximum number of private + colormap cells that can be allocated + a private colormap is used if the requested cells cannot + be allocated + there is only one colormap per gterm widget (if there are + multiple cell arrays they share the same colormap) + + Cell arrays (obsolete term?) + A cell array is mapping of an MxN array of 8 bit pixel values + to a region of the screen. + The pixel values in a cell array range from 0 to NC, and are + contiguous in that range. NC is the number of colors in + the gterm colormap. The first few values starting at 0 + are statically allocated and cell array pixels will + normally start at the first dynamically allocated value. + The cell array mapping defines the transformation used to paint + a region of the Gterm window from the cell array pixels. + Scaling and axis flipping are possible. + Cell arrays are defined and written to in separate steps. A + given write operation may modify only part of the MxN pixels + of the cell array. + + New operations + write colormap Writes N cells of the gterm colormap starting + at a given pixel value. + + define cell array Define transformation for cell array N. + Several cell arrays may be active. + + write cell array Write to a subregion of a cell array (operates + in cell array pixels, not screen pixels). + + Arbitrary regions of the colormap or a cell array may be + modified, allowing for very interactive operations. + + Binary pixel values must be encoded for transmission between the + client and server. The simplest encoding adds 040 to the value + of each pixel (byte), resulting in a printable byte stream. + Control codes may be used for compression schemes. + + Alternative scheme + Store cell array in off screen buffer. This is the same as + above except that in the above scheme the pixels are not + saved. + Modifying any pixel data, or editing the mapping causes the + affected region of the screen to be rewritten. + The advantage of this approach is that operations such as zoom + and pan can be implemented merely by modifying the mapping. + Given multiple cell arrays, one can also do blink, split + screen, etc. + Perhaps mappings should be separate from cell arrays. The + same array may be mapped to more than one region of the + screen, or a mapping may map portions of more than one + array. + Fundamental items are pixel array, mapping, colormap + + Pixmap operations + Create host or display pixmap + Destroy pixmap (or all such pixmaps) + Copy data to/from pixmap and screen + Read a file into a pixmap or series of pixmaps + Append pixmap to a file + + Should be combined with Obm capabilities for creating and + referencing pixmaps. + + Pixmap operations can be used for a number of purposes, + including movie making. + +Imaging Procedures + + Images (rasters) are implemented internally in Gterm using either + ximages or off screen pixmaps. Which format is used is decided at + raster create time and is controlled by a Gterm resource. This is + transparent to the client application. Currently only 8 bit rasters + are supported. + + GtRasterInit (gt) + GtAssignRaster (gt, raster, drawable) + GtCreateRaster (gt, raster, type, width, height) + GtDestroyRaster (gt, raster) + exists = GtQueryRaster (gt, raster, &width, &height) + n = GtNRasters (gt) + + GtWritePixels (gt, raster, pixels, x1, y1, nx, ny) + GtReadPixels (gt, raster, pixels, x1, y1, nx, ny) + pixmap = GtCreatePixmap (gt, src, x, y, width, height) + GtCopyPixmap (gt, pixmap, dst, x, y, width, height) + + GtWriteColormap (gt, first, nelem, r, g, b) + GtReadColormap (gt, first, nelem, r, g, b) + + GtInitMappings (gt) + GtCopyRaster (gt, rop, src,sx,sy,snx,sny, dst,dx,dy,dnx,dny) + GtSetMapping (gt, mapping, src,sx,sy,snx,sny, dst,dx,dy,dnx,dny) + GtGetMapping (gt, mapping, src,sx,sy,snx,sny, dst,dx,dy,dnx,dny) + GtEnableMapping (gt, mapping, enable) + GtRefreshMapping (gt, mapping) + + For the widget class we can also have commands to operate upon + pixmaps created by or written into a gterm widget. + + createPixmap name src [x y width height] + copyPixmap name dst [x y width height] + destroyPixmap name + + There should also be commands to delete pixmaps, write pixmaps to + files, and read pixmaps from files. + + The imaging routines operate in window or pixmap pixels. If a + window is resized, any mappings referencing the window are modified + to reflect the change in size. A query-size function is required + to pass the window size in pixels back to the client. A set-size + (resize window) procedure is also desirable to allow the client to + attempt to set the window to the optimum size for an image. + + The client uses a special library of procedures for imaging. These + use GIO escapes to communicate with the stdgraph kernel. The + stdgraph kernel uses special ESC codes to communicate with the + server. + + Applications which do only simple imaging will use GIO calls to + put a cell array and assign colors, using NDC coordinates for the + cell array mapping. More demanding applications that must operate + in pixel space, operate directly on image buffers, etc., will use + the GIO escapes directly. The stdgraph kernel will keep track of + the window size and perform NDC to pixel space conversions for the + put cell array call. + + +Implementation + + Code structure + + client + gio + gim + gki_escape + | (--IPC--) + stdgraph kernel + serial encoding + | (--IPC--) + gtermio + obm + gterm widget + + + Simple graphics applications use the high level GIO routines for + imaging. These include put/get cell array and put/get colors, with + gset being used to select colors for drawing. + + A small library of routines are used in client programs that have + more demanding imaging requirements. These are implemented using + GIO escapes and operate in pixel space, providing direct access to + the gterm imaging functions. + + The GIO escapes are processed by the stdgraph kernel. This uses ASCII + escape sequences defined in graphcap to communicate with the server. + The GIO escape codes are defined in lib$gescape.h. + + The gtermio code in Xgterm processes these escape sequences and + converts them into calls to the imaging routines in the gterm widget. + + The object manager also provides routines for calling the gterm + imaging routines from within UI code. + + The actual Xlib based imaging code is in the gterm widget. + + +Complications + + Cursor mode - wants to buffer all GKI instructions, including the + GIM escapes, some of which are voluminous. If any interactive image + editing, redrawing, etc. is done without initializing things, this + could be a lot of data. Would like cursor mode to work in the sense + that one can redraw the screen, zoom and pan. + + Cursor readback - for a cursor read within a mapped region of the + screen, the logical thing is to return raster coordinates rather + than Tek window coordinates. The server should make the mapping + transparent, so that the client gets raster coordinates regardless + of the image offset, scale, any axis flip, and so on. + + Cursor mode strategy - all GIM escapes issued by the client are + executed, but only setmapping instructions are buffered. During a + cursor mode redraw the setmapping instructions are edited to reflect + the cursor mode zoom/pan (this should be done by a GIM routine), and + retransimitted to the server at the time that they are encountered + in the display list. In most cases this will result in the image + data being redrawn at the appropriate time, e.g. after a frame draw + and area clear, and before any overlaid graphics is drawn. + + This requires that the server not initialize the imaging system on + every frame clear (probably the imaging subsystem should be + initialized when the cursor mode frame buffer is cleared, rather + than when the server screen is cleared). The space required to + buffer setmapping instructions is mimimal. A disadvantage is that + :.write/read will not save or redisplay image data. The major + advantage is that this provides full cursor mode zoom/pan capability + and is time and space efficient. + + To encapsulate manipulation of the GIM escapes in the cursor mode + code, a GIM (stdgraph kernel) routine should be called when a GIM + escape is executed to edit the instruction, if any, left behind in + the cursor mode buffer. This routine will have access to the + cursor mode frame buffer and will edit it as necessary, e.g. + deleting the instruction, replacing it, or editing earlier GIM + escapes in the same frame buffer. + + Cursor readback strategy - to solve this problem it appears to be + necessary to have the server pass back the "cursor number" in a + cursor read. When a cursor read occurs there is no way the client + can predict which cursor will be read; the server selects the cursor + depending upon the pointer location. The cursor number is the Tek + cursor, a raster cursor, or a region of a window. The WCS number + in the cursor value struct passed back to the client indicates + which cursor was read. + + +Timings + + Time to copy 631296 byte text file through a tty/pty + + lepus 8-9sec 70 Kb/sec + tucana 2sec 300 Kb/sec + + +Cursor Handling + + The general scheme is that when the cursor is read, the server + determines which raster the cursor is in and returns pixel + coordinates relative to this raster, regardless of how the raster is + mapped to the screen. The return cursor value includes the raster + number, pixel X and Y coordinates, and the keystroke (keycode) which + terminated the cursor read. + + Since the Tek cursor value struct does not provide adequate + resolution or any provision for the raster number, a custom cursor + return value is required. gtermio will continue to support a Tek + cursor, using a special escape to initiate a custom cursor read. + + gki_retcursor needs to be modified to provide more coordinate + resolution and to allow the "cursor" (raster) number to be returned. + + In cursor mode, WCS selection will use the CN/raster number instead + of screen position to determine the WCS to be used. A WCS maps a + range of world coordinates (e.g. image pixel coordinates) to a + viewport in NDC space. + + +Current cursor mechanism + + ESC SUB - initiate standard Tek cursor read + user types key to terminate graphics input mode + + server returns cursor value encoded as + key + hix; lox + hiy; loy + trailer1; trailer2 + x, y are encoded in Tek screen coordinates, 0-1023,0-779 + + gki_getcursor (fd, x, y, key, cursor) + stg_getcursor (cursor number) + call stg_readcursor to read cursor + returns GKI cursor value struct + cursor number, x, y, key + + stg_readcursor (cursor, x, y, key) + stg_rdcursor (tty, cursor, x, y, key, output_rc) + set raw mode + getc until pattern is matched + clear raw mode + stg_encode to decode cursor value + return x, y, key + + rcursor (fd, curval, maxch) + grc_cursor (rc, stream, x, y, key, ppos) (screen) + gtr_readcursor (stream, x, y, key) (screen) + gki_getcursor (fd, mx, my, key, 0) (GKI) + grc_scrtowcs (stream, x, y, xc, yc, wcs) (WCS) + grc_scrtondc (sx, sy, mx, my) (NDC) + wcs = grc_selectwcs (tr, mx, my) + grc_settran (w, ct) + grc_ndctowcs (ct, mx, my, wx, wy) (WCS) + format and return cursor value as a string (WCS) + + screen coordinates - workstation screen/window + NDC coordinates - normalized screen coordinates (no zoom) + WCS coordinates - world coordinates in active WCS + + WCS - max 16 per screen + wx1,wx2,wy1,wy2 range of world coordinates + sx1,sx2,sy1,sy2 viewport, NDC coordinates + xtran, ytran type of transformation in each axis + clip flag to clip at viewport boundary + + WSTRAN - cursor mode ndc-to-screen + vx1,vx2,vy1,vy2 range of NDC coordinates + mx1,mx1,my1,my2 range of GKI coordinates + + +Cursor mechanism with rasters + + The key concept underlying this scheme is that GKI (NDC) coordinates + refer to the "raster" the cursor is in, rather than to the screen, + hence are independent of the raster-to-screen mapping. One + logically draws into a raster, and any mappings defined on the + raster take care of rendering the graphics on the screen. A cursor + read returns both screen coordinates, used for cursor mode zoom/pan, + and image raster GKI/NDC coordinates. A special case is raster 0, + the screen (actually the drawing window), which is what GKI/NDC + coordinates always referred to in the past. When drawing into + raster 0 one is drawing directly to the screen. When drawing into a + raster, one is still drawing to the screen, but via any mapping or + mappings defined on the raster. + + Each raster has zero or more WCS associated with it. The WCS + associated with the raster defines a mapping between some world + coordinate system, e.g., image pixel coordinates, and NDC or + normalized raster coordinates. To get from world coordinates to + pixels on the screen, one converts from world coordinates to NDC + coordinates via the WCS, then from NDC coordinates to raster pixels, + then from raster pixels to screen pixels via the mapping. To be + more precise, the full transformation is as follows: + + GIO in the client: + world -> NDC + NDC -> GKI (clipped at viewport) + + Cursor mode in the CL: + GKI to "screen" (zoomed/clipped-GKI) coordinates + zoomed-GKI to Tek coordinates for serial protocol + + Gtermio code in the server: + Tek coordinates to raster pixel coordinates for current + drawing raster + + Gterm widget code: + raster pixel coordinates to screen pixel coordinates + via a mapping defined on the raster + repeat for each mapping defined on the raster + + Graphics drawing for raster overlays requires that the server treat + the input Tek encoded coordinates (1024x780) as normalized for the + current raster. If the raster number is zero the normal drawing + operation (into the display window) takes place. If the raster + number is nonzero any mappings defined on the referenced raster + define where the graphics is drawn on the screen. If a mapping is + disabled no drawing takes place. Graphics are automatically clipped + at the boundary of the destination rect defined by a mapping. + + In a cursor read operation, the server determines which raster if + any is mapped to the region of the screen the cursor is in. Both + screen (raster 0) and raster coordinates are returned using a + special cursor value struct. The cursor value return by RCURSOR + (hence =gcur and clgcur) returns the world coordinates defined by + the selected WCS for the current raster. If no WCS is defined NDC + coordinates are returned. If multiple WCS are defined for a raster + cursor mode selects the "nearest" viewport as it has always done + for screen coordinates. + + About the only alternative to the above scheme is to have the server + return raster pixel coordinates. The problem with this is that this + is inconsistent with the GIO graphics model, and the WCS cannot be + used to return world coordinates, or to draw graphics overlays. + + A complication with this scheme is that normally WCS 1 is used for + the screen (raster 0). Sometimes more than one WCS is used. Hence + to make a strict association between WCS number and raster number + would require that raster numbers be allocated accordingly in the + client. Also it is not clear what happens if there is more than one + WCS defined for a raster. To get around this problem a way is + needed to define which raster a WCS refers to. This can be done + without a (significant) protocol change by encoding the frame number + in the existing, little used WCS_CLIP field of the existing WCS + structure. + + +Colormap Sharing + + A gterm resource selects type of colormap: default, private, shared + default means default screen colormap, shared by all apps + private means colormap is used only by this gterm instance + shared means non-default colormap shared by multiple gterms + + In the case of the default colormap, read-only or read-write cells + are allocated out of the screen default colormap. This guarantees + that the colors of non-gterm windows will not be affected when gterm + colors are allocated, but it may not be possible to allocate all + requested colors, or having allocated these colors to a gterm + widget it may not be possible to run other applications. Use of + the default colormap is appropriate for applications that do not + use many colors. + + A private colormap is allocated and used by only a single gterm. + This guarantees that the expected number of colors will be available, + and prevents one gterm from changing another's colors. The main + disadvantage is that the window will go black (or whatever) when + the pointer is not in the window. + + A shared colormap is a non-default (custom) colormap shared by + multiple gterms. Allocation of colors is guaranteed, but when one + gterm modifies the colormap all gterms using the shared colormap + are affected. They are however still visible and if they contain + similar data the display may still appear reasonable. There can + be multiple shared colormaps, each with a different name. + + It is possible to use a trick to minimize colormap flashing when + private or shared colormaps are used. This works so long as the + default colormap has only a limited number of colors allocated, + and the gterm client needs only a limited number of colors (e.g. + 200 or so out of 256). The trick is to allocate as many colors as + possible from the default colormap, assigning the same pixels for + colors in the custom colormap. The default colormap is then copied + to the private (or shared) colormap, and the new colors are stored + in both colormaps. The newly allocated colors are then freed in + the default colormap. The custom colormap will then inherit most + of the color assignments of the default colormap, and in turn the + default colormap may still have the initial color assignments from + the custom colormap. + + Differences will appear as both colormaps change thereafter, but in + practice many color assignments are fairly static so colormap + flashing should be minimized. The default colormap can be updated + periodically by repeating the allocate, store, copy, and free + sequence, e.g., when the custom colormap is modified. + + Custom gterm colormap allocation strategy: in the normal case reserve + 216 colors for private use. The remaining cells are copied from the + default colormap to minimize colormap flashing. If the gterm client + requests more than 216 colors the full colormap is allocated. + + 0 - 37 copied from default colormap + 38 - 253 reserved for gterm client + 254 - 255 copied from default colormap + + The point where the gterm colormap starts (e.g. 38) should be defined + by a resource as there is no guarantee which end of the default + colormap static colors will be allocated at. + + if (use default colormap) { + allocate read-write cells + store colors + } else { + if (don't have colormap yet) { + map colormap name to atom + if (named gterm colormap not found) { + # Create gterm colormap. + open connection to display + create colormap, allocate all colors + call XSetRGBColormaps to set colormap property + call XSetCloseDownMode to make colormap permanent + close display + } else { + call XGetRGBColormaps to get colormap property + get colormap id + } + set colormap id for gterm window + call XSetWMColormapWindows to notify WM of custom colormap + } + store new colors in custom colormap + if (match colormaps) { + copy global cells from default colormap + attempt to allocate cells in default colormap + attempt to store new colors in default colormap + free cells allocated above + } + } + + If the gterm widget has a private colormap different than that of + its top level window, XSetWMColormapWindows must be called for gterm + window focus in/out events to indicate to the WM that the colormap + for the gterm window is to be loaded. + + +Windowing the Display + + Given a range of display pixel values and a normalized colormap, + apply a threshold/gain transformation to window the display (i.e., + write new screen colormap). This needs to be done in the UI to + provide acceptable interactive response. + + GtWindowDisplay (gw, offset, slope) + + offset (0.5 +/- X) center of windowed region + slope (+/- X) slope of transfer function + + The transfer function is applied to the normalized colormap + and the output colormap is written to the screen. + + To window over a greater dynamic range one must regenerate the + display pixel values from the raster or image (this can be done by + the client). For example, the client application can display a + histogram and the user can mark the region to be written to the the + gterm raster pixels. + + The marker facilities described in the next section can be used to + implement real-time display of the grayscale transfer function if + desired. The message facility could also be used to transfer the + image histogram and information about the histogram region loaded + into a raster, for use with the transfer function to generate a + full display of the grayscale mapping from disk image to screen. + + +Graphics Markers + + A "marker" is a graphics object, defined on a raster, which can be + created or destroyed, which can draw itself, or which can modify + (move or resize) itself in response to pointer events. Markers have + attributes such as the marker type (text, line, circle, polygon, + etc.), color, line width, center, width, height, visibility, and + sensitivity. Markers can accept callbacks which are executed when + the object is interactively moved or resized. + + Markers can be used to annotate a window, as if one were drawing + into a window. The chief difference between a marker and a simple + drawing operation (such as a polyline) is that markers are not just + lines on the screen, but actual objects capable of responding to + requests or taking independent action. + + Generic functions + + create + destroy + copy + set attribute + get attribute + raise, lower + + Generic attributes + + type + visibility + autoRedraw + sensitivity + foreground, background text markers + linecolor, linewidth + knotcolor, knotsize + fillcolor, fillstyle polygon markers + width, height + x, y + + Marker types + + text font, string + line vertices + box + rectangle + circle + ellipse + polyline vertices + polygon vertices + + Procedures + + gm = GmGreate (gt, type, interactive) + gm = GmCopy (gm) + GmDestroy (gm) + GmAddCallback (gm, func, client_data) + gm = GmSelect (gt, x, y, &what) + + GmMarkpos (gm) + GmRedraw (gm, func, erase) + GmRaise (gm, ref_gm|NULL) + GmLower (gm, ref_gm|NULL) + GmNotify (gm, events) + + GmAdd (gm, x, y) + GmDelete (gm, x, y) + GmMove (gm, x, y) + GmResize (gm, x, y) + GmRotate (gm, x, y) + + GmSetAttribute (gm, attribute, value, type) + GmGetAttribute (gm, attribute, value, type) + GmSetVertices (gm, points, first, npts) + npts = GmGetVertices (gm, points, first, maxpts) + + raster = GtSelectRaster (gt, st, sx, sy, rt, &rx, &ry, &mp) + GtMapVector (gt, mp, dir, st, sv, dt, dv, npts, clip) + + Markers operate in screen coordinates (raster 0). The SelectRaster + and MapVector routines may be used to convert to and from raster + coordinates if desired. + + Actions + create (type) + destroy marker + set (attr, value) + raise marker + lower marker + notify callback + + markpos marker + markposAdd marker point button1-down + redraw marker button1-up + add point + delete point + deleteDestroy point or marker delete or backspace + move marker + resize marker + moveResize point or marker button1-motion + rotate marker shift-button1 + + Marker specific functions (internal) + + bool = select (gm, x, y, &what) + classinit (gm) + markpos (gm, &rect) + redraw (gm, function) + + add (gm, x, y) + delete (gm, x, y) + move (gm, x, y) + resize (gm, x, y) + rotate (gm, x, y) + + The marker specific functions are the methods for each marker + class. The functions add, delete, move etc. merely edit the marker + descriptor. A separate call to redraw is required to redraw the + modified marker. + + Actions such as deleteDestroy and moveResize will select one of the + listed actions based upon the pointer coordinates. For example with + moveResize, if the pointer is in the center of a marker the entire + marker is moved, and if the pointer is near a point the point is + moved or the marker resized depending upon the type of marker. + + The default translations for these actions are shown at the right. + These translations are in effect only when the pointer is over a + marker that is sensitive and visible. The cursor will change to + indicate that the marker is active; the cursor type will indicate + whether the entire marker, a single point, or add-point will be + selected if button1 is pressed at that location. In addition, the + default translation for button1-down for the window is create + rectangle. Hence a rectangle object can be created and dragged out + with the left button at any time just using the default + translations. This can be used prior to executing a command to + indicate the region to be operated upon. + + Actions such as move, resize, rotate, etc. do not redraw the object + (unless autoRedraw is set). Instead, these actions do a GXor redraw + of the marker at the old location, edit the marker according to its + type, and then do another GXor redraw at the new location. When + tracking the cursor this produces a rubber-band effect. When + tracking completes (e.g., button1-up) the screen is refreshed at the + markpos position, erasing the old marker, any affected markers are + redrawn at the markpos position, and the edited marker is redrawn at + the new location. + + A Marker is created with GmCreate. If the interactive flag is set + a mode is entered where the mouse is used to set the initial + position and size of the object. The cursor changes to indicate + that the widget is waiting for input. The user moves the mouse to + the position on the screen where the object will go, clicks the left + pointer, and then does a drag to set the initial size and + orientation of the object. When the button is released the create + object operation is complete, unless the marker type is polygon in + which case multiple click-and-drag operations are required to + interactively define the polygon. + + If the create is not interactive, the GmCreate returns immediately, + and SetAttribute calls are used to set the object attributes and + then display the object. + + Once a marker has been created the sensitivity attribute controls + whether the object can be interactively moved or resized with the + mouse. If the marker is sensitive, when the pointer is placed + within the marker or near a vertex or edge the cursor will change to + indicate that the marker, vertex, or edge can be dragged to move or + resize the marker. Alternatively, the delete or backspace key can + be used to destroy the marker. This will not actually destroy the + marker, but will notify the client (via a callback) that the user + has requested that the marker be destroyed. + + When the mouse is near a sensitive marker a special translation + table defines the key or pointer bindings associated with the drag, + delete, etc. marker actions. Typical bindings would be left pointer + for create and drag, middle pointer to terminate a sequence such as + when drawing a polygon or to abort a create object, shift left + pointer to add a point to an existing polygon, and delete or + backspace to delete an object, or in add-point mode, the last vertex + in a polygon. + + All the gterm widget need do is, when there is one or more sensitive + marker in a window, track the cursor and load the marker translation + table when the pointer is over a marker which is sensitive. The + rest will be done by the marker actions. + + Markers can be used in UI code to provide a more general method of + position input than a cursor read, which can only specify a single + point. For example to input a rectangular region, one would do the + following: + + UI selects marker type rectangle + UI creates a rectangle marker in interactive mode + cursor changes to indicate create-object mode + user positions mouse and clicks left button + holding button down, user drags out the rectangle + button up terminates GmCreate + UI calls GetVertices and passes polygon back to client + UI destroys marker + + If desired, the client application can draw the polygon again + using normal graphics drawing commands (i.e., not as a marker). + + To mark a region on a raster in UI code: + + UI creates rectangle object in noninteractive mode + visibility and autoredraw are initially false + UI calls SetAttribute to set rectangle position, size, etc. + UI sets visibility attribute to cause marker to be drawn + + If the region is to be active, e.g. something should happen if the + user moves or resizes the region, then the sensitivity should be + set to true and a callback can be posted to take some action if the + region is changed. For example, this could be used to graphically + pan the image or adjust the colormap. + + Markers are only drawn to the screen, never to the screen pixmap. + Hence they can be erased by copying from the screen pixmap. If the + screen needs to be refreshed the markers are redrawn from the object + list maintained internally by the gterm widget. + + +Display of Pixel Dependent Information + + A common feature of image display UIs is the ability to display + information about the pixel under the cursor, either in sample mode + or continuously as the cursor is moved. For maximum flexibility + one must rely upon the client application to return information about + a pixel, since usually only the client has full access to the data, + and the significance of a pixel can be highly application specific. + An example of this is the display of the cursor position and pixel + intensity in user coordinates. + + To implement this feature we need the following capabilities. + + o The UI posts a callback procedure which is called whenever + the cursor moves, i.e., which receives pointer-moved events. + + o The UI obtains information about the pixel under the pointer + from the client. + + o The UI displays this information in a text object, either + overlaid on the image or in a separate text display area. + + The WS already provides the ability to post a callback to receive + pointer-moved events. What we need is an efficient way to obtain + information about the pixel under the cursor. Due to the overhead + of the client-server architecture, it is undesirable to query the + client every time we need information about a pixel. Hence, we must + get information for a block of pixels in single query and cache this + information in the server, sending another query only when the + pointer moves to a different region of the screen. + + This can be done by sending a request to the client to send a block + of information (text) for all the points in a grid in pixel space. + The client responds by generating the text as a message to a UI + parameter. The UI then needs a way to select text from the UI + parameter, and generate another query if the desired data is not + cached. + + The cached text consists of a sequence of lines of the form + + raster-x raster-y client-text + + The server will need to cache several such blocks of data, each with + a header identifying the raster number and the region of the raster + covered by the cached data. The object code in the server will + provide convenience routines for managing and searching this data. + + +Text Display Facilities + + Real-time display of pixel information requires some way of + displaying the text passed back by the client via the method + described in the last section. Text display can be done either + using a text widget ouside the gterm window, or using a text marker + if the text is to be overlaid on the image. An advantage of using a + marker for the text overlay is that since the marker is active, the + user can use the mouse to reposition the text on the screen. + + +Translations + + The Widget specifies the default translations. The Widget + translations resource specifies replacement, augment, or override + translations. Additional augment or override translations may + be specified in a function call (e.g. to cause the widget to invoke + an application specified menu via a translation). + + On a marker focusout, the widget must restore the gterm window + translations. + + At initialize time: + + if (translations resource defined) { + if (augment or override translations) { + defTranslations = compiled Gterm translations + compile auxiliary translations + set augment or override flag + } else + defTranslations = compiled translations resource + } else + defTranslations = compiled translations resource + + At focusout time: + + SetValues defTranslations + for (each auxiliary translation table) + augment or override widget translations + + Additional auxiliary widget translations can be specified with + GtAugmentTranslations or GtOverrideTranslations. + +oo |