Second year Advanced Project Report (2001)
by Stewart Smith
Project: User Interface Protocol
Supervisor: Linda McIver
Development Hardware/Software
The resulting code from this project can be run on either a MacOS (Version
7 through 9) or MacOS X based system. A limited amount of the code will also
run on other *nix based systems. Theoretically, parts should also work on
Windows/DOS based machines, but this has not been tested.
General Description
What is a User-Interface?
What a user interacts with - i.e. what they see (or hear, or feel).
The API problem
Traditionally, whenever a programmer wanted to create a program that interacted
with the user (being by input and/or output) they had to write their program
specifically for the system they were using. On a
Windows machine this would mean writing to the Win32 API. However, if
they then wanted to port their application over to
MacOS, MacOS X or any of
the X-Windows toolkits, you would have to completely re-write all parts of
your application concerning the UI.
Web Applications
A lot of people got sick of writing the same code 5 different ways each
doing exactly the same thing, but looking slightly different. A lot started
to create "Web Applications", a combination of client-side
HTML, Java and JavaScript and Server-side
languages such as Perl,
PHP, ASP, VBScript and Python. The
main problem with this solution is that everything is a hack.
The HTTP protocol was purely
designed for serving static documents (later extended for dynamic documents
using CGI), HTML was purely designed
for the markup of documents (Hyper Text Markup Language), JavaScript was a
hack to get some extra functionality out of the two and anyone who's had to
deal with "Session Management" knows exactly how much of a mess things can
get.
A Solution?
So what about developing a way of "Writing-once Running-many(places)"
for User Interfaces? Well, it's a good idea. It's also what some other people
have done (in one way or another).
Java and its SWING API is the most prominent
of these. SWING will allow you to code your Interface (in
Java ) once and have it displayed using the "Look-and-feel" of whatever
platform the program is run on. There are several problems with this though:
- It has to be written in Java (i.e. no
Perl)
- It's not networked (unless you code your interface and application
separately and invent your own protocol
The Qt toolkit from TrollTech is available for a number of platforms, but
it's mainly restricted to C++ and costs money on platforms other than Linux.
What needs to be displayed?
A User Interface (duh). But what does a User Interface consist of? For
this project, we're going to narrow the field down and primarily think of
Graphical User Interfaces (GUI).
When you observe current programs with a GUI. Such as an
Email program, an instant messenger and an mp3 player the interfaces are fairly
constant. That is, nothing radically changes too often while the program is
being run. In the MP3 player, you change the time, the track name, and maybe
add/subtract items from a playlist. In an Email program and instant messenger
you have message windows (which are all identical except for message contents).
In the above example, the only UI element that changes
often is the progress bar showing how far through the song we are.
What Needs to happen?
We need to be able to do several things:
- Create a GUI (add elements)
- Modify the GUI (add/modify/remove elements)
- Delete Elements
When does it need to happen?
-
Create items - on load, on user event, on program-specified
events (i.e. every second, on database update, on cd insertion)
- Modify Items:
- On user input
- On program-specified events (i.e. every second, on database update,
on cd insertion)
How can we do this?
- A protocol with 3 main functions - add, modify, delete.
- A method of accessing existing elements - some kind of object heirarchy
- Some way of adding elements of a 'type' (such as button, menu) consistently
Why a protocol?
Because of the need for program-specified events, there may be a lot of
'chatting' between the program and the UI server. Even though the up and
down streams of data are probably going to be pretty different
Aims
- To build a system that makes cross-platform User Interface development
a whole lot easier.
- To build a system that can tailor the User Interface to a specific
user’s needs without additional work by the programmer
What was Required
- Design of a "Language" to describe User Interface elements and events
(the protocol)
- A portable Object-Oriented Runtime environment
- An easy way to port the system to either OO or non-OO based host systems.
Method of Attack
The UI Language
Design something small and functional.
The Object Runtime
Instead of the traditional approach to Object Oriented
programming (creating classes and then instantiating objects from them) I
adopted another approach known as Prototype based OO. In my system, there
is no concept of a 'class'. Instead, everything is an object, and new objects
are created and based on another object. The object on which a new objects
is based is known as its prototype.
Class Based OO Class Tree
Warning and Alert are very similar.
To keep this structure, they must be implemented separately or Warning must
be implemented as a type of Alert.
|
Prototype Based OO Object Tree
but with prototypes, just say that Alert is Warning’s
prototype, and we have a relationship that keeps our tree in the logical
way we would like!
|
Part of a Typical Application's UI Object Runtime
The objects in black are the ones created by our application "MyApplication".
All the grey objects are those of the UI system.
Portability and Implementation
I chose to implement the system in C as it is one of the most portable languages
around. Although the libraries differ greatly between systems, C is compilable
on nearly every platform in existence and since this project is designed
to adapt to the local API set, the different C libraries pose no great problem.
It's often been asked "Why not in [Perl, Python, Java]?" and there is a simple
answer. If it was written in a higher level 'portable' language I am immediately
restricted to platforms that support that language. Some platforms don't
even have enough system resources to run a full implementation of [Java,
Perl, Python]!
What I hoped to complete
- A runtime environment with the capability to create objects, send
messages to objects and receive messages from objects.
- A specification and implementation of the basic 'protocol' allowing
a user (at a console) to create UI elements and receive events from them.
- An example program, running on MacOS 9 or MacOS X (preferably Both)
that would display an alert box on the screen using the UIP. I chose the
MacOS as I am familiar with it's API and it's my desktop platform of choice.
Achievements and Implementation Notes
- The Runtime Environment
- Ability to create Objects working
- Ability to add message handlers to objects
- Ability to send messages to objects
- Protocol Parser/Interpreter
- Completely hosed. Non-functional
- Example Program
- Displays an alert box under MacOS X (and under OS 9) using the UIP
functions.
- Instead of the language parser, the implementation of the test code
has been hard-wired.
Runtime Environment
All basic functionality is present and working. Although it has not been
stress tested and could fall over in a heap better than NT4 at any moment
:)
A lot of the data structures in the Runtime Environment have been implemented
using linked-lists. Although the code is small, they are not always ideal.
A future modification is to move a lot of the internals to hash tables.
Protocol Parser/UI Language
Basic rules of the language:
- Anything in square brackets references an existing object.
- a colon after the square brackets means "create a new child"
- a period after the square brackets means "send a message to"
- Curly braces mean "with contents"
- round brackets mean "with arguments"
- All arguments and contents have a name and value "name = value" and
are separated by commas or semi-colons.
- "End of Line" is a semi-colon
Unfortunately, getting flex and bison to behave on MacOS X has proved problematic.
Recently, I've decided to go and write my own language parser. The advantage
of this will be faster parsing and more portable code. Unfortunately, mine
is nowhere near complete.
Example Program
The runtime environment in the example program creates
the following object tree:
It then sends a show message to the Object:Window:Warning object. The Object:Window:Warning
object, having no handler for a 'show' message, passes control onto it's
prototype, the Object:Window:Alert object. The show message handler in the
Object:Window:Alert object then displays an alert on the screen. Notice how
the alert is exactly how a MacOS X Alert should look. When run on MacOS 9,
it will be exactly the same as a MacOS 9 alert should look! A universal Alert
function!
The following code is what is making the alert appear:
The commented greed code is what would appear in the UI language. Below it
is the C implementation of that code.
Project Documentation
Is sparse and incomplete. The code nees more documentation urgently and so
does the system itself. I attribute this lack of documentation to lack of
time (especially considering circumstances this semester). Nobody should
even consider using/modifing this project yet.
User Interface
- Run the MacOS Example Program (double click on it in the finder)
- Marvel at the alert box on the screen and the pages of debugging output
on stderr
Concluding Remarks
Not as much as been achieved as I would have liked. There is still a long
way to go and much blood, sweat and code needed before this project is complete.
However, there has been a good start made and many design problems have been
solved. With future work (which I'm intending to do) it may well become the
'next-big-thing' in UIs.
Appendix A - The Code
Here lies the source code for the MacOS Example App. As
compiled in Project Builder, on MacOS X with a Carbon Target. Even the Rez
files are included. Have fun.
list.c
#include <stdlib.h>
#include "List.h"
int list_new(List *theList)
{
theList->numItems = 0;
theList->list = NULL;
return 1;
}
void list_destroy(List *theList)
{
ListNode *current = theList->list;
while(current!=NULL)
{
theList->list = current->next;
free (current);
current = theList->list;
}
}
int list_append(List *theList,void* theItem)
{
ListNode *current = theList->list;
if(theList->list == NULL) // actually theList
{
theList->list = (ListNode*)malloc(sizeof(ListNode));
if(theList->list == NULL)
return 0;
theList->list->item = theItem;
theList->list->next = NULL;
}
else
{
while(current->next!=NULL)
current = current->next;
current->next = (ListNode*)malloc(sizeof(ListNode));
if (current->next==NULL)
return 0;
current->next->item = theItem;
current->next->next = NULL;
}
theList->numItems++;
return 1;
}
void *list_getItem(List *theList,void* item, int *(*compare)(void*,void*))
{
ListNode *current = theList->list;
if(theList->list ==NULL)
return 0;
while(current!=NULL)
{
if(compare(current->item,item))
return
current->item;
current = current->next;
}
return 0;
}
void *list_getID(List *theList,long id)
{
ListNode *current = theList->list;
long i;
if(theList->list == NULL)
return 0;
for(i=0;i<id;current=current->next,i++)
if(current->next==NULL)
return 0;
return current->item;
}
list.h
#ifndef __LIST_H__
#define __LIST_H__
typedef struct ListNodeStruc{
void *item;
struct ListNodeStruc *next;
} ListNode;
typedef struct { ListNode* list; int numItems; } List;
int list_new(List *theList);
int list_append(List *theList, void* theItem);
void list_destroy(List *theList);
void *list_getItem(List *theList,void* item, int *(*compare)(void*,void*));
void *list_getID(List *theList,long id);
#endif
MacOS.c
/*
MacOS.c
-------
MacOS System Dependent Stuff
*/
/*
#include <Types.h>
#include <Memory.h>
#include <Quickdraw.h>
#include <Fonts.h>
#include <Events.h>
#include <Menus.h>
#include <Windows.h>
#include <TextEdit.h>
#include <Dialogs.h>
#include <OSUtils.h>
#include <ToolUtils.h>
#include <SegLoad.h>
*/
#include <Carbon/Carbon.h>
#include "MacOS.h"
#include "Object.h"
/* macos_init
----------
Initialise Macintosh Managers
*/
int macos_init()
{
Object *currentObj;
MessageHandler *alert;
alert = (MessageHandler*)malloc(sizeof(MessageHandler));
// InitGraf(&qd.thePort);
// Initialize QuickDraw variables for our program.
// InitFonts();
// Initialize fonts.
// FlushEvents(everyEvent, 0); // Clear
event queue of any pending events.
// InitWindows();
// Initialize the Window Manager.
// InitMenus();
// Ditto for the Menu Manager.
// TEInit();
// blah, blah Text Edit.
// InitDialogs(0L);
// blah, blah Dialog Manager.
// InitCursor();
// Set the cursor to the arrow cursor and init.
// GetDateTime((unsigned long*) &qd.randSeed);
InitCursor();
currentObj = &rootObj;
currentObj = currentObj->new(currentObj,
currentObj,
"Window");
currentObj = currentObj->new(currentObj,
currentObj,
"Alert");
// set up alert
currentObj = object_getByName(&rootObj,"Object:Window:Alert");
fprintf(stderr,"***********ADDING A HANDLER TO %s\n",currentObj->name);
alert->handler = macos_alert;
strcpy(alert->message,"show");
object_addHandler(object_getByName(&rootObj,"Object:Window:Alert"),alert);
//Alert(kStartupAlertID,NULL);
return 0;
}
int macos_deinit()
{
return 0;
}
List macos_alert(List messages)
{
List retval;
Str255 string;
CopyCStringToPascal((char *)((Variable*)list_getID(&messages,0))->message,string);
ParamText(string,"\p","\p","\p");
Alert(129,NULL);
return retval;
}
Object.c
/*
Object.c
--------
Functions for dealing with Objects
*/
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include "Object.h"
Object rootObj;
/* object_init
-----------
Initialises everything to do with objects
*/
int object_init()
{
rootObj.parent = NULL;
rootObj.proto = NULL;
rootObj.new = root_new;
list_new(&(rootObj.messageHandlers));
list_new(&(rootObj.properties));
list_new(&(rootObj.Children));
rootObj.name = (char*)malloc(sizeof(char)*8);
strcpy(rootObj.name,"Object");
return 0; // i.e. success
}
Object *object_getByName(Object* this,char* name)
{
Object *current;
long i;
int progress = 0 ,j, done;
char *currentName = (char*)malloc(sizeof(char)*strlen(name));
if(name[0]==':')
current = this;
else
current = &rootObj;
fprintf(stderr,"Starting Traversal from %s\n",current->name);
done = 0;
do
{
// currentName = name we are currently searching
for in current
if (name[progress]==':')
progress++;
if(name[progress]=='\0')
progress++;
else
for(j=0;progress<strlen(name);progress++)
// initialisation of progress from above
{
if(name[progress]==':')
break;
currentName[j++] =
name[progress];
}
currentName[j]='\0';
// current = current object
fprintf(stderr,"current->name
= %s\t searching for currentName = %s\t progress=%d/%d\n",current->name,currentName,progress,strlen(name));
if(strcmp(current->name,currentName)!=0)
// i.e. we haven't found it.
{
fprintf(stderr,"********STARTINGG
TRAVERSING*****%d\n",current->Children.numItems);
// it's not the current object, but one of the
children could be it!
for(i=0;i<current->Children.numItems;i++)
{
/*
fprintf(stderr,"Child[%d] = %s\t currentName = %s\n"
,i
,((Object*)list_getID(&(current->Children),i))->name
,currentName);
*/
fprintf(stderr,"Traversing into child %s\n",((Object*)list_getID(&(current->Children),i))->name);
if(strcmp(
((Object*)list_getID(&(current->Children),i))->name,
currentName) ==
0)
{
// it's this child!
current = list_getID(&(current->Children),i);
break; // break out of searching
through the children
}
} // traverse children
}
// else not current
if(progress>strlen(name))
done=1;
}while(!done);
fprintf(stderr,"\n%s\t End Object: %s\n",name,current->name);
fprintf(stderr,"\tParent: %s\n",current->parent->name);
fprintf(stderr,"\tPrototype: %s\n",current->proto->name);
fprintf(stderr,"\tnumChildren = %d\n\n",current->Children.numItems);
return current;
}
/* root_new
--------
base function for creating a new object
this will become parent
proto is the prototype for the child
*/
Object* root_new(Object *this, Object *proto,char* name)
{
Object *newObject = (Object*)malloc(sizeof(Object));
newObject->parent = this;
newObject->proto = proto;
list_new(&(newObject->messageHandlers));
list_new(&(newObject->properties));
list_new(&(newObject->Children));
list_append(&(this->Children),newObject);
newObject->new = this->new;
newObject->name = name;
return newObject;
}
int object_addHandler(Object *this, MessageHandler *theHandler)
{
list_append(&(this->messageHandlers),theHandler);
return 0;
}
List object_runHandler(Object *this,Message message,List arguments)
{
long i;
int done=0;
MessageHandler *theHandler=0;
fprintf(stderr,"CALLING A HANDLER FROM %s\t",this->name);
do
{
for(i=0;i<this->messageHandlers.numItems;i++)
{
fprintf(stderr,"CALLINNG
A HANDLER %s.%s\n",this->name,((MessageHandler*)list_getID(&(this->messageHandlers),i))->message);
if(strcmp(((MessageHandler*)list_getID(&(this->messageHandlers),i))->message,message)==0)
{
theHandler = list_getID(&(this->messageHandlers),i);
done = 1;
break;
}
}
this = this->proto;
} while (!done);
if(theHandler)
return theHandler->handler(arguments);
else
fprintf(stderr,"***No Message
Handler Found***\n*** for %s from %s",message,this->name);
return;
}
void dumpObjects(Object *this,int num)
{
int i,j;
for(i=0;i<this->Children.numItems;i++)
{
for(j=0;j<num;j++)
fprintf(stderr,"
");
fprintf(stderr,"%s\n",((Object*)list_getID(&(this->Children),i))->name);
dumpObjects(list_getID(&(this->Children),i),num++);
}
}
main.c
/* main.c */
#include <Carbon/Carbon.h>
#include "main.h"
#include "Object.h"
#include "UIHost.h"
#include "MacOS.h"
void Initialize(void); /* function prototypes */
void EventLoop(void);
void MakeWindow(void);
void MakeMenu(void);
void DoEvent(EventRecord *event);
void DoMenuCommand(long menuResult);
void DoAboutBox(void);
void DrawWindow(WindowRef window);
static OSErr QuitAppleEventHandler(const AppleEvent *appleEvt, AppleEvent*
reply, UInt32 refcon);
Boolean gQuitFlag;
/* global */
int main(int argc, char *argv[])
{
List test;
Variable hello;
UIHostOS UIHost;
Object *this;
Initialize();
// MakeWindow();
// MakeMenu();
// EventLoop();
// initialise Objects :)
object_init();
// MacOS Specific stuff
UIHost.init = macos_init;
UIHost.deinit = macos_deinit;
UIHost.init();
this = &rootObj;
/*
[Object:Window]:Warning
{
proto = [Object:Window:Alert];
};
[Object:Window:Warning].show(text
= "Hello World!");
*/
// Our generic stuff
list_new(&test); // out list of arguments
hello.name="text"; // the name
is 'text'
strcpy(hello.type,"CStr"); //
the type is a C style string
hello.message="Hello World!";
// the data
list_append(&test,&hello); // it's now in our
argument list
this = object_getByName(&rootObj,"Object:Window:Alert");
// get the Window Object we're running a handler for
this = this->new(object_getByName(&rootObj,"Object:Window"),
object_getByName(&rootObj,"Object:Window:Alert"),
"Warning");
object_runHandler(this,"show",test);
// show the Window!
UIHost.deinit();
return 0;
}
void Initialize() /* Initialize some managers */
{
OSErr err;
InitCursor();
err = AEInstallEventHandler( kCoreEventClass, kAEQuitApplication,
NewAEEventHandlerUPP((AEEventHandlerProcPtr)QuitAppleEventHandler), 0, false
);
if (err != noErr)
ExitToShell();
}
static OSErr QuitAppleEventHandler( const AppleEvent *appleEvt, AppleEvent*
reply, UInt32 refcon )
{
gQuitFlag = true;
return noErr;
}
void EventLoop()
{
Boolean gotEvent;
EventRecord event;
gQuitFlag = false;
do
{
gotEvent = WaitNextEvent(everyEvent,&event,32767,nil);
if (gotEvent)
DoEvent(&event);
} while (!gQuitFlag);
ExitToShell();
}
void MakeWindow() /* Put up a window */
{
Rect wRect;
WindowRef myWindow;
SetRect(&wRect,50,50,600,200); /* left, top, right,
bottom */
myWindow = NewCWindow(nil, &wRect, "\pHello", true,
zoomNoGrow, (WindowRef) -1, true, 0);
if (myWindow != nil)
SetPort(GetWindowPort(myWindow));
/* set port to new window */
else
ExitToShell();
}
void MakeMenu() /* Put up a menu */
{
Handle menuBar;
MenuRef menu;
long response;
OSErr err;
menuBar = GetNewMBar(rMenuBar); /* read
menus into menu bar */
if ( menuBar != nil )
{
SetMenuBar(menuBar);
/* install menus */
// AppendResMenu(GetMenuHandle(mApple),
'DRVR');
err = Gestalt(gestaltMenuMgrAttr,
&response);
if ((err == noErr) && (response & gestaltMenuMgrAquaLayoutMask))
{
menu =
GetMenuHandle( mFile );
DeleteMenuItem(
menu, iQuit );
DeleteMenuItem(
menu, iQuitSeparator );
}
DrawMenuBar();
}
else
ExitToShell();
}
void DoEvent(EventRecord *event)
{
short part;
Boolean hit;
char key;
Rect tempRect;
WindowRef whichWindow;
switch (event->what)
{
case mouseDown:
part =
FindWindow(event->where, &whichWindow);
switch
(part)
{
case inMenuBar: /* process a moused menu command */
DoMenuCommand(MenuSelect(event->where));
break;
case inSysWindow:
break;
case inContent:
if (whichWindow != FrontWindow())
SelectWindow(whichWindow);
break;
case inDrag: /* pass screenBits.bounds */
GetRegionBounds(GetGrayRgn(), &tempRect);
DragWindow(whichWindow, event->where, &tempRect);
break;
case inGrow:
break;
case inGoAway:
DisposeWindow(whichWindow);
ExitToShell();
break;
case inZoomIn:
case inZoomOut:
hit = TrackBox(whichWindow, event->where, part);
if (hit)
{
SetPort(GetWindowPort(whichWindow)); // window must be current
port
EraseRect(GetWindowPortBounds(whichWindow, &tempRect)); //
inval/erase because of ZoomWindow bug
ZoomWindow(whichWindow, part, true);
InvalWindowRect(whichWindow, GetWindowPortBounds(whichWindow, &tempRect));
}
break;
}
break;
case keyDown:
case autoKey:
key = event->message & charCodeMask;
if (event->modifiers & cmdKey)
if (event->what == keyDown)
DoMenuCommand(MenuKey(key));
case activateEvt:
/* if you needed to do something special
*/
break;
case updateEvt:
DrawWindow((WindowRef)
event->message);
break;
case kHighLevelEvent:
AEProcessAppleEvent(
event );
break;
case diskEvt:
break;
}
}
void DoMenuCommand(long menuResult)
{
short menuID;
/* the resource ID of the selected menu */
short menuItem; /*
the item number of the selected menu */
menuID = HiWord(menuResult); /* use
macros to get item & menu number */
menuItem = LoWord(menuResult);
switch (menuID)
{
case mApple:
switch
(menuItem)
{
case iAbout:
DoAboutBox();
break;
case iQuit:
ExitToShell();
break;
default:
break;
}
break;
case mFile:
break;
case mEdit:
break;
}
HiliteMenu(0); /* unhighlight what MenuSelect
(or MenuKey) hilited */
}
void DrawWindow(WindowRef window)
{
Rect tempRect;
GrafPtr curPort;
GetPort(&curPort);
SetPort(GetWindowPort(window));
BeginUpdate(window);
EraseRect(GetWindowPortBounds(window, &tempRect));
DrawControls(window);
DrawGrowIcon(window);
EndUpdate(window);
SetPort(curPort);
}
void DoAboutBox(void)
{
(void) Alert(kAboutBox, nil); // simple alert dialog box
}
main.h
/* main.h */
#define rMenuBar 128
/* menu bar */
#define mApple 128
/* Apple menu */
#define iAbout 1
#define mFile 129
/* File menu */
#define iNew 1
#define iClose 4
#define iQuitSeparator 10
#define iQuit 11
#define mEdit 130
/* Edit menu */
#define kAboutBox 200 /* Dialog resource
for About box */
Object.h
/*
Object.h
--------
Definition for an Object
*/
#ifndef __OBJECT_H__
#define __OBJECT_H__
#include "List.h"
typedef struct VariableStruc {
char *name;
char type[11];
void* message;
} Variable;
typedef char Message[51];
typedef struct MessageHandlerStruc {
Message message;
List (*handler)(List); // List<Message>
} MessageHandler;
typedef struct ObjectStruc {
char *name;
struct ObjectStruc *parent;
struct ObjectStruc *proto;
List Children;
struct ObjectStruc *(*new)(struct ObjectStruc *this, struct
ObjectStruc *proto,char* name);
List messageHandlers;
List properties;
} Object;
extern Object rootObj;
int object_init();
Object* root_new(Object *this,Object *proto,char* name);
Object* object_getByName(Object *this, char* name);
int object_addHandler(Object *this, MessageHandler *theHandler);
List object_runHandler(Object *this,Message message,List arguments);
void dumpObjects(Object *this,int num);
#endif
UIHost.h
/*
UIHost.h
--------
Header file for UIHost - i.e. the system that hosts the
user interface
*/
/* UIHostOS
--------
Data structure keeps track of all functions and data for
each host OS of a UI
*/
typedef struct {
int (*init)(); //
function to initialise OS Specific things
int (*deinit)(); // function to de-initialise
any OS Specific things
} UIHostOS;
MacOS.h
/*
MacOS.h
-------
MacOS header file
*/
#ifndef __MACOS_H__
#define __MACOS_H__
#include "Object.h"
#define kStartupAlertID 128
int macos_init();
int macos_deinit();
List macos_alert(List messages);
#endif
main.r
/* main.r */
#include <Carbon/Carbon.r>
#include "main.h"
/* Unfortunately, we cannot yet process symbolic resource descriptions...*/
#define RAW 1
#if RAW
data 'MBAR' (rMenuBar, preload) {
$"0003 0080 0081 0082"
/* ...Ä.Å.Ç.É */
};
#else
resource 'MBAR' (rMenuBar, preload) {
{mApple, mFile, mEdit};
};
#endif
#if RAW
data 'MENU' (mApple, preload) {
$"0080 0000 0000 0000 0000 FFFF FFFB 0114"
/* .Ä........ˇˇˇ˚.. */
$"0C41 626F 7574 2048 656C 6C6F C900 0000"
/* .About Hello…... */
$"0001 2D00 0000 0000"
/* ..-..... */
};
#else
resource 'MENU' (mApple, "Apple", preload) {
mApple, textMenuProc,
AllItems & ~MenuItem2,
enabled, apple,
{
"About Hello…",
noicon, nokey, nomark, plain;
"-",
noicon, nokey, nomark, plain;
}
};
#endif
#if RAW
data 'MENU' (mFile, preload) {
$"0081 0000 0000 0000 0000 0000 2801 0446"
/* .Å..........(..F */
$"696C 6503 4E65 7700 4E00 0004 4F70 656E"
/* ile.New.N...Open */
$"004F 0000 012D 0000 0000 0543 6C6F 7365"
/* .O...-.....Close */
$"0057 0000 0453 6176 6500 5300 0008 5361"
/* .W...Save.S...Sa */
$"7665 2041 73C9 0000 0000 012D 0000 0000"
/* ve As….....-.... */
$"0B50 6167 6520 5365 7475 70C9 0000 0000"
/* .Page Setup….... */
$"0650 7269 6E74 C900 0000 0001 2D00 0000"
/* .Print….....-... */
$"0004 5175 6974 0051 0000 00"
/* ..Quit.Q... */
};
#else
resource 'MENU' (mFile, "File", preload) {
mFile, textMenuProc,
AllItems & ~MenuItem3 & ~MenuItem7 & ~MenuItem10,
enabled, "File",
{
"New",
noicon, "N", nomark,
plain;
"Open",
noicon, "O", nomark,
plain;
"-",
noicon, nokey, nomark,
plain;
"Close", noicon,
"W", nomark, plain;
"Save",
noicon, "S", nomark,
plain;
"Save As…", noicon,
nokey, nomark, plain;
"-",
noicon, nokey, nomark,
plain;
"Page Setup…", noicon,
nokey, nomark, plain;
"Print…", noicon,
"P", nomark, plain;
"-",
noicon, nokey, nomark,
plain;
"Quit",
noicon, "Q", nomark,
plain;
}
};
#endif
#if RAW
data 'MENU' (mEdit, preload) {
$"0082 0000 0000 0000 0000 0000 0001 0445"
/* .Ç.............E */
$"6469 7404 556E 646F 005A 0000 012D 0000"
/* dit.Undo.Z...-.. */
$"0000 0343 7574 0058 0000 0443 6F70 7900"
/* ...Cut.X...Copy. */
$"4300 0005 5061 7374 6500 5600 0005 436C"
/* C...Paste.V...Cl */
$"6561 7200 0000 0000"
/* ear..... */
};
#else
resource 'MENU' (mEdit, "Edit", preload) {
mEdit, textMenuProc,
AllItems & ~MenuItem2 & ~MenuItem7 & ~MenuItem9
& ~MenuItem14 & ~MenuItem18,
enabled, "Edit",
{
"Undo",
noicon, "Z", nomark,
plain;
"-",
noicon, nokey, nomark,
plain;
"Cut",
noicon, "X", nomark,
plain;
"Copy",
noicon, "C", nomark,
plain;
"Paste", noicon,
"P", nomark, plain;
"Clear", noicon,
nokey, nomark, plain;
}
};
#endif
#if RAW
data 'DITL' (kAboutBox) {
$"0002 0000 0000 0010 0015 0026 00D0 8814"
/* ...........&.–à. */
$"4865 6C6C 6F20 6865 6C6C 6F20 6865 6C6C"
/* Hello hello hell */
$"6F2E 2E2E 0000 0000 0074 011F 0088 0159"
/* o........t...à.Y */
$"0402 4F4B 0000 0000 0036 008B 004A 00C5"
/* ..OK.....6.ã.J.≈ */
$"0402 4F4B"
/* ..OK */
};
#else
resource 'DITL' (kAboutBox) {
{
{16, 21, 38, 208}, StaticText {disabled,
"Hello hello hello"},
{116, 287, 136, 345}, Button {enabled,
"OK"},
}
};
#endif
data 'ALRT' (kAboutBox) {
$"0028 0028 008B 0118 00C8 5555"
/* .(.(.ã...»UU */
};
MacOs support.r
data 'WIND' (128, "Console Window") {
$"0053 0027 017F 01D5 0000 0100 0000 0000"
/* .S.'...’........ */
$"0000 0F55 4920 5465 7374 2043 6F6E 736F"
/* ...UI Test Conso */
$"6C65 380A"
/* le8¬ */
};
data 'MBAR' (128) {
$"0003 0080 0081 0082"
/* ...Ä.Å.Ç */
};
data 'MENU' (128) {
$"0080 0000 0000 0000 0000 FFFF FFFB 0114"
/* .Ä........ˇˇˇ˚.. */
$"1041 626F 7574 2055 4920 5465 7374 2E2E"
/* .About UI Test.. */
$"2E00 0000 0001 2D00 0000 0000"
/* ......-..... */
};
data 'MENU' (129) {
$"0081 0000 0000 0000 0000 FFFF FB77 0446"
/* .Å........ˇˇ˚w.F */
$"696C 6503 4E65 7700 4E00 0004 4F70 656E"
/* ile.New.N...Open */
$"004F 0000 012D 0000 0000 0543 6C6F 7365"
/* .O...-.....Close */
$"0057 0000 0453 6176 6500 5300 000A 5361"
/* .W...Save.S..¬Sa */
$"7665 2041 732E 2E2E 0000 0000 012D 0000"
/* ve As........-.. */
$"0000 0D50 6167 6520 5365 7475 702E 2E2E"
/* ...Page Setup... */
$"0000 0000 0850 7269 6E74 2E2E 2E00 5000"
/* .....Print....P. */
$"0001 2D00 0000 0004 5175 6974 0051 0000"
/* ..-.....Quit.Q.. */
$"00"
/* . */
};
data 'MENU' (130) {
$"0082 0000 0000 0000 0000 FFFF FD7B 0445"
/* .Ç........ˇˇ˝{.E */
$"6469 7404 556E 646F 005A 0000 012D 0000"
/* dit.Undo.Z...-.. */
$"0000 0343 7574 0058 0000 0443 6F70 7900"
/* ...Cut.X...Copy. */
$"4300 0005 5061 7374 6500 5600 0005 436C"
/* C...Paste.V...Cl */
$"6561 7200 0000 0001 2D00 0000 000A 5365"
/* ear.....-....¬Se */
$"6C65 6374 2041 6C6C 0041 0000 012D 0000"
/* lect All.A...-.. */
$"0000 0E50 7265 6665 7265 6E63 6573 2E2E"
/* ...Preferences.. */
$"2E00 0000 0000"
/* ...... */
};
data 'ALRT' (128) {
$"0028 0028 00AD 01D0 0080 5555 280A"
/* .(.(.≠.–.ÄUU(¬ */
};
data 'ALRT' (129) {
$"0028 0028 00AD 01D0 0081 5555 280A"
/* .(.(.≠.–.ÅUU(¬ */
};
data 'DITL' (128) {
$"0003 0000 0000 005C 0157 0070 0191 0402"
/* .......\.W.p.ë.. */
$"4F6B 0000 0000 0055 014F 0077 0197 8000"
/* Ok.....U.O.w.óÄ. */
$"0000 0000 0014 0047 004E 0186 888B 5468"
/* .......G.N.ÜàãTh */
$"6973 2070 726F 6772 616D 2069 7320 6120"
/* is program is a */
$"7465 7374 206F 6620 736F 6D65 2066 756E"
/* test of some fun */
$"6374 696F 6E61 6C69 7479 206F 6620 6120"
/* ctionality of a */
$"4765 6E65 7269 6320 5573 6572 2049 6E74"
/* Generic User Int */
$"6572 6661 6365 2050 726F 746F 636F 6C2E"
/* erface Protocol. */
$"2049 7420 6973 2069 6E63 6F6D 706C 6574"
/* It is incomplet */
$"652C 2075 6E73 7570 706F 7274 6564 2061"
/* e, unsupported a */
$"6E64 2063 6F75 6C64 2064 6F20 6E61 7374"
/* nd could do nast */
$"7920 7468 696E 6773 2E64 0000 0000 0013"
/* y things.d...... */
$"0012 0033 0032 A002 0002"
/* ...3.2†... */
};
data 'DITL' (129) {
$"0003 0000 0000 005C 0157 0070 0191 0402"
/* .......\.W.p.ë.. */
$"4F6B 0000 0000 0055 014F 0077 0197 8000"
/* Ok.....U.O.w.óÄ. */
$"0000 0000 0014 0047 004E 0186 8802 5E30"
/* .......G.N.Üà.^0 */
$"0000 0000 0013 0012 0033 0032 A002 0002"
/* .........3.2†... */
};
UItest.r
data 'vers' (1) {
$"0001 2000 0000 0676 302E 302E 311B 496E"
/* .. ....v0.0.1.In */
$"6974 6961 6C20 4465 7665 6C6F 706D 656E"
/* itial Developmen */
$"7420 5665 7273 696F 6E"
/* t Version */
};
data 'vers' (2) {
$"0001 2000 0000 0676 302E 302E 311B 496E"
/* .. ....v0.0.1.In */
$"6974 6961 6C20 4465 7665 6C6F 706D 656E"
/* itial Developmen */
$"7420 5665 7273 696F 6E"
/* t Version */
};
data 'BNDL' (128) {
$"5549 5031 0000 0001 4652 4546 0000 0000"
/* UIP1....FREF.... */
$"0080 4943 4E23 0000 0000 0080"
/* .ÄICN#.....Ä */
};
data 'UIP1' (0, "Owner resource") {
$"00"
/* . */
};
data 'FREF' (128) {
$"4150 504C 0000 00"
/* APPL... */
};
data 'ICN#' (128) {
$"0000 0000 0000 0000 0FFF FFE0 3000 0018"
/* .........ˇˇ‡0... */
$"23FF FF88 4C00 0064 4800 0024 5071 0014"
/* #ˇˇàL..dH..$Pq.. */
$"50D9 4014 5089 8014 5089 8014 5089 4014"
/* PŸ@.PâÄ.PâÄ.Pâ@. */
$"50D9 4014 4870 0024 4C00 0064 23FF FF88"
/* PŸ@.Hp.$L..d#ˇˇà */
$"3000 0018 0FFF FFE0 0000 0000 0007 FFF0"
/* 0....ˇˇ‡......ˇ */
$"0005 0010 0007 FFF0 0004 0010 0004 0010"
/* ......ˇ........ */
$"0004 0010 0004 0010 0004 0010 0004 0010"
/* ................ */
$"0004 0010 0004 0010 0004 0010 0007 FFF0"
/* ..............ˇ */
$"0000 0000 0000 0000 0FFF FFE0 3FFF FFF8"
/* .........ˇˇ‡?ˇˇ¯ */
$"3FFF FFF8 7FFF FFFC 7FFF FFFC 7FFF FFFC"
/* ?ˇˇ¯.ˇˇ¸.ˇˇ¸.ˇˇ¸ */
$"7FFF FFFC 7FFF FFFC 7FFF FFFC 7FFF FFFC"
/* .ˇˇ¸.ˇˇ¸.ˇˇ¸.ˇˇ¸ */
$"7FFF FFFC 7FFF FFFC 7FFF FFFC 3FFF FFF8"
/* .ˇˇ¸.ˇˇ¸.ˇˇ¸?ˇˇ¯ */
$"3FFF FFF8 0FFF FFE0 0000 0000 0007 FFF0"
/* ?ˇˇ¯.ˇˇ‡......ˇ */
$"0007 FFF0 0007 FFF0 0007 FFF0 0007 FFF0"
/* ..ˇ..ˇ..ˇ..ˇ */
$"0007 FFF0 0007 FFF0 0007 FFF0 0007 FFF0"
/* ..ˇ..ˇ..ˇ..ˇ */
$"0007 FFF0 0007 FFF0 0007 FFF0 0007 FFF0"
/* ..ˇ..ˇ..ˇ..ˇ */
};
data 'icl8' (128) {
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 FFFF FFFF FFFF FFFF FFFF FFFF"
/* ....ˇˇˇˇˇˇˇˇˇˇˇˇ */
$"FFFF FFFF FFFF FFFF FFFF FF00 0000 0000"
/* ˇˇˇˇˇˇˇˇˇˇˇ..... */
$"0000 FFFF 0000 0000 0000 0000 0000 0000"
/* ..ˇˇ............ */
$"0000 0000 0000 0000 0000 00FF FF00 0000"
/* ...........ˇˇ... */
$"0000 FF00 0000 FFFF FFFF FFFF FFFF FFFF"
/* ..ˇ...ˇˇˇˇˇˇˇˇˇˇ */
$"FFFF FFFF FFFF FFFF FF00 0000 FF00 0000"
/* ˇˇˇˇˇˇˇˇˇ...ˇ... */
$"00FF 0000 FFFF F6F6 F6F6 F6F6 F6F6 F6F6"
/* .ˇ..ˇˇˆˆˆˆˆˆˆˆˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6FF FF00 00FF 0000"
/* ˆˆˆˆˆˆˆˆˆˇˇ..ˇ.. */
$"00FF 0000 FFF6 F6F6 F6F6 F6F6 F6F6 F6F6"
/* .ˇ..ˇˆˆˆˆˆˆˆˆˆˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 FF00 00FF 0000"
/* ˆˆˆˆˆˆˆˆˆˆˇ..ˇ.. */
$"00FF 00FF F6F6 F6F6 F6FF FFFF F6F6 F6FF"
/* .ˇ.ˇˆˆˆˆˆˇˇˇˆˆˆˇ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 00FF F6F6 F6F6 FFFF F6FF FFF6 F6FF"
/* .ˇ.ˇˆˆˆˆˇˇˆˇˇˆˆˇ */
$"F6FF F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˆˇˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 00FF F6F6 F6F6 FFF6 F6F6 FFF6 F6FF"
/* .ˇ.ˇˆˆˆˆˇˆˆˆˇˆˆˇ */
$"FFF6 F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˇˆˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 00FF F6F6 F6F6 FFF6 F6F6 FFF6 F6FF"
/* .ˇ.ˇˆˆˆˆˇˆˆˆˇˆˆˇ */
$"FFF6 F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˇˆˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 00FF F6F6 F6F6 FFF6 F6F6 FFF6 F6FF"
/* .ˇ.ˇˆˆˆˆˇˆˆˆˇˆˆˇ */
$"F6FF F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˆˇˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 00FF F6F6 F6F6 FFFF F6FF FFF6 F6FF"
/* .ˇ.ˇˆˆˆˆˇˇˆˇˇˆˆˇ */
$"F6FF F6F6 F6F6 F6F6 F6F6 F6FF 00FF 0000"
/* ˆˇˆˆˆˆˆˆˆˆˆˇ.ˇ.. */
$"00FF 0000 FFF6 F6F6 F6FF FFFF F6F6 F6F6"
/* .ˇ..ˇˆˆˆˆˇˇˇˆˆˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 FF00 00FF 0000"
/* ˆˆˆˆˆˆˆˆˆˆˇ..ˇ.. */
$"00FF 0000 FFFF F6F6 F6F6 F6F6 F6F6 F6F6"
/* .ˇ..ˇˇˆˆˆˆˆˆˆˆˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6FF FF00 00FF 0000"
/* ˆˆˆˆˆˆˆˆˆˇˇ..ˇ.. */
$"0000 FF00 0000 FFFF FFFF FFFF FFFF FFFF"
/* ..ˇ...ˇˇˇˇˇˇˇˇˇˇ */
$"FFFF FFFF FFFF FFFF FF00 0000 FF00 0000"
/* ˇˇˇˇˇˇˇˇˇ...ˇ... */
$"0000 FFFF 0000 0000 0000 0000 0000 0000"
/* ..ˇˇ............ */
$"0000 0000 0000 0000 0000 00FF FF00 0000"
/* ...........ˇˇ... */
$"0000 0000 FFFF FFFF FFFF FFFF FFFF FFFF"
/* ....ˇˇˇˇˇˇˇˇˇˇˇˇ */
$"FFFF FFFF FFFF FFFF FFFF FF00 0000 0000"
/* ˇˇˇˇˇˇˇˇˇˇˇ..... */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 00FF FFFF"
/* .............ˇˇˇ */
$"FFFF FFFF FFFF FFFF FFFF FFFF 0000 0000"
/* ˇˇˇˇˇˇˇˇˇˇˇˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF 00ED"
/* .............ˇ.Ì */
$"0000 0000 0000 0000 0000 00FF 0000 0000"
/* ...........ˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF FFFF"
/* .............ˇˇˇ */
$"FFFF FFFF FFFF FFFF FFFF FFFF 0000 0000"
/* ˇˇˇˇˇˇˇˇˇˇˇˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF F6F6"
/* .............ˇˆˆ */
$"F6F6 F6F6 F6F6 F6F6 F6F6 F6FF 0000 0000"
/* ˆˆˆˆˆˆˆˆˆˆˆˇ.... */
$"0000 0000 0000 0000 0000 0000 00FF FFFF"
/* .............ˇˇˇ */
$"FFFF FFFF FFFF FFFF FFFF FFFF 0000 0000"
/* ˇˇˇˇˇˇˇˇˇˇˇˇ.... */
};
data 'icl4' (128) {
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 FFFF FFFF FFFF FFFF FFFF FFF0 0000"
/* ..ˇˇˇˇˇˇˇˇˇˇˇ.. */
$"00FF 0000 0000 0000 0000 0000 000F F000"
/* .ˇ............. */
$"00F0 00FF FFFF FFFF FFFF FFFF F000 F000"
/* ..ˇˇˇˇˇˇˇˇˇ.. */
$"0F00 FFCC CCCC CCCC CCCC CCCC CFF0 0F00"
/* ..ˇÃÃÃÃÃÃÃÃÜ..
*/
$"0F00 FCCC CCCC CCCC CCCC CCCC CCF0 0F00"
/* ..¸ÃÃÃÃÃÃÃÃÃÃ..
*/
$"0F0F CCCC CFFF CCCF CCCC CCCC CCCF 0F00"
/* ..ÃÜˇÃœÃÃÃÃÜ..
*/
$"0F0F CCCC FFCF FCCF CFCC CCCC CCCF 0F00"
/* ..ÃÃˇœ¸œœÃÃÃÜ.. */
$"0F0F CCCC FCCC FCCF FCCC CCCC CCCF 0F00"
/* ..Ãøøœ¸ÃÃÃÜ..
*/
$"0F0F CCCC FCCC FCCF FCCC CCCC CCCF 0F00"
/* ..Ãøøœ¸ÃÃÃÜ..
*/
$"0F0F CCCC FCCC FCCF CFCC CCCC CCCF 0F00"
/* ..ÃøøœœÃÃÃÜ..
*/
$"0F0F CCCC FFCF FCCF CFCC CCCC CCCF 0F00"
/* ..ÃÃˇœ¸œœÃÃÃÜ.. */
$"0F00 FCCC CFFF CCCC CCCC CCCC CCF0 0F00"
/* ..¸ÃœˇÃÃÃÃÃÃÃ..
*/
$"0F00 FFCC CCCC CCCC CCCC CCCC CFF0 0F00"
/* ..ˇÃÃÃÃÃÃÃÃÜ..
*/
$"00F0 00FF FFFF FFFF FFFF FFFF F000 F000"
/* ..ˇˇˇˇˇˇˇˇˇ.. */
$"00FF 0000 0000 0000 0000 0000 000F F000"
/* .ˇ............. */
$"0000 FFFF FFFF FFFF FFFF FFFF FFF0 0000"
/* ..ˇˇˇˇˇˇˇˇˇˇˇ.. */
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"0000 0000 0000 0FFF FFFF FFFF FFFF 0000"
/* .......ˇˇˇˇˇˇˇ.. */
$"0000 0000 0000 0F06 0000 0000 000F 0000"
/* ................ */
$"0000 0000 0000 0FFF FFFF FFFF FFFF 0000"
/* .......ˇˇˇˇˇˇˇ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FCC CCCC CCCC CCCF 0000"
/* .......ÃÃÃÃÃÜ.. */
$"0000 0000 0000 0FFF FFFF FFFF FFFF 0000"
/* .......ˇˇˇˇˇˇˇ.. */
};
data 'ics#' (128) {
$"0000 7FFE FFFE ED06 CF86 CB86 EF86 FFFE"
/* ...˛ˇ˛Ì.œÜÀÜÔܡ˛ */
$"7FFE 03FC 03FC 0204 0204 0204 0204 03FC"
/* .˛.¸.¸.........¸ */
$"0000 7FFE FFFE FFFE FFFE FFFE FFFE FFFE"
/* ...˛ˇ˛ˇ˛ˇ˛ˇ˛ˇ˛ˇ˛ */
$"7FFE 03FC 03FC 03FC 03FC 03FC 03FC 03FC"
/* .˛.¸.¸.¸.¸.¸.¸.¸ */
};
data 'ics8' (128) {
$"0000 0000 0000 0000 0000 0000 0000 0000"
/* ................ */
$"00FF FFFF FFFF FFFF FFFF FFFF FFFF FF00"
/* .ˇˇˇˇˇˇˇˇˇˇˇˇˇˇ. */
$"FFFF FFFF FFFF FFFF FFFF FFFF FFFF FF00"
/* ˇˇˇˇˇˇˇˇˇˇˇˇˇˇˇ. */
$"FFFF FFF6 FFFF F6FF F6F6 F6F6 F6FF FF00"
/* ˇˇˇˆˇˇˆˇˆˆˆˆˆˇˇ. */
$"FFFF F6F6 FFFF FFFF FFF6 F6F6 F6FF FF00"
/* ˇˇˆˆˇˇˇˇˇˆˆˆˆˇˇ. */
$"FFFF F6F6 FFF6 FFFF FFF6 F6F6 F6FF FF00"
/* ˇˇˆˆˇˆˇˇˇˆˆˆˆˇˇ. */
$"FFFF FFF6 FFFF FFFF FFF6 F6F6 F6FF FF00"
/* ˇˇˇˆˇˇˇˇˇˆˆˆˆˇˇ. */
$"FFFF FFFF FFFF FFFF FFFF FFFF FFFF FF00"
/* ˇˇˇˇˇˇˇˇˇˇˇˇˇˇˇ. */
$"00FF FFFF FFFF FFFF FFFF FFFF FFFF FF00"
/* .ˇˇˇˇˇˇˇˇˇˇˇˇˇˇ. */
$"0000 0000 0000 FFFF FFFF FFFF FFFF 0000"
/* ......ˇˇˇˇˇˇˇˇ.. */
$"0000 0000 0000 FFFF FFFF FFFF FFFF 0000"
/* ......ˇˇˇˇˇˇˇˇ.. */
$"0000 0000 0000 FFF6 F6F6 F6F6 F6FF 0000"
/* ......ˇˆˆˆˆˆˆˇ.. */
$"0000 0000 0000 FFF6 F6F6 F6F6 F6FF 0000"
/* ......ˇˆˆˆˆˆˆˇ.. */
$"0000 0000 0000 FFF6 F6F6 F6F6 F6FF 0000"
/* ......ˇˆˆˆˆˆˆˇ.. */
$"0000 0000 0000 FFF6 F6F6 F6F6 F6FF 0000"
/* ......ˇˆˆˆˆˆˆˇ.. */
$"0000 0000 0000 FFFF FFFF FFFF FFFF 0000"
/* ......ˇˇˇˇˇˇˇˇ.. */
};
data 'ics4' (128) {
$"0000 0000 0000 0000 0FFF FFFF FFFF FFF0"
/* .........ˇˇˇˇˇˇ */
$"FFFF FFFF FFFF FFF0 FFFC FFCF CCCC CFF0"
/* ˇˇˇˇˇˇˇˇ¸ˇœÃÜ */
$"FFCC FFFF FCCC CFF0 FFCC FCFF FCCC CFF0"
/* ˇÃˇˇ¸ÃœˇÃ¸ˇ¸Ãœ */
$"FFFC FFFF FCCC CFF0 FFFF FFFF FFFF FFF0"
/* ˇ¸ˇˇ¸Ãœˇˇˇˇˇˇˇ */
$"0FFF FFFF FFFF FFF0 0000 00FF FFFF FF00"
/* .ˇˇˇˇˇˇ...ˇˇˇˇ. */
$"0000 00FF FFFF FF00 0000 00FC CCCC CF00"
/* ...ˇˇˇˇ....¸ÃÜ. */
$"0000 00FC CCCC CF00 0000 00FC CCCC CF00"
/* ...¸ÃÜ....¸ÃÜ. */
$"0000 00FC CCCC CF00 0000 00FF FFFF FF00"
/* ...¸ÃÜ....ˇˇˇˇ. */
};
data 'SIZE' (-1) {
$"58A0 0020 0000 0020 0000"
/* X†. ... .. */
};