#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>
#include <X11/keysym.h>
#include <X11/keysymdef.h>
#include <math.h>
#ifndef WCTYPE
#include <ctype.h>
#else
#include <wctype.h>
#endif
#include "txtview.bitmap"
#include "mykeydef.h"
#define MAXLINES 5000
#define MAXCOMMENTS 500
#define xds(a) { XDrawString(display,w,small_gc,0,CURY_OFFs,a,strlen(a));\
return;}
typedef struct {
char *text,*action;
int aflag;
} ACTION;
extern char *save_eqn[MAXLINES];
extern ACTION comments[MAXCOMMENTS];
extern int n_comments,NLINES;
extern Display *display;
extern int screen;
extern GC gc, small_gc;
extern int DCURX,DCURXs,DCURY,DCURYs,CURY_OFFs,CURY_OFF;
#define MYMASK (ButtonPressMask |\
ButtonReleaseMask |\
KeyPressMask |\
ExposureMask |\
StructureNotifyMask |\
LeaveWindowMask |\
EnterWindowMask)
typedef struct {
Window up,down,pgup,pgdn,kill,home,end,base,text,src,action;
int here,first,hgt,wid,nlines,which;
int dh,dw;
} TXTVIEW;
TXTVIEW txtview;
/*
[Up] [Down] [PgUp] [PgDn] [Kill]
[Home] [End] [Src] [Actn]
*/
int txt_view_events(XEvent ev)
{
int x,y;
Window w;
if(txtview.here==0)return;
switch(ev.type){
case Expose:
case MapNotify:
redraw_txtview(ev.xany.window);
break;
case ConfigureNotify:
if(ev.xconfigure.window!=txtview.base)return;
x=ev.xconfigure.width;
y=ev.xconfigure.height;
resize_txtview(x,y);
break;
case EnterNotify:
enter_txtview(ev.xexpose.window,2);
break;
case LeaveNotify:
enter_txtview(ev.xexpose.window,1);
break;
case ButtonPress:
txtview_press(ev.xbutton.window,ev.xbutton.x,ev.xbutton.y);
break;
case KeyPress:
txtview_keypress(ev);
break;
}
}
txtview_keypress(XEvent ev)
{
Window w=ev.xkey.window;
int maxlen=64;
char ks;
if(w==txtview.base||w==txtview.text){
ks=(char)get_key_press(&ev);
if(ks==UP){txtview_press(txtview.up,0,0); return;}
if(ks==DOWN){txtview_press(txtview.down,0,0); return;}
if(ks==PGUP){txtview_press(txtview.pgup,0,0); return;}
if(ks==PGDN){txtview_press(txtview.pgdn,0,0); return;}
if(ks==HOME){txtview_press(txtview.home,0,0); return;}
if(ks==END){txtview_press(txtview.end,0,0); return;}
}
}
enter_txtview(Window w,int val)
{
if(w==txtview.up||w==txtview.down||w==txtview.pgup||
w==txtview.pgdn||w==txtview.home||w==txtview.end||
w==txtview.src||w==txtview.action||w==txtview.kill)
XSetWindowBorderWidth(display,w,val);
}
do_txt_action(char *s)
{
get_graph();
extract_action(s);
ping();
chk_delay();
redraw_params();
redraw_ics();
reset_graph();
}
resize_txtview(int w,int h)
{
int hgt=h-8-3*DCURYs;
XMoveResizeWindow(display,txtview.text,2,3*DCURYs+5,w-4,hgt);
txtview.nlines=(int)(hgt/DCURY);
/* printf(" nlines=%d \n",txtview.nlines); */
}
txtview_press(Window w,int x,int y)
{
int j;
int nt;
if(txtview.which==1)
nt=n_comments;
else
nt=NLINES;
if(w==txtview.text){
if(txtview.which==0)return;
if(x>(2*txtview.dw))return;
j=txtview.first+y/txtview.dh;
if((j<n_comments)&&(comments[j].aflag>0))
do_txt_action(comments[j].action);
return;
}
if(w==txtview.up){
if(txtview.first>0){
txtview.first-=1;
redraw_txtview_text();
}
}
if(w==txtview.down){
j=txtview.first+1+txtview.nlines;
if(j<=nt){
txtview.first+=1;
redraw_txtview_text();
}
}
if(w==txtview.home){
txtview.first=0;
redraw_txtview_text();
}
if(w==txtview.end){
j=nt-txtview.nlines;
if(j>=0){
txtview.first=j;
redraw_txtview_text();
}
}
if(w==txtview.kill){
txtview.here=0;
XDestroySubwindows(display,txtview.base);
XDestroyWindow(display,txtview.base);
}
if(w==txtview.pgup){
j=txtview.first-txtview.nlines;
if(j<0)j=0;
txtview.first=j;
redraw_txtview_text();
}
if(w==txtview.pgdn){
j=txtview.first+txtview.nlines;
if(j<nt){
txtview.first=j;
redraw_txtview_text();
}
}
if(w==txtview.src){
txtview.which=0;
redraw_txtview_text();
}
if(w==txtview.action){
if(n_comments>0){
txtview.which=1;
redraw_txtview_text();
}
}
}
redraw_txtview(Window w)
{
if(w==txtview.text)
redraw_txtview_text();
if(w==txtview.up)
xds("Up");
if(w==txtview.down)
xds("Down");
if(w==txtview.pgup)
xds("PgUp");
if(w==txtview.pgdn)
xds("PgDn");
if(w==txtview.kill)
xds("Kill");
if(w==txtview.home)
xds("Home");
if(w==txtview.end)
xds("End");
if(w==txtview.src)
xds("Source");
if(w==txtview.action)
xds("Action");
}
redraw_txtview_text()
{
int i,j;
XClearWindow(display,txtview.text);
for(i=0;i<txtview.nlines;i++){
/* printf("lines=%d NLINES=%d first=%d \n",
txtview.nlines,NLINES,txtview.first); */
j=i+txtview.first;
switch(txtview.which){
case 0:
if(j<NLINES){
XDrawString(display,txtview.text,gc,txtview.dw,i*txtview.dh+CURY_OFFs,
save_eqn[j],strlen(save_eqn[j]));
/* printf("line: %d\n",j); */
}
break;
case 1:
if(j<n_comments)
XDrawString(display,txtview.text,gc,txtview.dw,i*DCURY+CURY_OFFs,
comments[j].text,strlen(comments[j].text));
break;
}
}
}
init_txtview()
{
txtview.here=0;
txtview.dh=DCURY;
txtview.dw=DCURX;
txtview.which=0;
txtview.first=0;
}
make_txtview()
{
int minwid=DCURXs*40,minlen=3*DCURYs+8+10*DCURY;
Window base,w;
int ww=7*DCURXs,hh=DCURYs+4;
static char *wname[]={"Text Viewer"},*iname[]={"Txtview"};
XWMHints wm_hints;
XTextProperty winname,iconname;
XSizeHints size_hints;
if(txtview.here==1)return;
base=make_window(RootWindow(display,screen),0,0,minwid,minlen,4);
txtview.base=base;
XSelectInput(display,base,ExposureMask|KeyPressMask|ButtonPressMask|
StructureNotifyMask);
XStringListToTextProperty(wname,1,&winname);
XStringListToTextProperty(iname,1,&iconname);
size_hints.flags=PPosition|PSize|PMinSize;
size_hints.min_width=minwid;
size_hints.min_height=minlen;
size_hints.x=0;
size_hints.y=0;
wm_hints.initial_state=IconicState;
wm_hints.flags=StateHint;
XSetWMProperties(display,base,&winname,&iconname,
NULL,0,&size_hints,NULL,NULL);
make_icon(txtview_bits,txtview_width,txtview_height,base);
txtview.up=make_window(base,DCURXs,2,2*DCURXs,DCURYs,1);
txtview.down=make_window(base,DCURXs+ww,2,4*DCURXs,DCURYs,1);
txtview.pgup=make_window(base,DCURXs+2*ww,2,4*DCURXs,DCURYs,1);
txtview.pgdn=make_window(base,DCURXs+3*ww,2,4*DCURXs,DCURYs,1);
txtview.kill=make_window(base,DCURXs+4*ww,2,4*DCURXs,DCURYs,1);
txtview.home=make_window(base,DCURXs,2+hh,4*DCURXs,DCURYs,1);
txtview.end=make_window(base,DCURXs+ww,2+hh,3*DCURXs,DCURYs,1);
txtview.src=make_window(base,DCURXs+2*ww,2+hh,6*DCURXs,DCURYs,1);
txtview.action=make_window(base,DCURXs+3*ww,2+hh,6*DCURXs,DCURYs,1);
txtview.text=make_window(base,2,3*DCURYs+5,minwid-4,10*DCURY,1);
txtview.here=1;
txtview.nlines=10;
txtview.which=0;
txtview.first=0;
txtview.dh=DCURY;
txtview.dw=DCURX;
}
syntax highlighted by Code2HTML, v. 0.9.1