pkg://twcw-1.1.tar.gz:79235/
twcw-1.1/twcw.c
downloads
/*
* twcw: A gui application that sends Morse Code
* Copyright (C) 1997 Ted Williams WA0EIR
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of
* the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be
* useful, but WITHOUT ANY WARRANTY; without even the implied
* warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
* PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public
* License along with this program; if not, write to the Free
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139,
* USA.
*
* Version 1.1 - MAR 2003
*/
/*
* main Function
* main calls the following functions:
* 1) build_widgets() to create the interface.
* 2) setup() to initialize a message queue and signal traping.
* 3) fork_sendCW() to create the child process.
* main then adds a work proceedure (do_work) and enters the event loop.
*/
#include "common.h"
#include "twcw.h"
#include "vibroplex.xpm"
/* Global */
AppRes app_res;
int main (int argc, char *argv[])
{
Widget iconwin;
Pixmap pixmap, mask;
XpmAttributes pix_attributes;
XpmColorSymbol transparentColor[1] = {{NULL, "none", 0}};
struct stat buf;
Pixel bg;
Dimension width;
/*
* Describe the application defined resources. This struct is
* for the app resources which are read from the resource
* file. See the resource file (Twcw) for more info.
*/
XtResource app_res_desc[] =
{
{
XmNcall, /* Name */
XmCCall, /* Class */
XmRString, /* Target data type */
sizeof (char *), /* size of target type */
XtOffsetOf (AppRes, call), /* Offset into LogRes */
XtRImmediate, "N0CALL" /* Default data type */
},
{
XmNbuttonNames, /* Name */
XmCButtonNames, /* Class */
XmRStringTable, /* Target data type */
sizeof (char **), /* size of target type */
XtOffsetOf (AppRes, buttonNames), /* Offset into LogRes */
XtRImmediate, "Bogus Names" /* Default value */
},
{
XmNcpuSpeed, /* Name */
XmCCpuSpeed, /* Class */
XmRString, /* Target data type */
sizeof (char *), /* size of target type */
XtOffsetOf (AppRes, cpuSpeed), /* Offset into LogRes */
XtRImmediate, "100.0" /* Default value */
},
{
XmNserialDevice, /* Name */
XmCSerialDevice, /* Class */
XmRString, /* Target data type */
sizeof (char *), /* size of target type */
XtOffsetOf (AppRes, serialDevice), /* Offset into LogRes */
XtRImmediate, "/dev/ttyS1" /* Default value */
}
};
#ifdef XmVERSION_STRING
extern const char _XmVersionString[];
printf ("Compiled with %s\n", XmVERSION_STRING + 4);
printf ("Running with %s\n", _XmVersionString + 4);
#endif
/*
* Initialize the tool kit, create the application and icon shells,
* get the app defined resources and check that dirPath and
* buttonNames are defined. This does not check for valid
* pathnames. They can be NULL - just gota have twcw.dirPath
* and twcw.buttonNames in Twcw.
*/
shell = XtVaAppInitialize (&ac, "Twcw", NULL, 0, &argc, argv, NULL,
XmNmwmFunctions, MWM_FUNC_ALL | MWM_FUNC_CLOSE,
XmNminHeight,250,
XmNiconName, "TWCW",
NULL);
/*
* Create Icon window and its pixmap
*/
iconwin = XtVaAppCreateShell ("Iconwin", "shell",
wmShellWidgetClass, XtDisplay(shell),
XmNmappedWhenManaged, False,
XmNwidth, 60,
XmNheight, 40,
NULL);
XtVaGetValues (iconwin,
XmNbackground, &bg,
NULL);
transparentColor[0].pixel = bg;
pix_attributes.closeness = 40000;
pix_attributes.valuemask = XpmColorSymbols | XpmCloseness;
pix_attributes.colorsymbols = transparentColor;
pix_attributes.numsymbols = 1;
XpmCreatePixmapFromData (XtDisplay(shell),
DefaultRootWindow (XtDisplay(shell)),
vibroplex, &pixmap, &mask, &pix_attributes);
/*
* Get resources and check to see if buttonNames was set
*/
XtGetApplicationResources (shell, &app_res, app_res_desc,
XtNumber (app_res_desc), NULL, 0);
if (!strcmp ((char *)app_res.buttonNames, "Bogus Names"))
{
fprintf (stderr, "twcw: buttonNames resource not found\n");
exit (1);
}
/*
* build the widgets
*/
build_widgets (shell, &app_res);
/*
* Initialize dirpath and helppath
* and check that they are valid
*/
strcpy (dirpath, getenv ("HOME"));
strcat (dirpath, TWCWDIR); /* twcwDir is always in $HOME */
if (stat (dirpath, &buf) == -1)
{
perror ("twcw");
fprintf (stdout, "twcw: Can't find %s\n", dirpath);
exit (1);
}
strcpy (helppath, "/usr/local/share/twcw"); /* helpfile is always here */
strcat (helppath, HELPFILE);
if (stat (helppath, &buf) == -1)
{
perror ("twcw");
fprintf (stdout, "twcw: Can't find %s\n", helppath);
exit (1);
}
/*
* Setup the message queue and signal traps
*/
if (setup() == False)
{
fprintf (stderr, "twcw: Can't Open Message Queue\n");
exit (1);
}
/*
* Fork the sendCW program
*/
if ((pid = fork_sendCW(app_res.cpuSpeed, app_res.serialDevice)) == False)
{
fprintf (stderr, "twcw: Can't fork send_cw\n");
exit (1);
}
/*
* Set min width, add the Work Proceedure, and enter the event loop
*/
XtVaGetValues (shell,
XmNwidth, &width,
NULL);
XtVaSetValues (shell,
XmNminWidth, width,
NULL);
/*
* Realize and Set pixmap properties in clock_shell and iconwin
*/
XtRealizeWidget (iconwin);
XtVaSetValues (iconwin,
XmNbackgroundPixmap, pixmap,
NULL);
XtVaSetValues (shell,
XmNiconWindow, XtWindow(iconwin),
NULL);
XtAppAddWorkProc (ac, do_work, (XtPointer) 0);
XtAppMainLoop (ac);
exit (0);
}
/*
* fork_sendCW Function
* Forks the send_CW child process and returns it's pid
*/
int fork_sendCW (char *cpu_Speed, char *ser_Dev)
{
int pid;
switch (pid = fork ())
{
case -1: /* Can't fork a child */
perror ("fork");
exit (1);
case 0: /* Child comes here */
execlp ("sendCW", "sendCW", cpu_Speed, ser_Dev, NULL);
perror ("execl");
break;
default: /* Parent comes here */
break;
}
return (pid);
}
/*
* do_work Function
* Work Proceedure to get messages from the sendCW process
*/
Boolean do_work (XtPointer cdata)
{
int rtn;
struct tag1 indata;
/* First look for a WPM_DONE message */
rtn = msgrcv (qid, (struct msgbuf *) &indata,
MAX_WORD_LENGTH, WPM_DONE, IPC_NOWAIT);
if (rtn != -1)
{
XUndefineCursor (XtDisplay (shell), XtWindow (shell));
}
/* Then look for a SENT_MSG */
rtn = msgrcv (qid, (struct msgbuf *) &indata,
MAX_WORD_LENGTH, SENT_MSG, IPC_NOWAIT);
if (rtn == -1) /* if no SENT_MSG's in queue */
{
usleep(1); /* Give callbacks a chance??? */
}
else
{
XmTextFieldInsert (textf1,
XmTextFieldGetLastPosition (textf1), indata.data.word);
}
return (False); /* Always register again */
}