INTRODUCTION

The BeOS offers a variety of options for setting the colour space used by bitmap
images, and to render these images on the screen. These options are sufficient
for the vast majority of applications that render images onto the user interface.
However, there is one class of applications dealing with 8-bit greyscale images
for which graphics support is not yet adequate. An example of this type of
application is medical imaging, which requires high quality graphics rendering of
8-12 bit greyscale images for diagnostic purposes.

Although the BeOS supports 8-bit greyscale colour spaces, currently the screen
can only be configured to display colours in either the B_CMAP8, B_RGB16, or
B_RGB32 colour spaces. In the 32-bit colour space there are a sufficient number
of possible grey levels so that an 8-bit greyscale image can be rendered
without loss of information. In the 8-bit colour map however, there are only
36 unique grey values, so rendering an 8-bit greyscale image using this colour
map will result in a "banding" effect where there is a noticeable difference
between adjacent grey values.

To address this problem, I have developed a little utility called BeGrey which is
capable of modifying the default 8-bit colour map to include a greater number of
unique grey values. This allows an application running in a lower screen depth
to take advantage of a full range of grey values for displaying greyscale images
without having to resort to using a full screen mode (such as a BWindowScreen).

Since the screen must be shared by other applications, and to display the BeOS
user interface itself, it is not possible to indiscriminately change the default colour
map. There are many user interface components such as bitmaps and icons which
map directly into the colour map, and rely on the fact that the colours there will
produce the desired result on the screen. When changing the screen colour map,
it is inevitable that user interface will change in appearance, but care must be
taken to ensure that visual integrity is maintained. By this, I mean that any user
interface component on the screen should retain the visible contrast between
the various colours that it uses.
For example, if an icon contains a bright yellow foreground on a dark blue
background, it would be unacceptable to map both of these colours to the
same intermediate shades of grey - the colour contrast would be lost.

Also, in many cases, it is not necessary to map all of the colour map to shades of
grey in order to display greyscale images. When the number of unique grey levels
on the screen is sufficiently high, the user will no longer detect any "banding effect"
as adjacent grey levels become indistinguishable on the monitor. Therefore, I have
provided a configurable interface to the colour map utility in order to set the
number of unique grey levels which are required. Once there are a sufficient
number of grey levels, the remaining entries in the colour map may be left to their
original values.

In order to minimise the effect of changing the colour map on the user interface,
the colour map is edited in a specific sequence. This is done in order to protect
certain colour entries from being changed when the number of requested grey
values is not too high. Specifically, the following colours are protected in the
following order:
- the background colour of the current workspace
- the colours used in window title tabs
- the blue and red colours in the Be logo
- the colours used for folder icons in the Tracker
- other primary colours (RGB) in decreasing intensity
- secondary colours (CMY) in decreasing intensity

The colour map entries of the list above are reserved, moving down the list as
long as the number of remaining entries is greater than the number of requested
grey values. Then the remaining colour map entries are modified while maintaining
their relative perceptual brightness. For example, light colours are mapped to
light shades of grey while dark colours are mapped to dark shades of grey.

In this way, the number of grey shades can easily be increased to 160 or more
without severely influencing the appearance of most of the user interface.


INSTALLATION

BeGrey will run in whichever folder it finds itself, and can be launched from the
command line, or from the user interface. On systems with the primary task of
viewing greyscale images, it might be useful to launch BeGrey from within the
UserBootScript file.

USAGE

The utility can be run from the command line, and has a single argument: the
number of desired grey levels. This value can vary between zero and 256, although
any number less than 37 will result in the default colour map. If no command line
parameter is given, or if launched by double clicking on the application's icon,
then a graphical interface is presented. This interface consists of an alert
window with a slider used to set the number of grey values in the colour map, and
a button to apply the changes. At the bottom of the window is a greyscale wedge
showing the current available shades - at low number of unique grey levels, the
banding effect is clearly visible here.

Once the desired number of grey levels is set, and the "Apply" button pressed,
BeGrey modifies the colour map, fills in the "inversion map", and optimises the
"index map" arrays in the system colour map. Refer to the BScreen class
documentaion in the BeBook for an explanation of these arrays.  Finally, the
screen blanks to force the user interface to be updated and voila - the colour
map has been changed.

The number of grey levels which are required for any particular application can
depend on many factors, so the choice of how many greys to set is left to the
user. I would like to be able to offer real-time feedback to the user so that
the colour map changes while the slider is manipulated, but this is not currently
possible due to the mechanism used update the graphics card colour palette.
I may tackle this issue in a future release.

In 15 or 16-bit colour spaces, the modified colour map will have no effect (except
for changing bitmaps drawn in 8-bit spaces). Applications will not be able to take
advantage of the higher number of available grey shades. In these colour spaces,
the maximum possible number of grey shades is 32 since only 5 bits are available
for each of the RGB components.

From an application, in order to access all the grey shades for image display, do
not use the BScreen::IndexForColor function. This will only return 32 different
indices (like a 15-bit colour space). Instead, read the BScreen::ColorMap entries,
and generate a lookup-table for each of the available grey shades. Then create
a display BBitmap by passing your raw greyscale data through this lookup-table.
The values of the pixels in the BBitmap will contain the index into the BScreen
colour map. 

KNOWN BUGS

* Open applications don't get proper update messages after the colour map
has been changed. Windows will refresh properly when they next receive an
update event invalidating the window's contents.

* Launching BeGrey, then changing workspaces, dragging BeGrey to the new
workspace and applying a modified colour map there corrupts the display. In this
case, change back to a different workspace using a Command-Fkey, and close
BeGrey to recover the screen.
To resolve this for now, close the BeGrey app BEFORE changing workspaces,
and open a new copy in the new workspace.

* In PR2, BeGrey can trash the Deskbar application, but I believe that this was a
bug in Deskbar which has been corrected in R3. To avoid this problem in PR2, I have
managed to launch BeGrey from the system BootScript (after the Appserver is
loaded, but before the Deskbar is launched) but please don't tell anyone at Be that
I did this. Deskbar runs fine once BeGrey has done its thing.

REVISION HISTORY

* version 0.7 May 2, 1998:
-First version that actually did what I wanted it to do.

* version 0.8 May 11, 1998
-Fixed bug which caused desktop color to change after the colour map was set
to 256 greys, and then reduced to a slightly lower number. Now the desktop
colour will remain unchanged for any number of grey levels up to 255. This is
still a problem when switching workspaces though.

* version 0.9 B May 20, 1998
-Made screen blank less noticeable by trying to maintain the current screen
resolution when changing the graphics card's colour palette. Before, a fixed
screen resolution was used, and this caused some monitors to lose synch
and flicker while the screen was blanking.
-Beta version unleashed on an unsuspecting public.

CONTACT

For more information, praise, flames, or bug reports, please contact me at:

craig@cvc.uab.es
Craig D. von Land

