3
* gnutime/gnuavi test program - Xt frontend
5
* Copyright (C) 1998 Rasca, Berlin
8
* This program is free software; you can redistribute it and/or modify
9
* it under the terms of the GNU General Public License as published by
10
* the Free Software Foundation; either version 2 of the License, or
11
* (at your option) any later version.
13
* This program is distributed in the hope that it will be useful,
14
* but WITHOUT ANY WARRANTY; without even the implied warranty of
15
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
* GNU General Public License for more details.
18
* You should have received a copy of the GNU General Public License
19
* along with this program; if not, write to the Free Software
20
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25
#include <X11/Intrinsic.h>
26
#include <X11/Shell.h>
27
#include <X11/StringDefs.h>
28
#ifdef HasSharedMemory
31
#include <X11/extensions/XShm.h>
37
static void x_fini(void);
39
static XtAppContext gAppCont;
40
static Widget gTop, gVid;
41
static String fallback[] = {
43
"*translations: #override \\n\\"
44
" <Key>Q: quit() \\n\\"
45
" <Key>P: play() \\n\\"
46
" <Key>S: stop() \\n",
51
int loop; /* flag if looping is on */
52
int depth; /* display bits per pixel */
64
* called if "q" was pressed
67
action_quit (Widget w, XEvent *ev, String *parms, Cardinal *num_parms)
75
action_stop (Widget w, XEvent *ev, String *parms, Cardinal *num_parms)
77
printf ("stop() not done ..\n");
83
action_play (Widget w, XEvent *ev, String *parms, Cardinal *num_parms)
85
printf ("play() not done..\n");
88
static XtActionsRec action_tab[] = {
89
{"stop", action_stop},
90
{"play", action_play},
91
{"quit", action_quit},
98
evh_exit (Widget w, XtPointer xtp, XEvent *ev, Boolean *boo)
100
if ((ev->type == ClientMessage) &&
101
(ev->xclient.format == 32) &&
102
(ev->xclient.data.l[0] == *((Atom*)xtp)))
107
x_play_sound (XtPointer xtp, XtIntervalId *id)
112
* returns time in mili secs
117
struct timeval curr_time;
118
gettimeofday (&curr_time, NULL);
119
return ((curr_time.tv_sec * 1000L + curr_time.tv_usec / 1000L)&0x7FFFFF);
123
* time callback procedure to display a frame
126
x_display_frame (XtPointer xtp, XtIntervalId *id)
128
app *ap = (app *)xtp;
129
video *vid = ap->vid;
130
XImage *ximage = ap->ximage;
131
char *buf = ap->image;
132
unsigned char *snd_buf;
134
int todo = 1, snd_size =0;
137
ap->time_ms = time_ms();
138
/* printf (" -t %ld %ld\n", ap->time_ms, time); */
141
switch (vid_next_in(vid)) {
143
if (!vid_get_frame (vid, buf)) {
147
XtAppAddTimeOut (gAppCont, vid->tpf, x_display_frame, ap);
150
/* printf (" -f\n"); */
155
if (vid_get_sound (vid, &snd_buf, &snd_size)) {
156
snd_play_data (snd_buf, snd_size, 0);
157
/* printf (" -s snd_size=%d\n", snd_size); */
168
XtAppAddTimeOut (gAppCont, vid->tpf, x_display_frame, ap);
174
#ifdef HasSharedMemory
176
XShmPutImage (XtDisplay(gTop), XtWindow(ap->widget), ap->gc, ximage,
177
0, 0, 0, 0, vid->width, vid->height, True);
180
XPutImage (XtDisplay(gTop), XtWindow(ap->widget), ap->gc, ximage,
181
0, 0, 0, 0, vid->width, vid->height);
183
time = vid->tpf - (time_ms() - time) ;
184
/* printf (" -t %ld\n", time); */
186
if (vid->tpf + time < 0)
187
vid_skip_frame (vid);
191
printf ("x_display_frame() time=%ld tpf=%d\n", time, vid->tpf);
193
XtAppAddTimeOut (gAppCont, time, x_display_frame, ap);
199
x_init (int *argc, char **argv)
201
gTop = XtVaAppInitialize (&gAppCont, "XMplay", NULL, 0,
202
argc, argv, fallback, XtNinput, True, NULL);
203
XtAppAddActions (gAppCont,
204
action_tab, sizeof(action_tab)/sizeof(XtActionsRec));
210
x_main (int width, int height)
214
gVid = XtVaCreateManagedWidget ("xvid", coreWidgetClass, gTop,
215
XtNwidth, width, XtNheight, height, NULL);
216
XtRealizeWidget (gTop);
217
wm_del = XInternAtom (XtDisplay(gTop), "WM_DELETE_WINDOW", False);
218
XSetWMProtocols (XtDisplay(gTop), XtWindow(gTop), &wm_del, 1);
219
XtAddEventHandler (gTop, NoEventMask, True, evh_exit, &wm_del);
225
static XShmSegmentInfo shminfo;
230
x_loop (video *vid, int use_shm, int loop, int use_snd)
233
Screen *screen = XtScreen (gTop);
234
Display *dpy = XtDisplay(gTop);
235
Visual *vis = DefaultVisualOfScreen (screen);
236
#ifdef HasSharedMemory
239
use_shm = XShmQueryExtension(dpy);
247
ap.depth = DefaultDepthOfScreen (screen);
249
ap.gc = XCreateGC (dpy, XtWindow(ap.widget), 0, NULL);
250
#ifdef HasSharedMemory
252
ap.ximage =XShmCreateImage (dpy, vis, ap.depth, ZPixmap, NULL,
253
&shminfo, vid->width, vid->height);
257
ap.image = XtMalloc (vid->width * vid->height * 4 /* ap.bpp / 8*/);
258
ap.ximage =XCreateImage (dpy, vis,
259
ap.depth, ZPixmap, 0, ap.image, vid->width, vid->height,
264
fprintf (stderr, "Can't create XImage!\n");
267
pad = ap.ximage->bytes_per_line -
268
ap.ximage->width * ap.ximage->bits_per_pixel / 8 ;
270
printf (" ximage bytes /p line = %d\n", ap.ximage->bytes_per_line);
271
printf (" bpp = %d\n", ap.ximage->bits_per_pixel);
272
printf (" depth = %d\n", ap.ximage->depth);
273
printf (" pad = %d\n", pad);
275
switch (ap.ximage->depth) {
277
codec = VV_COD_RGB555;
280
codec = VV_COD_RGB565;
283
codec = VV_COD_RGB888;
286
printf ("visual not supported\n");
289
vid_set_video_parms (vid, codec, pad);
291
#ifdef HasSharedMemory
293
shminfo.shmid = shmget (IPC_PRIVATE,
294
vid->width * vid->height * 4 /* (ap.bpp/8)*/,
296
if (shminfo.shmid == -1) {
300
shminfo.shmaddr = ap.image = shmat (shminfo.shmid, 0, 0);
301
shminfo.readOnly = False;
302
ap.ximage->data = shminfo.shmaddr;
303
if (XShmAttach (dpy, &shminfo) == 0) {
304
perror ("XShmAttach()");
309
ap.use_shm = use_shm;
310
ap.use_snd = use_snd;
311
ap.time_ms = time_ms();
313
XtAppAddTimeOut (gAppCont, 1, x_play_sound, &ap);
314
XtAppAddTimeOut (gAppCont, 2, x_display_frame, &ap);
315
XtAppMainLoop(gAppCont);
323
#ifdef HasSharedMemory
325
XShmDetach (XtDisplay(gTop), &shminfo);
326
shmdt (shminfo.shmaddr);
327
shmctl (shminfo.shmid, IPC_RMID, 0);