#include #include #include #include #include #include #include #include #include #include #include #include "DMX512.h" /* lines for mpw use, put these files in the search path select the lines here and hit enter //cpshlb "{Active}" >> "{outf}" ≥ "{errf}" //linkappl "DMX" >> "{outf}" ≥ "{errf}" //linktool "DMX" >> "{outf}" ≥ "{errf}" */ QDGlobals qd; typedef pdmxacc (*dmxP) (); // this is for the drivers' exports the app needs; therefore declare a function WindowRecord myW; // at least this appl has one window; so hardcode it here EventRecord theEvent;// same applies to the event char myT[256] = "";// this one is used at various places, in a non-handmade, hardcoded world this has to go Str255 myPT = "";// This is the placeholder to draw strings; Comes from the char / unsigned char gotcha in the universal headers Rect wrect = {40,10,440,800};// initial window bounds hardcoded Rect r = {0,0,0,0};// reused where needed Point PT; // reused where needed, e.g. for storing point from event record WindowPtr myWP = 0;// have a pointer for myW pdmxacc symAddr = 0; // as defined in DMX512.h a struct with accessor functions OSStatus status = 0; // well, everyone has something like this char gDRAW = 0; // a switch for the draw function if to draw //---------------------------------------------------------------------------------------- //#include "getapicmds.cp" pdmxacc getapicmds() // how to get an export from the system zone { pdmxacc symAddr = 0; unsigned char symClass = 0; Str255 title = "\papicmds"; long counter = 0; OSStatus status = noErr; CFragConnectionID connID; USBDeviceRef usbDevRef = kNoDeviceRef; USBDeviceDescriptor desc; UInt16 i = 0; THz gCurrentZone; while (status == noErr && i < 128) // iterate the connected usb devices { i++; status = USBGetNextDeviceByClass(&usbDevRef, &connID, 0xff, 0x00, 0x01); if (status == noErr) status = USBGetDeviceDescriptor(&usbDevRef, &desc, sizeof(desc)); if (status == noErr) if ((desc.vendor == 0xe10c) && (desc.product == 0x0100)) i = 128; if (status) return 0; } status= USBGetDriverConnectionID (&usbDevRef, &connID); printf("\n driver conn id status %i, dev ref %i, conn id %i \n",status, usbDevRef, connID); gCurrentZone = GetZone(); SetZone(SystemZone()); status = FindSymbol(connID, title, &(Ptr)symAddr, &symClass);// get the accessor struct printf("\n symaddr %p, symclass %i \n",symAddr,symClass); SetZone(gCurrentZone); return symAddr; }; //---------------------------------------------------------------------------------------- //#include "drawtask.cp" static OSStatus Mytask (void *parameter) { long counter = 0; short rowcount = 120; short digitspervalue = 3; short colcounter = 0; short rowcounter = 1; char* here = 0; char* base = 0; WindowPtr oldport; //while ( gDRAW ) // this is in main // { base = symAddr->getRXmemaddr(); // symaddr is retrieved in main and global here = base; rowcounter = 1; GetPort(&oldport); SetPort(myWP); // myWP windowpointer in main and global, there is only one WIND //BeginUpdate(myWP); // Don't bracket unless you have an update event while ( here < (base)+512 ) { MoveTo(10, ( (rowcounter++) * 12) ); // ignoring all textstyle directions while ( ((colcounter++) <= 35) && (here < (base)+512) ) { sprintf( myT ,"%03i ",(unsigned char)(*here) ); c2pstrcpy( myPT, myT); here++; GetPen(&PT); r.top = PT.v -11; r.left = PT.h; r.bottom = r.top + 12; r.right = r.left + StringWidth(myPT); EraseRect(&r); DrawString(myPT); }; colcounter=0; }; base = symAddr->getTXmemaddr(); here = base; while ( here < (base)+512 ) { MoveTo(10, ( (rowcounter++) * 12) ); // ignoring all textstyle directions while ( ((colcounter++) <= 35) && (here < (base)+512) ) { sprintf( myT ,"%03i ",(unsigned char)(*here) ); c2pstrcpy( myPT, myT); here++; GetPen(&PT); r.top = PT.v -11; r.left = PT.h; r.bottom = r.top + 12; r.right = r.left + StringWidth(myPT); EraseRect(&r); DrawString(myPT); }; colcounter=0; }; MoveTo(10, ( (rowcounter++) * 12) ); sprintf (myT,"S:%08i R:%08i, txf %08i, rxf %08i, txst %03i, rxst %03i, txsl %03i, rxsl %03i, TX:%p, RX:%p\n", symAddr->getSTATUS(), symAddr->getRUNMODE(), symAddr->getTXframecount(), symAddr->getRXframecount(), symAddr->getTXstartcode(), symAddr->getRXstartcode(), symAddr->getTXslots(), symAddr->getRXslots(), symAddr->getTXmemaddr(), symAddr->getRXmemaddr() ); c2pstrcpy( myPT, myT); GetPen(&PT); r.top = PT.v -11; r.left = PT.h; r.bottom = r.top + 13; r.right = r.left + StringWidth(myPT)+ wrect.right; EraseRect(&r); DrawString(myPT); rowcounter = 1; // EndUpdate(myWP); SetPort(oldport); // MPYield(); // and don't draw from an mp task or a thread cause you don't know the actual graphics port (yes, it is possible to invent a custom task switching procedure - but its not neccassery) // } // while return 0; }; //---------------------------------------------------------------------------------------- //#include "morse.cp" /* The guts of a morse code tutorial/training/transmission system. Set length variables to control speed and spacing. Written for Lattice C. Note short is 16 bits, int == long is 32 bits. */ // C++ comments added by Hado Hein // original file : http://www.vectorbd.com/bfd/license/stmorse.lzh // at : http://www.vectorbd.com/bfd/license/ // modified in 2002 for Mac // the way is to calculate a string down in send_morse // then use the first char of the string to see what it is a work it down via the lookup array defined here // m_send turns on the information carrier (light, sound) and then waits its time // m_pause turns off the information carrier and the waits its time // m_wait itself is here for waiting /* Initial values are for 5 WPM */ short l_dot = 240, /* 1200/WPM */ l_dash = 720, /* 3*l_dot */ l_el = 240, /* Interelement spacing == l_dot */ l_char = 480, /* Char spacing, normally 2*l_el */ l_word = 960; /* Word spacing, 4*l_dot */ /* Note that the routine actually sends l_el after each element, l_char after each character, and l_word for a space, so the character space is l_el+l_char == 3*l_el, and word space is l_el+l_char+l_word == 7*l_el, agreeing with the standards */ /* Coding table: '.' = send dit; '_' = send dah; ' ' = word space; anything else (ie, '\0') terminates sequence. */ #define NO_CODE "\0" char *codes[128] = { NO_CODE, /* 00 */ NO_CODE, /* 01 */ NO_CODE, /* 02 */ NO_CODE, /* 03 */ NO_CODE, /* 04 */ NO_CODE, /* 05 */ NO_CODE, /* 06 */ NO_CODE, /* 07 */ NO_CODE, /* 08 */ " \0", /* 09 TAB */ " \0", /* 0A \N */ NO_CODE, /* 0B */ NO_CODE, /* 0C */ NO_CODE, /* 0D */ NO_CODE, /* 0E */ NO_CODE, /* 0F */ NO_CODE, /* 10 */ NO_CODE, /* 11 */ NO_CODE, /* 12 */ NO_CODE, /* 13 */ NO_CODE, /* 14 */ NO_CODE, /* 15 */ NO_CODE, /* 16 */ NO_CODE, /* 17 */ NO_CODE, /* 18 */ NO_CODE, /* 19 */ NO_CODE, /* 1A */ NO_CODE, /* 1B */ NO_CODE, /* 1C */ NO_CODE, /* 1D */ NO_CODE, /* 1E */ NO_CODE, /* 1F */ " \0", /* 20 SPACE */ "..._.\0", /* 21 ! Understood */ "._.._.\0", /* 22 " */ "._._..\0", /* 23 # Paragraph */ "..._.._\0", /* 24 $ Dollar sign */ "_._._\0", /* 25 % Start/Attention */ "._...\0", /* 26 & Wait */ ".____.\0", /* 27 ' */ "_.__.\0", /* 28 ( */ "_.__._\0", /* 29 ) */ "..._._\0", /* 2A * End of Work */ "._._.\0", /* 2B + End of Message */ "__..__\0", /* 2C , */ "_..._\0", /* 2D - */ "._._._\0", /* 2E . */ "_.._.\0", /* 2F / */ "_____\0", /* 30 0 */ ".____\0", /* 31 1 */ "..___\0", /* 32 2 */ "...__\0", /* 33 3 */ "...._\0", /* 34 4 */ ".....\0", /* 35 5 */ "_....\0", /* 36 6 */ "__...\0", /* 37 7 */ "___..\0", /* 38 8 */ "____.\0", /* 39 9 */ "___...\0", /* 3A : */ "_._._.\0", /* 3B ; */ NO_CODE, /* 3C < */ "_..._\0", /* 3D = Double dash */ "._._\0", /* 3E > Newline */ "..__..\0", /* 3F ? */ NO_CODE, /* 40 @ */ "._\0", /* 41 A */ "_...\0", /* 42 B */ "_._.\0", /* 43 C */ "_..\0", /* 44 D */ ".\0", /* 45 E */ ".._.\0", /* 46 F */ "__.\0", /* 47 G */ "....\0", /* 48 H */ "..\0", /* 49 I */ ".___\0", /* 4A J */ "_._\0", /* 4B K */ "._..\0", /* 4C L */ "__\0", /* 4D M */ "_.\0", /* 4E N */ "___\0", /* 4F O */ ".__.\0", /* 50 P */ "__._\0", /* 51 Q */ "._.\0", /* 52 R */ "...\0", /* 53 S */ "_\0", /* 54 T */ ".._\0", /* 55 U */ "..._\0", /* 56 V */ ".__\0", /* 57 W */ "_.._\0", /* 58 X */ "_.__\0", /* 59 Y */ "__..\0", /* 5A Z */ NO_CODE, /* 5B [ (start prosign, see below) */ "........\0", /* 5C \\ Error */ NO_CODE, /* 5D ] (end prosign, see below) */ NO_CODE, /* 5E ^ */ "..__._\0", /* 5F _ */ NO_CODE, /* 60 ` */ "._\0", /* 61 a */ "_...\0", /* 62 b */ "_._.\0", /* 63 c */ "_..\0", /* 64 d */ ".\0", /* 65 e */ ".._.\0", /* 66 f */ "__.\0", /* 67 g */ "....\0", /* 68 h */ "..\0", /* 69 i */ ".___\0", /* 6A j */ "_._\0", /* 6B k */ "._..\0", /* 6C l */ "__\0", /* 6D m */ "_.\0", /* 6E n */ "___\0", /* 6F o */ ".__.\0", /* 70 p */ "__._\0", /* 71 q */ "._.\0", /* 72 r */ "...\0", /* 73 s */ "_\0", /* 74 t */ ".._\0", /* 75 u */ "..._\0", /* 76 v */ ".__\0", /* 77 w */ "_.._\0", /* 78 x */ "_.__\0", /* 79 y */ "__..\0", /* 7A z */ NO_CODE, /* 7B { */ NO_CODE, /* 7C | */ NO_CODE, /* 7D } */ NO_CODE, /* 7E ~ */ NO_CODE /* 7F */ }; char* target = 0; //---------------------------------------------------------------------------------------- short m_wait( short len ) /* wait around for len milliseconds */ { long starttick = TickCount(); long endtick = (starttick + (len/30) ); // here is the brake for unchanged values take /1 but then also take gem on an old machine // dividing 30 is quite ok and readable // the System Clock is said to be running in ms if( len == 0 ) return( 0 ); while( TickCount() <= endtick ) {Mytask(0);SystemTask();} }; //---------------------------------------------------------------------------------------- short m_pause( short len ) /* pause len milliseconds */ { // SOUND OFF (*target) = 0; return( m_wait( len ) ); }; /* m_pause */ //---------------------------------------------------------------------------------------- short m_send( short len ) /* send tone for len milliseconds */ { // SOUND ON (*target) = 255; return( m_wait( len ) ); }; /* m_send */ //---------------------------------------------------------------------------------------- /* send_morse: sends each character in the supplied string subject to the above translation table. Exception: '[' sets l_char :== 0 and ']' returns l_char to its original value. Thus prosigns can be composed (eg, [SK], [KN]) rather than using the equivalent punctuation given above. It is the sender's responsibility to see that the results are meaningful; send_morse will happily cram together anything, including [absolute garbage]. Note that end of string simulates ']' so prosigns cannot be broken into separate calls to send_morse. Also note that for multiple calls, str should start or end with a space character (' ', '\t', '\n') because the first character of a new str will be sent immediately, and only inter-character space is given following the last character of str */ short send_morse( char *str ) { char secstr[100] =" cq cq cq Love Parade 2002 Berlin says : access peace. +\0"; long starttime = TickCount(); long endtime = TickCount(); short ll_char, i, len, j, els; char ch, elem, *seq; // SOUND PRE PROC target = (symAddr->getTXmemaddr())+511; if (str==0) str=secstr; printf("\n MORSE CALLED \"%s\"\n at %p\n", str,target); ll_char = l_char; /* Actual inter-character space */ len = strlen( str ); for( i=0; i #define kAppleMenu 128 #define kFileMenu 1001 #define kEditMenu 1002 #define kModeMenu 1003 #define kConfigMenu 1004 #define kSpecialMenu 1005 enum { _about = 1}; enum { _new = 1, _open, _close, _save, _revert=6, _import=8, _export, _getInfo=11, _pageSetup=13, _printone, _print, _quit=17 }; enum { _undo = 1, _cut=3, _copy, _paste, _clear, _duplicate=8, _selectAll }; enum { _copydmx = 1}; enum { _dmxout = 1, _dmxin, _startTX = 4, _startRX, _chTX = 7}; enum { _morse = 1, _limit, _route, _transform}; OSErr DispatchMenu(long* menuCommand, WindowPtr frontWindow) // Typical System 7,8,9 non carbon event dispatching { OSErr error = noErr; short menu = 0; short item = 0; Str255 iName; char i = 0; short j = 0; MenuHandle aMenu = 0; menu = HiWrd(*menuCommand); item = LoWrd(*menuCommand); if(!item) return false; // that user went away switch(menu) { case kAppleMenu: if (item==_about); else { GrafPtr oldPort; GetPort(&oldPort); aMenu = GetMenuHandle(kAppleMenu); GetMenuItemText(aMenu, item, iName); OpenDeskAcc(iName); SetPort(oldPort); } break; case kFileMenu: // based on front win action if (item==_quit) gDRAW = 0; break; case kEditMenu: break; case kModeMenu: if (item==_copydmx) { short theChar; aMenu = GetMenuHandle(kModeMenu); GetItemMark(aMenu, _copydmx, &theChar); // first see what the menu says we're doing if (theChar) SetItemMark(aMenu, _copydmx, noMark);// alter it else SetItemMark(aMenu, _copydmx, checkMark);// alter it if (theChar) symAddr->setCOPYMODE(0); // set runmode also in interface else symAddr->setCOPYMODE(1); // " } break; case kConfigMenu: if (item==_dmxout) { short theChar; aMenu = GetMenuHandle(kConfigMenu); GetItemMark(aMenu, _dmxout, &theChar); if (theChar) SetItemMark(aMenu, _dmxout, noMark); else SetItemMark(aMenu, _dmxout, checkMark); } else if (item==_dmxin) { short theChar; aMenu = GetMenuHandle(kConfigMenu); GetItemMark(aMenu, _dmxin, &theChar); if (theChar) SetItemMark(aMenu, _dmxin, noMark); else SetItemMark(aMenu, _dmxin, checkMark); } // gather switch ./. akt config und reset config // ggf. turn off copymode break; case kSpecialMenu: if (item==_morse) send_morse(0); if (item==_limit) { short somuch = symAddr->getTXslots(); symAddr->setTXslots ( (--somuch) ); };// this is not what the menu says, but the dialog boxes and the logic of the config menu are not stable yet if (item==_route) { short somuch = symAddr->getTXstartcode(); symAddr->setTXstartcode ( (++somuch) ); };// " if (item==_transform) { short somuch = symAddr->getRXstartcode(); symAddr->setRXstartcode ( (++somuch) ); };// " // later, to be done, these functions go config menu with text entry, checking in a DLOG, these menu items here would get also specialized functions like the draw task break; } HiliteMenu(0);// clean up InvalMenuBar();// redraw all menus according to their perhaps changed settings return error; } //---------------------------------------------------------------------------------------- OSErr DispatchEvent() // Typical System 7,8,9 non carbon event dispatching { OSErr error = noErr; short eventWhere = 0; WindowPtr hitWindow = 0; long menuComm = 0; Rect dragRect; short windowType; eventWhere = FindWindow(theEvent.where, &hitWindow); /* works always */ switch (theEvent.what) { case mouseDown: switch (eventWhere) { case inMenuBar: menuComm = MenuSelect(theEvent.where); if(menuComm) error = DispatchMenu(&menuComm,hitWindow);// HIT window mustn't be FRONT ! CHANGE LATER break; case inDrag: dragRect = (**GetGrayRgn()).rgnBBox; DragWindow(hitWindow, theEvent.where, &dragRect); break; case inGrow: break; case inGoAway: break; case inZoomIn: case inZoomOut: break; case inDesk: break; case inSysWindow: SystemClick(&theEvent, hitWindow); break; case inContent: break; } /* end of mclick */ break; case keyDown: case autoKey: if (theEvent.modifiers & cmdKey) { menuComm = MenuKey( (char)(theEvent.message&charCodeMask) ); error = DispatchMenu(&menuComm,hitWindow); }// see in menubar break; case mouseUp: case keyUp: break; case updateEvt: break; case activateEvt: break; case diskEvt: if (HiWrd(theEvent.message) != noErr) { Point ignored; ignored.h = ignored.v = 90; /* sys7*/ DILoad(); /* load the disk initialization package */ DIBadMount(ignored, theEvent.message); DIUnload(); /* unload the disk initialization package */ } break; case osEvt: break; case kHighLevelEvent: break; case nullEvent: break; } return 0; }//---------------------------------------------------------------------------------------- void main() { short curresfile = 0; //Mac Handle mBar; //Mac MenuHandle appleMenu;//Mac InitGraf(&qd.thePort); InitFonts(); InitWindows(); InitMenus(); TEInit(); InitDialogs(0L); InitCursor(); symAddr = getapicmds();// find driver and get access if (symAddr) printf ("S:%i R:%i, txf %i, rxf %i, txst %i, rxst %i, txsl %i, rxsl %i, P:%p\n", symAddr->getSTATUS(), symAddr->getRUNMODE(), symAddr->getTXframecount(), symAddr->getRXframecount(), symAddr->getRXstartcode(), symAddr->getTXstartcode(), symAddr->getRXslots(), symAddr->getTXslots(),symAddr->getRXmemaddr() ); // the driver directly sets an interface so stdlog the state else {printf ("\n\n no api \n"); return;} // bail else os will crash curresfile = CurResFile();// Mac - before getting rsrcs mBar = GetNewMBar((short)128);// Get the MenuBar SetMenuBar(mBar); // Set it appleMenu = GetMenuHandle(kAppleMenu); // Get Apple Menu (installed with MBar) AppendResMenu(appleMenu,'DRVR'); // Extend Apple Menu DrawMenuBar(); // to do : update menubar according to getconfig / copymode myWP = NewCWindow(&myW, &wrect, myPT, true, 4, WindowPtr(-1), false, 0); // got here, ok get a WIND from System SetPort(myWP);// make it ready to draw (from this process!) ForeColor(33);// guess, black TextSize(9); TextFont(0);// guess, small font while ( gDRAW ) { WaitNextEvent( (-1) , &theEvent, 5, (RgnHandle)0); DispatchEvent();Mytask(0);}; // First get a (null) event, Dispatch if Command; anyhow draw the stuff again (Mytask) gDRAW = 0;// security if (myWP) CloseWindow(myWP);// the system would close it anyway when the process goes, being tidy is a good feeling };