home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Club Amiga de Montreal - CAM
/
CAM_CD_1.iso
/
files
/
266.lha
/
SetKey_v2.0
/
src
/
showsubs.c
< prev
next >
Wrap
C/C++ Source or Header
|
1989-07-10
|
10KB
|
462 lines
#include <stdio.h>
#include <exec/types.h>
#include <exec/io.h>
#include <exec/memory.h>
#include <graphics/gfxbase.h>
#include <graphics/text.h>
#include <graphics/gfxmacros.h>
#include <devices/console.h>
#include <devices/keymap.h>
#include <libraries/dos.h>
#include <libraries/dosextens.h>
#include <intuition/intuition.h>
#include <functions.h>
extern UBYTE filestring[];
UBYTE *LoTypes;
ULONG *LoMap;
UBYTE *LoCap;
UBYTE *LoRep;
UBYTE *HiTypes;
ULONG *HiMap;
UBYTE *HiCap;
UBYTE *HiRep;
int abort=0;
extern void FillKeyMap();
extern long DLength();
extern void NewStr();
long tlen;
UBYTE *told,*tnew;
struct {
UBYTE length;
UBYTE string[127];
} DStr[8]; /* one per each qualifier */
struct IOStdReq *WriteMsg; /* I/O request block pointer */
struct MsgPort *WritePort; /* a port at which to receive replies*/
int DescLen[8]={2,4,4,8,4,8,8,16};
struct KeyMap MyKeyMap;
/* For writing to the console: */
void MakeConWP()
{
WritePort = CreatePort("mycon.write",0L);
if(WritePort == 0L) exit(100); /* error in createport */
WriteMsg = CreateStdIO(WritePort);
if(WriteMsg == 0L) exit(200); /* error in createstdio */
}
/* output a NULL-terminated string of characters to a console */
void
TurnCursorOff()
{
WriteMsg->io_Command = CMD_WRITE;
WriteMsg->io_Data = (APTR)" p";
WriteMsg->io_Length = -1;
DoIO(WriteMsg);
return;
}
/* this function returns a value of 0 if the console
* device opened correctly and a nonzero value (the error
* returned from OpenDevice) if there was an error.
*/
long OpenConsole(window)
struct Window *window;
{
/* Open a console device */
long error;
MakeConWP(); /* make a write console port */
WriteMsg->io_Data = (APTR) window;
WriteMsg->io_Length = (long)sizeof(*window);
error=OpenDevice("console.device", 0L, WriteMsg, 0L);
TurnCursorOff();
return(error);
}
/* Set the current KeyMap with pointers in given keymap. */
void SetKeyMap(KeyMap)
struct KeyMap *KeyMap;
{
WriteMsg->io_Command = CD_SETKEYMAP;
WriteMsg->io_Length = 32L;
WriteMsg->io_Data = (APTR)KeyMap;
DoIO(WriteMsg);
}
/* Make a new string so the FreeMem does not crash */
void FixDeadKey(key)
int key;
{
int i;
char *temp;
told=(UBYTE *)LoMap[key];
tnew=(UBYTE *)&LoMap[key];
LoMap[key]=0;
if(told[0]==0) tnew[3]=told[1];
else tnew[3]=*(told+told[1]);
if(told[2]==0) tnew[2]=told[3];
else tnew[2]=*(told+told[3]);
LoTypes[key]&=0x0F;
}
/* Fill Default keymap and copy to MyKeyMap */
void DefaultKeyMap()
{
int i;
FillKeyMap(&MyKeyMap);
for(i=0;i<64;i++)
{
LoTypes[i]=MyKeyMap.km_LoKeyMapTypes[i];
LoMap[i]=MyKeyMap.km_LoKeyMap[i];
if(LoTypes[i]&0x40) NewStr(i);
if(abort) return;
if(LoTypes[i]&0x20) FixDeadKey(i);
}
for(i=0;i<8;i++)
{
LoCap[i]=MyKeyMap.km_LoCapsable[i];
LoRep[i]=MyKeyMap.km_LoRepeatable[i];
}
for(i=0;i<56;i++)
{
HiTypes[i]=MyKeyMap.km_HiKeyMapTypes[i];
HiMap[i]=MyKeyMap.km_HiKeyMap[i];
if(HiTypes[i]&0x40) NewStr(i+0x40);
if(abort) return;
if(HiTypes[i]&0x20) FixDeadKey(i+0x40);
}
for(i=0;i<7;i++)
{
HiCap[i]=MyKeyMap.km_HiCapsable[i];
HiRep[i]=MyKeyMap.km_HiRepeatable[i];
}
}
/* DeAlloc string mem before exit and before LoadKeyMap() */
void ClearStr(key)
int key;
{
int i;
for(i=0;i<key;i++) /* deallocate strings both lo and hi*/
{
if(LoTypes[i]&0x40)
{
told=(UBYTE *)LoMap[i];
FreeMem(told,DLength(told));
}
}
}
ULONG LoadKeyMap(string)
char *string;
{
int i;
ULONG segment;
UWORD *Ptr,*km;
ULONG *temp,*nptr,length;
char *name;
segment=(ULONG)LoadSeg(string);
if(segment==0) return(0L);
Ptr=(UWORD *)BADDR(segment);
temp=(ULONG *)Ptr;
length=*(temp-1);
nptr=(ULONG *)(Ptr+7);
name=(char *)*nptr;
if((ULONG)name < (ULONG)temp || (ULONG)name > (length+(ULONG)temp))
{
UnLoadSeg(segment);
return(0L);
}
km=(UWORD *)&MyKeyMap.km_LoKeyMapTypes;
for(i=0;i<16;i++) km[i]=Ptr[i+9];
SetKeyMap(&MyKeyMap);
ClearStr();
DefaultKeyMap();
UnLoadSeg(segment);
return(segment);
}
/* Fill the given KeyMap with pointer to current keymap. */
void FillKeyMap(KeyMap)
struct KeyMap *KeyMap;
{
WriteMsg->io_Command = CD_ASKKEYMAP;
WriteMsg->io_Length = 32L;
WriteMsg->io_Data = (APTR) KeyMap;
DoIO(WriteMsg);
}
/* strings are stored as sl0sO0sl1sO1...s0s1...
* where sl0 is length of string 0 and sO0 is offset from start of descriptor
* since descriptor overhead comes first sO0 is number of bytes in descriptor
* since contiguous and monotonically increasing the last string offset +
* length is the total length.
*/
long DLength(DString)
UBYTE *DString;
{
long temp;
int i,num;
temp=num=DString[1]; /* number of strings in descriptor */
for (i=0;i<num;i++,i++) temp+=DString[i]; /* total length of strings */
return(temp);
}
FreeKeyMap(which)
int which;
{
FreeMem(LoTypes,120L);
if(which>1)FreeMem(LoMap,480L);
if(which>2)FreeMem(LoCap,15L);
if(which>3)FreeMem(LoRep,15L);
}
/* Make a new string so the FreeMem does not crash */
void NewStr(key)
int key;
{
int i,j,in,out,len,desc;
UBYTE type;
told=(UBYTE *)LoMap[key];
tlen=DLength(told); /* total length of strings + descriptor */
tnew=(UBYTE *)AllocMem(tlen,0L);
if(tnew==0)
{
ClearStr(key);
FreeKeyMap(4);
abort=1;
return;
}
type=LoTypes[key]&0x07;
desc=out=DescLen[type]; /* account for bytes in descriptor */
for(i=0;i<desc;i++)
{
len=tnew[i]=told[i];
i++;
in=told[i];
tnew[i]=out;
for(j=0;j<len;j++)tnew[out+j]=told[in+j];
out+=len;
}
LoMap[key]=(ULONG)tnew;
}
void ConsoleCleanup()
{
CloseDevice(WriteMsg);
DeleteStdIO(WriteMsg);
DeletePort(WritePort);
}
/* take string and put in DStr array for easy editing */
void String(key)
int key;
{
int i,in,out,test,oldtest,offset;
UBYTE type;
for (i=0;i<8;i++) DStr[i].length=DStr[i].string[0]=NULL;
type=LoTypes[key]&0x07;
if (LoTypes[key]&0x40) /* strings */
{
told=(UBYTE *)LoMap[key];
oldtest=-1;
in=0;
for(out=0;out<8;out++)
{
if ((test=(type&out))>oldtest)
{
oldtest=test;
DStr[out].length=told[(in<<1)]; /* length */
offset=told[(in<<1)+1]; /* offset */
for(i=0;i<DStr[out].length;i++)DStr[out].string[i]=told[offset+i];
DStr[out].string[i]=NULL;
in++;
}
}
}
else /* plain keys */
{
told=(UBYTE *)&LoMap[key];
if((type&7)==7) type=3; /* special case of ctrl with bits 5&6 to 0 */
oldtest=-1;
in=3;
for(out=0;out<8;out++)
{
if ((test=(type&out))>oldtest)
{
oldtest=test;
DStr[out].length=1; /* length */
DStr[out].string[0]=told[in]; /* key value */
DStr[out].string[1]=NULL;
--in;
}
}
}
} /* end of String */
/* put string back in standard Descriptor format from DStr array */
DeString(key)
int key;
{
int shift,alt,ctrl,i,offset,keyflag,sum,test,oldtest,in,out;
UBYTE type;
shift =DStr[1].length+DStr[3].length+DStr[5].length+DStr[7].length;
alt =DStr[2].length+DStr[3].length+DStr[6].length+DStr[7].length;
ctrl =DStr[4].length+DStr[5].length+DStr[6].length+DStr[7].length;
type=0;
if (shift) type|=1;
if (alt) type|=2;
if (ctrl) type|=4;
offset=tlen=DescLen[type]; /* account for bytes in descriptor */
keyflag=1; /* true mean it is a key */
for (sum=0,i=0;i<8;i++)
{
if (DStr[i].length>1) keyflag=0;
sum+=DStr[i].length;
}
if (sum>4) keyflag=0;
if (!keyflag) /* strings */
{
for (i=0;i<8;i++) tlen+=DStr[i].length;
tnew=AllocMem(tlen,0L);
if(tnew==0)
{
ClearStr(120);
FreeKeyMap(4);
abort=1;
return;
}
if (LoTypes[key]&0x40)
{
told=(UBYTE *)LoMap[key];
FreeMem(told,DLength(told));
}
oldtest=-1;
in=0;
for(out=0;out<8;out++)
{
if ((test=(type&out))>oldtest)
{
oldtest=test;
tnew[(in<<1)]=DStr[out].length; /* length */
tnew[(in<<1)+1]=offset; /* offset */
for(i=0;i<DStr[out].length;i++)tnew[offset+i]=DStr[out].string[i];
offset+=DStr[out].length;
in++;
}
}
LoMap[key]=(ULONG)tnew;
LoTypes[key]=0x40|type;
}
else /* plain keys */
{
told=(UBYTE *)&LoMap[key];
oldtest=-1;
in=3;
for(out=0;out<8;out++)
{
if ((test=(type&out))>oldtest)
{
oldtest=test;
told[in]=DStr[out].string[0]; /* key value */
--in;
}
}
if (type!=3 || LoTypes[key]!=7) LoTypes[key]=type;
}
}
/* Save off current keymap in hunk format (not easy)*/
ULONG
SaveKeyMap(strng)
char *strng;
{
return(1L);
}
AllocKeyMap()
{
LoTypes=(UBYTE *)AllocMem(120L,0L);
if(LoTypes==0) goto Cancel;
LoMap= (ULONG *)AllocMem(480L,0L);
if(LoMap==0)
{
FreeKeyMap(1);
goto Cancel;
}
LoCap= (UBYTE *)AllocMem(15L,0L);
if(LoCap==0)
{
FreeKeyMap(2);
goto Cancel;
}
LoRep= (UBYTE *)AllocMem(15L,0L);
if(LoRep==0)
{
FreeKeyMap(3);
goto Cancel;
}
HiTypes=LoTypes+64;
HiMap= LoMap+64;
HiCap= LoCap+8;
HiRep= LoRep+8;
return;
Cancel:
abort=1;
return;
}