$f16=16 s=1.1 $d %=$w$h $16 $a top=4; left=10; line=96 $a just=1; nls=1.4 $a invert=0; cap=0; capsh=0 $b6 $l1 LASER PRINTER CONTROLLER $b2 $l1 GENERAL-PURPOSE PROTOCOL $b6 $l0 1. FUNCTION 2. PRINCIPLES OF OPERATION 3. ASCII CONTROL CHARACTERS 4. CONTROL SEQUENCE FORMAT 5. BASIC OPERATIONS 6. FONT DEFINITION 7. GRAPHICS $b10 $l3 Hamish Dewar Igor Hansen September 1983 $n $a pageno=1 $l1$h 1. FUNCTION $p The general-purpose protocol defines a format for the presentation of text to the laser printer controller. It is designed to give access to the special facilities of the printer through the medium of control sequences embedded in the character stream which constitutes the text to be printed. The protocol allows the full capability of the printing device to be exercised, including precise positioning effects and the creation of arbitrary dot patterns, while permitting ordinary text to be presented with a minimum of protocol overhead. $p Because the control sequences are introduced by the ASCII Escape character, this protocol places no restrictions on the use of the full ASCII printing set and standard format effectors in the text itself. The ASCII printing set may be extended to a full 8 bit set, provided that the communication medium permits transfer of arbitrary byte values. This permits any single font to contain up to 223 printing characters (256 less 32 controls and space). $p Among the effects which may be achieved by means of control sequences is the selection of one of a number of alternative protocols. These give access to emulation modes and to a text-formatting mode, on a per-document basis. The text-formatting mode provides the facilities of pagination, line-filling and justification, but it also provides access to all the special capabilities of the printer. It is entirely text based and is designed for user created files. By contrast, the general-purpose protocol, based on control sequences, is designed for files created by utilities such as spoolers and formatters. $n $l1$h 2. PRINCIPLES OF OPERATION $p The basic function of the printer controller is to generate images of pages to be printed in the form of a matrix of pixels in which a pixel is 'on' or 'set' if a dot is to appear in the corresponding position on the physical page and 'off' otherwise. For the xxxxxxxx printer, the physical page size is A4 and, allowing for mandatory hardware margins, this gives a maximum page area of 7.8" across and 11.5" down. The dot density of the printer is 300 dots to the inch, so that the matrix of pixels is 2340 across and 3450 down, a little over 8 million pixels in total. $p The print image is created by the sequential execution of actions which are invoked by the character stream sent to the controller. The conceptual model is that of writing or plotting: there is a current operating position which determines where the next information is to be written; the act of writing automatically alters the current position in a precisely defined way; and there are also explicit positioning actions. The effect of writing is cumulative, which means that over-printing effects can readily be achieved. The controller places no restrictions on the order in which actions have to be executed. The current position may be set to any point in the image at any time. $p The controller permits a number of 'pages' to be set up on a single sheet of paper, through a facility to define individual page formats within the full print area. In the subsequent description, the term 'sheet' or 'physical page' will be used for the full print area and the term 'page' by itself for a page format within this print area. $p In the absence of control sequences, plain text is printed in a fashion similar to the operation of a conventional printer. A default page format and font are used. Consecutive printing characters are placed directly in the page format in adjacent positions. Line breaks are caused by the appropriate ASCII format effectors (see following section). Over-long lines are truncated, not wrapped. Page breaks are caused either by reaching the bottom of the current page or by receipt of an ASCII Form Feed character. $p More generally, the principle of operation of the controller is: $a tab=10; indent=1 $b actions are taken on the basis of the incoming characters $b the effect of each action depends on the current environment as well as the character involved $b as well as a printing effect the action usually also modifies part of the environment for subsequent actions $b control sequences usually do not have a printing effect but modify aspects of the environment. $a indent=0 $n $p The most important components of the environment are:- $l0 the current page format the currently selected font the current space increment the current feed increments the current position on the page $p The current position identifies a particular point within the page format. It is represented by two values, one for the vertical or Y axis and one for the horizontal or X axis. Associated with the current position is a state variable which records whether the position was established implicitly by character interpretation or explicitly by control sequence. The main function of this state variable is to determine whether automatic vertical movement is required at the start of a line of text. Because the page formats include the possibility of printing along the length of the paper as well as across the width, it is important to understand that the terms 'vertical' and 'horizontal' are used in a relative sense. The same applies to the terms 'top', 'bottom', 'left' and 'right'. The interpretation of the positioning commands does not depend on the absolute values of these co-ordinates or the direction of incrementing, so these are not defined. $p Within any selected font, an individual printing character denotes a particular pattern of dots. The effect of the occurrence of the character in the text is that the associated pattern of dots is placed in the page image at the point identified by the current position and then the current position is moved to the right by an amount determined by the symbol -- the character width. $p Considered at this level, a font is an ordered set of character patterns and associated widths. The ordering corresponds to the sequencing of characters in the character set. The printer pre-supposes either a standard or an extended ASCII coding in the limited sense that the interpretation of the control characters (decimal 0-31) and the space character (32) is fixed. The remaining character codes, from decimal 33 to a maximum of 255, have a graphical interpretation as determined by the font definition. Not all fonts provide a complete set of characters. If a printing character code (33-255) occurs which is not defined in the currently selected font, it is ignored. As well as a width, each character pattern has associated with it two positioning values which control the placing of the character relative to the current position. For all standard fonts, these values are chosen so that the current position is treated as the leftmost point on the Base-Line. That is, the body of the character extends up from the current position, and any descender extends below it. $p A complete font has associated with it an ascender height and a descender height, which establish the default vertical movements when printing text in that font -- the feed increments. The feed increments may also be set by an explicit control sequence. A font also has a space width, which establishes the horizontal increment to be caused by the ASCII space character (decimal 32) for that font. The space increment may also be set by an explicit control sequence. $p The way in which lines of plain text are laid out on the page may now be described more precisely. When a character is received at the start of a page or line, without any explicit vertical movement having been specified, the availability of sufficient space between the current vertical position and the bottom of the page is checked, and if there is not, a Form Feed function is executed. In all cases, the current position is then moved down by an amount equal to the ascender feed increment minus one. A Line Feed function completes the two-stage vertical movement by moving down by an amount equal to the descender height plus one. $n 3. ASCII CONTROL CHARACTERS $p The following control characters have a significance within the general-purpose protocol. $a tab=6,10,20; indent=2 $b2 $i-2 CR $t+ RETURN $t+ (decimal 13) $b CR causes the current position to revert to the leftmost point within the current page format, without change of vertical position $b0 (this code is treated as equivalent to the character pair CR LF if the Auto-LF option is set) $b $i-2 LF $t+ Line Feed $t+ (decimal 10) $b This code first causes the vertical position to be moved down by the ascender feed increment minus one, in just those circumstances in which the appearance of a printing character would cause this effect. Then, in all cases, the current position is moved down by the amount of the current descender feed increment plus one. In the absence of Auto-CR, there is no change of horizontal position. $b0 (this code is treated as equivalent to the character pair CR LF if the Auto-CR option is set) $b $i-2 BS $t+ Back Space $t+ (decimal 8) $b BS causes the horizontal position to be adjusted to the left by an amount equal to the current space increment. If the movement would imply a position outside the current page limits, the position is set to the leftmost point within the page. $b $i-2 FF $t+ Form Feed $t+ (decimal 12) $b FF causes termination of the page defined by the current page format and a new page to be started. Depending on the page formats involved, terminating a page may or may not involve printing a sheet of paper. As a safe-guard, the controller discards multiple form feeds which would cause more than one blank sheet to be produced. The current position on the new page is set to the top left printing position. $b $i-2 ESC $t+ Escape $t+ (decimal 27) $b ESC is used to introduce control sequences (see next section). $b $i-2 NUL $t+ Null $t+ (decimal 0) $b The Null character is ignored. $b2 $a indent=0 (additional control characters may be defined in due course) $b0 (the presence of an undefined control character in the character stream is a data error) $n $l1$h 4. FORMAT OF CONTROL SEQUENCES $p All control sequences start with a fixed control sequence initiator, hereafter designated LEADIN. For full compatibility with ANSI control sequence standards, LEADIN should consist of the character pair Escape followed by left square bracket. However, the controller permits omission of the second character, so that Escape alone may be used. $p Depending on the individual control sequence, LEADIN is followed by a variable number of numeric parameters, and the control sequence is terminated by a function-code, which is always a letter. In other words, LEADIN and the function-code act as a sandwich for the parameter information. The semi-colon character is used as a separator between multiple parameters. $p Numeric parameters are presented in free format decimal. Negative values are indicated by a preceding minus sign. They may, where non-integral values are appropriate, contain a decimal point. When a value is used to specify a measurement on the page, it is by default interpreted as a number of pixels. However, in these cases, the number may be followed by a double-quote symbol to indicate that the value should be interpreted as inches. $n $l1$h 5. BASIC OPERATIONS $a tab=4; indent=1 $b2 $l1 LEADIN $h(height); $h(width) P start page $b The effect of the P control sequence is to define and start a new page format. The current position when the sequence is executed is taken as the top left position of the page, and the parameters define the height and width of the page respectively. They may be specified in inches rather than pixels, using the double-quote convention (eg 7.25"). Subsequent printing takes place within the page thus defined until an 'end page' sequence or a Form Feed is encountered. Page formats may be nested one within the other, to a maximum depth of eight. $b It is legitimate within the protocol for a movement to cause the current position to move out of the page limits on the right-hand or bottom edge. Any printing operations specified when the current position is off-page are ignored. However the current position is not permitted to go off-page at the left-hand or top edge, and any movement which would imply this is limited to prevent it. $b2 $l1 LEADIN E end page $b The 'end page' control sequence causes the current page to be closed and the page format active when that format was started to be re-instated. $b2 $l4 LEADIN $h(offset) A move up LEADIN $h(offset) B move down LEADIN $h(offset) C move right LEADIN $h(offset) D move left $b These control sequences cause the current position to be modified by the amount specified by 'offset' in the direction denoted by the control code 'A' to 'D'. $b2 $l1 LEADIN $h(degrees) R rotate $b The current direction of printing is altered by rotation through the number of degrees specified. Only multiples of 90 degrees are valid for the present controller. The current position does not change, though its significance is altered. The significance of 'top', 'bottom', 'left' and 'right' are similarly altered. $b2 $l1 LEADIN $h(font-number) F select font $b The font denoted by the specified number becomes the current font. If the current space increment has not been explicitly set since the last 'start page' command, it is set to the space-width of the font. Similarly, if the current feed increments have not been explicitly set since the last 'start page' command, these are set to the heights of the font. There is no change in the current position. $b If there is no defined font for the number specified, all subsequent printing characters up to the next valid font selection are ignored. $b2 $l1 LEADIN $h(space-width) H set space increment $b The current space increment is set to the value specified. $b2 $l1 LEADIN $h(ascender-height); $h(descender-height) V set feed increments $b The current line feed increments are set to the values specifed. $a indent=0 $n $l1$h 6. FONT DEFINITION $p The controller has available a number of built-in fonts and the protocol permits the definition of additional fonts. A distinction is made between $h(basic) fonts and $h(derived) fonts. The basic fonts contain direct specifications for the pattern of each character included in the font. Derived fonts specify the characters they contain by selection from the basic fonts. Basic fonts are identified by an alphabetic name, which may be up to 12 characters long. Derived fonts are identified by a number in the range zero to 63. $p Typically derived fonts are defined for individual documents, and the derived font numbers may be freely assigned and re-assigned (with the exception of fonts 0 and 1). $p Font selection is in terms of derived, not basic, fonts. Hence the numerical parameter to the 'select font' control code. Font zero is always pre-defined in terms of a specific basic font which is used as the default for normal (listing) operation in A4 format, and font 1 is defined as a reduced version of this basic font for use in the double A5 format. $p The simplest form of definition of additional derived fonts is to identify them directly with a complete basic font. They may also be defined partly in terms of one basic font, and partly in terms of others. Derived font characters may also be defined as the result of applying an operation to a basic font character, for example scaling, emboldening, or slanting. $p The representation of basic fonts takes one of two forms: either a bitmap representation of the dot pattern or a representation as a set of line vectors. The controller supports both forms of representation and corresponding definitions. In general, the line vector representation is more flexible: characters thus represented may be scaled by arbitrary factors, whereas bitmap representations may be scaled only by integral factors; the line vector form is also more economical in storage. On the other hand, the bitmap representation gives completely precise control over the exact final pattern for each character. $p There is a single control code ('S') for font specification, the various cases being distinguished by the first parameter. This control sequence continues after the code letter 'S' with the font-name. $a indent=1 $n $l1b Basic Font Definition $b $l1$h (a) bitmap representation $b $l1 LEADIN $h(0); $h(ascender-height); $h(descender-height); $h(space-width) S font-name $b The parameter $h(ascender-height) defines the vertical envelope above the Base-line for all the characters in the font and the parameter $h(descender-height) defines the envelope below the Base-line. $h(Ascender-height) must be strictly positive. $h(Descender-height) may be zero. These values are used by the controller when processing running text (in the absence of explicit commands) to determine line spacing and the position of the Base-Line for characters in that font. $b The parameter $h(space-width) defines the default value for the width of a space when this font is being used. $b The extra parameter $h(font-name,) which follows the control code 'S', is the name of the font and may consist of up to 12 alphanumeric characters. Leading $h(spaces) are ignored and the name is terminated by LF (or CR if Auto-LF is set). $a indent=0 $p The line containing the font specification control sequence is followed by a sequence of character definitions. Each of these takes the form of a character definition control sequence followed by hexadecimal values representing the strips of dots making up the character. $a indent=1 $b $l1 LEADIN $h(char-value); $h(height); $h(down-offset); $h(width); $h(left-offset) K $b The parameter $h(char-value) is the ASCII character value in decimal. It must be in the range 33 to 255. The remaining parameters are all in units of pixels: in this case the option of specifying the values in inches is not available, since the values must be precise. $h(Height) is the number of horizontal strips making up this character; $h(down-offset) is the number of strips out of the total which are to be displaced below the Base-Line (to form a descender); $h(width) is the number of pixels in each horizontal strip, which also defines the effective width of the character for purposes of composition; $h(left-offset) is the amount by which the whole matrix of strips is to be displaced to the left of the origin (for characters which may overlap preceding characters). $b Following the control sequence comes a sequence of variable length hexadecimal values, $h(height) in number, each defining a horizontal strip of dots, $h(width) in number. The order of the strips is top to bottom. The number of hexadecimal digits required to represent a strip is the smallest number which multiplied by 4 is greater than or equal to the width specified for the character. This is a maximum: trailing zeros need not be included provided that the hexadecimal value is terminated by a space or format effector. If the maximum number of digits is present, there may be such a terminator but need not be; that is, the values can simply be run together. The digits correspond to a successive groups of four dots starting at the left of the strip, most signficant bit leftmost, and bit set corresponding to a dot. $n Here is a possible definition of an equals-sign with $h(height) 10 and $h(width) 19: $l0 LEADIN 61;10;0;19;0K 3FFF8 3FFF8 00000 00000 00000 3FFF8 3FFF8 00000 00000 00000 or, more compactly: LEADIN 61;10;0;19;0K 3FFF83FFF80 0 0 3FFF83FFF80 0 0 $b The font definition is terminated by any control sequence other than 'define character' (control code 'K'). $n $l1$h (b) line-vector representation $b $l1 LEADIN $h(1); $h(ascender-height); $h(descender-height); $h(space-width); $h(scale) S $b The first parameter indicates the line-vector type of font specification. The next three parameters have the same significance as for bitmap fonts. The parameter $h(scale) is an internal scaling factor which is to be applied to each character in the font in combination with any external scaling factor. A value greater than unity implies a scaling up and a value less than unity a scaling down. For each of the individual characters in the font, there is a control sequence followed by a series of co-ordinate pairs which trace out the shape of the character. $b $l1 LEADIN $h(char-value); $h(height); $h(down-offset); $h(width); $h(left-offset) K $b These parameters have the same significance as those for bitmap characters, bearing in mind the possibility of arbitrary scaling being applied. The co-ordinate system used in defining the shape of the character is internal to the character definition and is interpreted (when the character is drawn) relative to the position determined by current position offset by $h(down-offset) and $h(left-offset.) All co-ordinate values are non-negative and, in accordance with standard graphics practice, the 0,0 point corresponds to the bottom left position. $p The co-ordinate pairs are interpreted sequentially as tracing out a path as a sequence of point-to-point lines or point-to-point moves (as with plotter 'pen-down' or 'pen-up' modes). The initial position is the 0,0 point. The horizontal co-ordinate is presented first, and the convention is adopted that a move as opposed to a line is indicated by preceding this value by a minus-sign. The last co-ordinate pair is indicated by the convention of preceding the final (vertical) value by a minus sign. $p The font definition is terminated by any control sequence other than 'define character' (control code 'K'). $n $l1b Derived fonts $b $l1 LEADIN $h(font-number); $h(ascender-height); $h(descender-height); $h(space-width) T $b The effect of this command is, first, to discard any existing definition of the derived font specifed by $h(font-number) and then to define the overall attributes for the font, on the same principles as for basic fonts. $b The 'T' control sequence is followed by a number of derived character specifications. $b $l1 LEADIN $h(char-value); $h(number); $h(base-char-value); $h(scale); $h(op); $h(amount) I font-name $b The effect is to define one or more character values in the derived font by reference to the same number of characters in a base font. The parameter $h(char-value) determines the first character in the derived font, and $h(base-char-value) the first character in the base font. Number indicates how many consecutive character values are involved. $h(Scale) denotes a scaling factor, which must be integral if the base font is a bitmap one. The parameter $h(op) stands for one of the following operations to be applied to the base character(s) to yield the derived character(s): $l0 1 no operation 2 bold 3 slant by $h(amount) degrees 4 rotate by $h(amount) degrees $b $h(Font-name) designates the base font, which must have been defined earlier. The whole command unit is terminated by a line break. $b The font definition is terminated by a control sequence other than a character definition (control code 'I'). $a indent=0 $n2 $l1$h 7. GRAPHICAL DATA $p Pictorial information of any kind may be included in a document by including the appropriate direct specification of the data in the text, using a format which closely resembles that used for font definition. The difference is that the shape specified is drawn at the current position rather than being stored away for subsequent use. $b $l1$h (a) bitmap representation $b $l1 LEADIN $h(0); $h(height); $h(down-offset); $h(width); $h(left-offset) G $a indent=1 $b The control sequence is followed by hexadecimal values in the same form as for bitmap character specification. The pattern of dots is drawn immediately at the current position. $b $l1$h (b) line vector representation $b $l1 LEADIN $h(1); $h(height); $h(down-offset); $h(width); $h(left-offset); $h(scale) G $b The control sequence is followed by co-ordinate pairs in the same form as for line vector character specification. The shape described, scaled as indicated, is drawn immediately at the current position, on the same basis of alignment as for line vector characters. $a indent=0