/*
 *  acm : an aerial combat simulator for X
 *  Copyright (C) 1991-1994  Riley Rainey
 *
 *  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; version 2 dated June, 1991.
 *
 *  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.
 */

#include <pm.h>
#include <X11/Xos.h>

#if defined(NETAUDIO)

static char	*files[] = {
	"crash.au",
	"gear_up.au",
	"gear_dn.au",
	"missile.au",
	"cannon.au",
	"crash.au",
	"screetch.au",
	"stall.au",
	"rwr.au"
	};
	
static char	*paths[NUM_SOUNDS];
static void	done_callback();

int
initializeAudio(c, v, display)
craft *c;
viewer *v;
char *display;
{
	int		i, n;
	AuBucketAttributes *ret_attr;
	AuDeviceAttributes *dev;
	AuStatus	status;
	char		auserver[256], *p;

/*
 *  If the X display specification has a screen field, remove it so that we
 *  can use it as an audio server name.
 */
 
	strcpy (auserver, display);
	n = strlen(auserver);	
	if (auserver[n] == '.') {
		auserver[n] = '\0';
	}

/*
 *  Lazy initialization of sound paths array
 */

	if (!paths[0]) {
		for (i=0; i<NUM_SOUNDS; ++i) {
			paths[i] = strdup(acm_find_file(files[i]));
		}
	}

/*
 *  Open the audio server and send it our sounds
 */
	
	if ((v->aserver = AuOpenServer(auserver, 0, (char *) NULL,
		0, (char *) NULL, (char **) NULL)) == NULL) {
		v->aserver = (AuServer *) NULL;
		return -1;
	}
	for (i=0; i<NUM_SOUNDS; ++i) {
		if ((v->sound[i] = AuSoundCreateBucketFromFile (v->aserver,
			paths[i], AuAccessListMask | AuAccessImportMask,
			&ret_attr, &status)) == AuNone) {
			printf ("Unable to create sound bucket: %s\n",
				paths[i]);
			AuCloseServer (v->aserver);
			v->aserver = (AuServer *) NULL;
			return -1;
		}
		v->flow[i] = 0;
	}

/*
 *  Select an output device
 */

	v->audioOutput[0] = AuNone;
	for (i=0; i<AuServerNumDevices(v->aserver); ++i) {
		dev = AuServerDevice(v->aserver, i);
		if (AuDeviceKind(dev) == AuComponentKindPhysicalOutput &&
		    AuDeviceNumTracks(dev) == 1) {
			v->audioOutput[0] = AuDeviceIdentifier(dev);
			break;
		}
	}

	return 0;
}

void
shutdownAudio(c, v)
craft *c;
viewer *v;
{
	int i;
	AuStatus status;

	if (v->aserver) {
		for (i=0; i<NUM_SOUNDS; ++i) {
			AuDestroyBucket(v->aserver, v->sound[i], &status);
		}
		AuCloseServer (v->aserver);
		v->aserver = (AuServer *) NULL;
	}
}

void
playSound (c, id)
craft *c;
int id;
{
	viewer *v;
	AuStatus	status;

	for (v=c->vl; v; v=v->next) {
		if (v->aserver) {
			AuSoundPlayFromBucket (v->aserver, v->sound[id],
				v->audioOutput[0], AuFixedPointFromSum(1,0),
				NULL, NULL, 0, &v->flow[id], (int *) NULL,
				(int *) NULL, &status);
		}
	}
}

void
playContinuousSound (c, id)
craft *c;
int id;
{
	viewer *v;
	AuStatus	status;

	for (v=c->vl; v; v=v->next) {
		if (v->aserver) {
			AuSoundPlayFromBucket (v->aserver, v->sound[id],
				v->audioOutput[0], AuFixedPointFromSum(1,0),
				done_callback, (AuPointer) v,
				10, &v->flow[id], (int *) NULL, (int *) NULL,
				&status);
		}
	}
}

void
stopSound(c, id)
craft *c;
int id;
{
	viewer *v;
	AuStatus	status;

	for (v=c->vl; v; v=v->next) {
		if (v->aserver != (AuServer *) NULL && v->flow[id] != 0) {
			AuStopFlow (v->aserver, v->flow[id], &status);
			AuDestroyFlow (v->aserver, v->flow[id], &status);
			v->flow[id] = 0;
		}
	}
}

static void
done_callback (audio, which, event, data)
AuServer	*audio;
AuEventHandlerRec *which;
AuEvent		*event;
AuPointer	data;
{
	viewer *v = (viewer *) data;
	int		mult, mon;
	AuStatus	status;
	
	printf ("event type = %d\n", event->type);
}


#else /* defined(HAS_NETAUDIO) */

int
initializeAudio(c, v)
craft *c;
viewer *v;
{
	int i;
	for (i=0; i<NUM_SOUNDS; ++i) {
		v->flow[i] = 0;
	}
	return -2;
}

void
shutdownAudio(c, v)
craft *c;
viewer *v;
{
}

void
playSound (c, id)
craft *c;
int id;
{
}

void
playContinuousSound (c, id)
craft *c;
int id;
{
}

void
stopSound(c, id)
craft *c;
int id;
{
}

#endif /* defined(HAS_NETAUDIO) */
