summaryrefslogtreecommitdiffstats
path: root/mpeglib/lib/decoder/tplayPlugin.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'mpeglib/lib/decoder/tplayPlugin.cpp')
-rw-r--r--mpeglib/lib/decoder/tplayPlugin.cpp264
1 files changed, 264 insertions, 0 deletions
diff --git a/mpeglib/lib/decoder/tplayPlugin.cpp b/mpeglib/lib/decoder/tplayPlugin.cpp
new file mode 100644
index 00000000..01c44cbc
--- /dev/null
+++ b/mpeglib/lib/decoder/tplayPlugin.cpp
@@ -0,0 +1,264 @@
+/*
+ tplay player plugin
+ Copyright (C) 1999 Martin Vogt
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU Library General Public License as published by
+ the Free Software Foundation.
+
+ For more information look at the file COPYRIGHT in this package
+
+ */
+
+
+#include "tplayPlugin.h"
+
+#include "../tplay/tplayfunctions.h"
+
+#include <iostream>
+
+using namespace std;
+
+TplayPlugin::TplayPlugin() {
+ info=new info_struct();
+
+ info->progname = NULL;
+ info->loop = FALSE;
+ info->in_seconds = FALSE;
+ info->speed = DEFAULT_SPEED;
+ info->bits = DEFAULT_BITS;
+ info->channels = DEFAULT_CHANNELS;
+ info->buffer_size = BUFFER_SIZE;
+ info->show_usage = FALSE;
+ info->swap = FALSE;
+ info->forceraw = FALSE;
+ info->force = FALSE;
+ info->device = NULL;
+ info->verbose = FALSE;
+ info->optind = 0;
+ info->buffer = NULL;
+ info->firstblock = NULL;
+ info->number_of_blocks = 0;
+ info->readblock = 0;
+ info->writeblock = 0;
+ info->readcount = 0;
+ info->writecount = 0;
+ info->alldone = FALSE;
+ info->overflow = FALSE;
+ info->underflow = FALSE;
+ info->audioset = FALSE;
+ info->headerskip = 0;
+ info->blocksize = 4096;
+ info->bytes_on_last_block = 0;
+
+ startStamp=new TimeStamp();
+ endStamp=new TimeStamp();
+}
+
+
+TplayPlugin::~TplayPlugin() {
+ delete startStamp;
+ delete endStamp;
+ delete info;
+}
+
+
+
+void TplayPlugin::decoder_loop() {
+ int bytesread, count, stereo;
+ char *p, *bufferp;
+
+ if (input == NULL) {
+ cout << "TplayPlugin::decoder_loop input is NULL"<<endl;
+ exit(0);
+ }
+ if (output == NULL) {
+ cout << "TplayPlugin::decoder_loop output is NULL"<<endl;
+ exit(0);
+ }
+
+ TimeStamp* stamp;
+ long pos;
+
+ info->buffer = (char*) malloc(info->buffer_size * sizeof(char));
+
+ while(runCheck()) {
+ switch(streamState) {
+ case _STREAM_STATE_FIRST_INIT : {
+ read_header();
+
+ if (info->channels == 1)
+ stereo = FALSE;
+ else
+ stereo = TRUE;
+
+ info->number_of_blocks = 0;
+ bufferp = info->buffer;
+ pluginInfo->setLength(getTotalLength());
+ output->writeInfo(pluginInfo);
+ lhasLength=true;
+
+ setStreamState(_STREAM_STATE_INIT);
+ break;
+ }
+ case _STREAM_STATE_INIT :
+ setStreamState(_STREAM_STATE_PLAY);
+ cout << "audioSetup call"<<endl;
+ output->audioOpen();
+ output->audioSetup(info->speed, stereo, 1, 0, info->bits);
+ break;
+ case _STREAM_STATE_PLAY :
+ bytesread = 0;
+ count = 0;
+ p = bufferp;
+ while ((bytesread < info->blocksize) && (count != -1) &&
+ ((count = input->read(p,info->blocksize-bytesread))!=0)){
+ p += count;
+ bytesread += count;
+ }
+ if (info->swap) {
+ swap_block(bufferp, bytesread);
+ }
+
+ if (bytesread > 0) {
+ pos=input->getBytePosition();
+ stamp=input->getTimeStamp(pos-bytesread);
+ output->audioPlay(stamp,endStamp,(char *) bufferp, bytesread);
+ }
+
+ if (bytesread < info->blocksize) {
+ info->alldone = TRUE;
+
+ }
+ break;
+ case _STREAM_STATE_WAIT_FOR_END:
+ // exit while loop
+ lDecoderLoop=false;
+ break;
+ default:
+ cout << "unknown stream state:"<<streamState<<endl;
+ }
+ }
+ cout << "tplay exit"<<endl;
+ free(info->buffer);
+ info->buffer = NULL;
+ output->audioFlush();
+}
+
+
+int TplayPlugin::seek_impl(int second) {
+ int bytes_per_second;
+ int seconds;
+ int back;
+
+
+ bytes_per_second = info->speed * info->channels * (info->bits / 8);
+
+
+
+ seconds = bytes_per_second * second;
+ back=input->seek(seconds);
+
+ return back;
+}
+
+
+void TplayPlugin::config(const char* key,const char* value,void* user_data) {
+ DecoderPlugin::config(key,value,user_data);
+}
+
+
+void TplayPlugin::swap_block(char * buffer, int blocksize) {
+ register int i;
+ char c, *p;
+
+ p = buffer;
+ for (i = 0; i < (blocksize / 2); i++) {
+ c = *p;
+ *p = *(p + 1);
+ *++p = c;
+ p++;
+ }
+}
+
+
+void TplayPlugin::read_header() {
+ int bytesread, count;
+ char *p, *bufferp;
+
+ info->firstblock = (char*) malloc(info->blocksize * sizeof(char));
+ bufferp = info->firstblock;
+ if (!info->forceraw) {
+ bytesread = 0;
+ count = 0;
+ p = bufferp;
+ while ((bytesread < info->blocksize) && (count != -1) &&
+ ((count=input->read(p,info->blocksize-bytesread)) != 0)){
+ p += count;
+ bytesread += count;
+ }
+
+ if (bytesread < SUN_HDRSIZE)
+ cout << "Sample size is too small"<<endl;
+
+ if (read_au(info,info->firstblock) && read_wav(info,info->firstblock)) {
+ if (info->verbose)
+ printf("Playing raw data: %ld samples/s, %d bits, %d channels.\n",
+ info->speed, info->bits, info->channels);
+ }
+
+ if (info->swap)
+ swap_block(bufferp, bytesread);
+
+ if (bytesread < info->blocksize) {
+ info->alldone = TRUE;
+ info->bytes_on_last_block = bytesread;
+ return;
+ }
+
+ if (info->headerskip) {
+ count = 0;
+ bytesread = info->blocksize - info->headerskip;
+ p = info->firstblock + (info->blocksize - info->headerskip);
+ while ((bytesread < info->blocksize) && (count != -1) &&
+ ((count = input->read(p,info->blocksize - bytesread)) != 0)) {
+ p += count;
+ bytesread += count;
+ }
+ }
+
+ info->writeblock++;
+ info->writecount++;
+ }
+ else {
+ if (info->verbose)
+ printf("Playing raw data: %ld samples/s, %d bits, %d channels\n",
+ info->speed, info->bits, info->channels);
+ }
+}
+
+/**
+ Nobody is perfect I'm too tired to fix this race
+*/
+
+int TplayPlugin::getTotalLength() {
+ float wavfilesize = input->getByteLength();
+ int back=0;
+
+
+ float frequence=info->speed;
+
+ int bits=info->bits;
+
+
+ if (bits == 16) {
+ wavfilesize=wavfilesize/2;
+ }
+ if (info->channels==2) {
+ wavfilesize=wavfilesize/2;
+ }
+ if (frequence != 0) {
+ back=(int)(wavfilesize/frequence);
+ }
+ return back;
+}