From a82cd9ef156d844e96d481506f5f4bffe922a2e0 Mon Sep 17 00:00:00 2001 From: Chris Tallon Date: Sun, 28 Oct 2007 23:59:05 +0000 Subject: [PATCH] 0.2.7 readiness patches for Windows --- GNUmakefile | 2 +- abstractoption.cc | 35 ++++ abstractoption.h | 37 ++++ afeed.cc | 6 +- audio.h | 3 +- audioplayer.cc | 22 +- audiowin.cc | 439 +++++++++++++++++++++++++++++++++++++++- audiowin.h | 33 ++- boxx.cc | 19 ++ boxx.h | 11 + colour.cc | 1 + command.cc | 22 +- demuxeraudio.cc | 36 +++- draintarget.h | 1 + dssourcepin.cc | 160 ++++++++++++++- dssourcepin.h | 4 +- media.cc | 6 +- message.h | 1 + objects.mk | 2 +- remote.cc | 39 +++- remote.h | 9 +- stream.cc | 24 ++- surface.h | 5 + surfacewin.cc | 113 ++++++++++- surfacewin.h | 8 +- vaudioplayer.cc | 21 +- video.h | 3 +- videowin.cc | 457 ++++++++++++++++++++++++++++++++---------- videowin.h | 20 +- vmedialist.cc | 5 +- vompwin.rc | 7 +- vopts.cc | 52 ++++- vopts.h | 3 +- vpicture.cc | 12 +- vpicturebanner.cc | 3 +- vtimeredit.cc | 20 +- vvideolive.cc | 19 +- vvideorec.cc | 19 +- wbutton.cc | 12 +- winmain.cc | 9 + wjpeg.cc | 93 ++++++++- wjpeg.h | 37 +++- wol.cc | 68 ++++++- woptionbox.cc | 18 +- woptionpane.cc | 43 ++++ woptionpane.h | 3 + wremoteconfig.cc | 21 ++ wremoteconfig.h | 3 + wsymbol.cc | 10 + wsymbol.h | 2 + wtabbar.cc | 55 +++++ wtabbar.h | 2 + wwinaudiofilter.cc | 238 ++++++++++++++++++++++ wwinaudiofilter.h | 56 ++++++ wwinmp3audiofilter.cc | 249 +++++++++++++++++++++++ wwinmp3audiofilter.h | 54 +++++ wwinvideofilter.cc | 232 +++++++++++++++++++++ wwinvideofilter.h | 55 +++++ 58 files changed, 2669 insertions(+), 270 deletions(-) create mode 100644 abstractoption.cc create mode 100644 abstractoption.h create mode 100644 wwinaudiofilter.cc create mode 100644 wwinaudiofilter.h create mode 100644 wwinmp3audiofilter.cc create mode 100644 wwinmp3audiofilter.h create mode 100644 wwinvideofilter.cc create mode 100644 wwinvideofilter.h diff --git a/GNUmakefile b/GNUmakefile index faa83f3..94b18fe 100644 --- a/GNUmakefile +++ b/GNUmakefile @@ -6,7 +6,7 @@ CXX=$(CROSS)g++ LD=$(CROSS)g++ INCLUDES = -I../jpeg/jpeg-6b -CXXFLAGS_DEV = -g -O0 -Wall -Wshadow -DDEV -D_GNU_SOURCE $(INCLUDES) +CXXFLAGS_DEV = -g -O0 -Wall -Wshadow -Werror -DDEV -D_GNU_SOURCE $(INCLUDES) CXXFLAGS_REL = -O3 -Wall -Wshadow -Werror -D_GNU_SOURCE $(INCLUDES) LDFLAGS = -Wall -static diff --git a/abstractoption.cc b/abstractoption.cc new file mode 100644 index 0000000..e995018 --- /dev/null +++ b/abstractoption.cc @@ -0,0 +1,35 @@ +/* + Copyright 2007 Chris Tallon,Marten Richter + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ +#include "abstractoption.h" + +bool AbstractOption::loadOptionsfromServer(VDR* vdr) +{ + return true; +} + +bool AbstractOption::saveOptionstoServer() +{ + return true; +} + +bool AbstractOption::addOptionPagesToWTB(WTabBar *wtb) +{ + return true; +} diff --git a/abstractoption.h b/abstractoption.h new file mode 100644 index 0000000..edf6321 --- /dev/null +++ b/abstractoption.h @@ -0,0 +1,37 @@ +/* + Copyright 2007 Chris Tallon, Marten Richter + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef ABSTRACT_OPTION_H +#define ABSTRACT_OPTION_H + +class WTabBar; +class VDR; + +class AbstractOption +{ + public: + virtual bool loadOptionsfromServer(VDR* vdr); + virtual bool saveOptionstoServer(); + virtual bool addOptionPagesToWTB(WTabBar *wtb); + +}; + +#endif + diff --git a/afeed.cc b/afeed.cc index e942d24..5b8dce9 100644 --- a/afeed.cc +++ b/afeed.cc @@ -82,13 +82,15 @@ void AFeed::threadMethod() else { // Log::getInstance()->log("AFeed", Log::DEBUG, "No data delay"); - MILLISLEEP(100); + //MILLISLEEP(100); + MILLISLEEP(20); //Performance Issue Marten } } else { Demuxer::getInstance()->flushAudio(); - MILLISLEEP(100); + //MILLISLEEP(100); + MILLISLEEP(20); //Performance Issue } } } diff --git a/audio.h b/audio.h index 3830bf8..de88286 100644 --- a/audio.h +++ b/audio.h @@ -24,6 +24,7 @@ #include #include "defines.h" #include "draintarget.h" +#include "abstractoption.h" typedef struct { @@ -35,7 +36,7 @@ typedef struct unsigned char lfe; } audio_volume; -class Audio : public DrainTarget +class Audio : public DrainTarget, public AbstractOption { public: Audio(); diff --git a/audioplayer.cc b/audioplayer.cc index 5dd2c65..627fd8d 100644 --- a/audioplayer.cc +++ b/audioplayer.cc @@ -507,13 +507,19 @@ UCHAR AudioPlayer::checkState() void AudioPlayer::waitTimed(int ms) { threadLock(); - struct timeval ct; - gettimeofday(&ct,NULL); struct timespec nt; int sec=ms/1000; int us=1000*(ms - 1000*sec); +#ifndef WIN32 + struct timeval ct; + gettimeofday(&ct,NULL); nt.tv_sec=ct.tv_sec+sec; nt.tv_nsec=1000*us+1000*ct.tv_usec; +#else + DWORD ct=timeGetTime(); + nt.tv_sec=ct/1000+sec; + nt.tv_nsec=1000*us+1000*ct*1000; +#endif threadWaitForSignalTimed(&nt); threadUnlock(); } @@ -671,23 +677,25 @@ char * AudioPlayer::getID3Info() { if (info && info->avrBitrate != info->bitRate) bitrateType='V'; rt=new char[len]; if (!tag && info) { - snprintf(rt,len-1,"%s: %s/L%d %cBR,SR=%dk,%s\n",tr("MpegInfo"), + SNPRINTF(rt,len-1,"%s: %s/L%d %cBR,SR=%dk,%s\n",tr("MpegInfo"), info->mpegVersion,info->mpegLayer,bitrateType,info->sampleRate/1000, info->info); } else if (tag && info){ - char tmp[taglen+1]; - snprintf(rt,len-1,"%s\n" + char *tmp=new char[taglen+1]; + SNPRINTF(rt,len-1,"%s\n" "%s: %s/L%d %cBR,SR=%dk,%s\n", tag->toString(tmp,taglen,false), tr("MpegInfo"), info->mpegVersion,info->mpegLayer,bitrateType,info->sampleRate/1000, info->info); + delete [] tmp; } else if (tag && !info){ - char tmp[taglen+1]; - snprintf(rt,len-1,"%s\n", + char *tmp=new char[taglen+1]; + SNPRINTF(rt,len-1,"%s\n", tag->toString(tmp,taglen,false)); + delete [] tmp; } rt[len-1]=0; } diff --git a/audiowin.cc b/audiowin.cc index 1dcaeaa..13f7130 100644 --- a/audiowin.cc +++ b/audiowin.cc @@ -20,6 +20,11 @@ #include "audiowin.h" #include "videowin.h" +#include "vdr.h" +#include "wtabbar.h" +#include "wwinaudiofilter.h" +#include "wwinmp3audiofilter.h" +#include "i18n.h" @@ -30,19 +35,37 @@ AudioWin::AudioWin() firstsynched=false; winvolume=0; volume=20; - - +audiofilterselected=-1; + mp3audiofilterselected=-1; + aud_type=Audio::MPEG2_PES; } AudioWin::~AudioWin() { + int i; + for (i=0;isetAudioStreamType(type); + aud_type=type; if (!initted) return 0; return 1; } @@ -149,6 +174,181 @@ void AudioWin::PrepareMediaSample(const MediaPacketList& mplist,UINT samplepos) mediapacket = mplist.front(); } +void AudioWin::initFilterDatabase() +{ + /* This method should determine all availiable DirectShow Filters */ + IFilterMapper2* filtmap=NULL; + HRESULT result; + result = CoCreateInstance(CLSID_FilterMapper2,NULL,CLSCTX_INPROC, + IID_IFilterMapper2,(void**)&filtmap); + if (result != S_OK) + { + Log::getInstance()->log("AudioWin", Log::ERR , "Unable to create FilterMapper!"); + return; + } + /* Wishlist, what Mediatypes do we want */ + GUID mtypesin[]={MEDIATYPE_Audio,MEDIASUBTYPE_MPEG2_AUDIO, + /*MEDIATYPE_Audio,MEDIASUBTYPE_MPEG1Payload,*/ + MEDIATYPE_Audio,MEDIASUBTYPE_DOLBY_AC3, + MEDIATYPE_Audio, MEDIASUBTYPE_DOLBY_AC3_SPDIF}; + IEnumMoniker *myenum; + result = filtmap->EnumMatchingFilters(&myenum,0,TRUE,MERIT_DO_NOT_USE+1, + TRUE,3,mtypesin,NULL,NULL,FALSE,TRUE,0,NULL,NULL,NULL); + if (result != S_OK) + { + filtmap->Release(); + Log::getInstance()->log("AudioWin", Log::ERR , "Unable to enum Filters!"); + return; + } + ULONG gethowmany; + IMoniker * moni; + while(myenum->Next(1,&moni,&gethowmany)==S_OK) + { + AudioFilterDesc desc; + ZeroMemory(&desc,sizeof(desc)); + + LPOLESTR string; + moni->GetDisplayName(0,0,&string); + desc.displayname=new char[wcslen(string)+1]; + wcstombs(desc.displayname,string,wcslen(string)+1); + CoTaskMemFree(string); + IPropertyBag *bag; + if (moni->BindToStorage(0,0,IID_IPropertyBag,(void**)&bag) == S_OK) + { + VARIANT vari; + VariantInit(&vari); + result = bag->Read(L"FriendlyName",&vari,NULL); + if (result == S_OK) + { + desc.friendlyname=new char[wcslen(vari.bstrVal)+1]; + wcstombs(desc.friendlyname,vari.bstrVal,wcslen(vari.bstrVal)+1); + } + VariantClear(&vari); + bag->Release(); + + } + + + audiofilterlist.push_back(desc); + + + + moni->Release(); + // bctx->Release(); + } + int i; + audiofilterselected=-1; + myenum->Release(); + filtmap->Release(); +} + +void AudioWin::initMp3FilterDatabase() +{ + /* This method should determine all availiable DirectShow Filters */ + IFilterMapper2* filtmap=NULL; + HRESULT result; + result = CoCreateInstance(CLSID_FilterMapper2,NULL,CLSCTX_INPROC, + IID_IFilterMapper2,(void**)&filtmap); + if (result != S_OK) + { + Log::getInstance()->log("AudioWin", Log::ERR , "Unable to create FilterMapper!"); + return; + } + /* Wishlist, what Mediatypes do we want */ + GUID mtypesin[]={MEDIATYPE_Audio,MEDIATYPE_WaveFmt_Mpeg1Layer3, + MEDIATYPE_Audio,MEDIASUBTYPE_MPEG2_AUDIO}; + IEnumMoniker *myenum; + result = filtmap->EnumMatchingFilters(&myenum,0,TRUE,MERIT_DO_NOT_USE+1, + TRUE,3,mtypesin,NULL,NULL,FALSE,TRUE,0,NULL,NULL,NULL); + if (result != S_OK) + { + filtmap->Release(); + Log::getInstance()->log("AudioWin", Log::ERR , "Unable to enum Filters!"); + return; + } + ULONG gethowmany; + IMoniker * moni; + while(myenum->Next(1,&moni,&gethowmany)==S_OK) + { + AudioFilterDesc desc; + ZeroMemory(&desc,sizeof(desc)); + + LPOLESTR string; + moni->GetDisplayName(0,0,&string); + desc.displayname=new char[wcslen(string)+1]; + wcstombs(desc.displayname,string,wcslen(string)+1); + CoTaskMemFree(string); + IPropertyBag *bag; + if (moni->BindToStorage(0,0,IID_IPropertyBag,(void**)&bag) == S_OK) + { + VARIANT vari; + VariantInit(&vari); + result = bag->Read(L"FriendlyName",&vari,NULL); + if (result == S_OK) + { + desc.friendlyname=new char[wcslen(vari.bstrVal)+1]; + wcstombs(desc.friendlyname,vari.bstrVal,wcslen(vari.bstrVal)+1); + } + VariantClear(&vari); + bag->Release(); + + } + + + mp3audiofilterlist.push_back(desc); + + + + moni->Release(); + // bctx->Release(); + } + int i; + mp3audiofilterselected=-1; + myenum->Release(); + filtmap->Release(); +} + +bool AudioWin::loadOptionsfromServer(VDR* vdr) +{ + char *name=vdr->configLoad("DirectShow","AudioFilter"); + + if (name != NULL) + { + for (int i = 0;i configLoad("DirectShow","Mp3AudioFilter"); + + if (name != NULL) + { + for (int i = 0;i configSave("DirectShow", + "AudioFilter",audiofilterlist[audiofilterselected].displayname); + VDR::getInstance()->configSave("DirectShow", + "Mp3AudioFilter",mp3audiofilterlist[mp3audiofilterselected].displayname); + return true; +} + UINT AudioWin::DeliverMediaSample(const UCHAR* buffer, UINT *samplepos) { DeliverMediaPacket(mediapacket, buffer, samplepos); @@ -192,24 +392,18 @@ UINT AudioWin::DeliverMediaPacket(MediaPacket packet, /*Inspect PES-Header */ /* UINT header_length=buffer[(packet.pos_buffer+8)%bufferlength]+8/*is this right*; */ - if (*samplepos==0) {//stripheader - headerstrip=buffer[packet.pos_buffer+8]+9/*is this right*/; + if (*samplepos==0 && packet.type!=MPTYPE_MPEG_AUDIO_LAYER3) {//stripheader + headerstrip=buffer[packet.pos_buffer+8]+9; if (packet.type == MPTYPE_AC3) headerstrip+=4; //skip ac3 bytes *samplepos+=headerstrip; if ( packet.synched ) { vw->DeliverAudioMediaSample();//write out old data - /* if (packet.presentation_time<0) { //Preroll? - *samplepos=packet.length;//if we have not processed at least one - return packet.length;//synched packet ignore it! - }*/ - reftime1=packet.presentation_time; reftime2=reftime1+1; firstsynched=true; } else { if (!firstsynched) {// *samplepos=packet.length;//if we have not processed at least one - return packet.length;//synched packet ignore it! } } @@ -278,6 +472,231 @@ UINT AudioWin::DeliverMediaPacket(MediaPacket packet, } +int AudioWin::dsInitAudioFilter(IGraphBuilder* dsgraphbuilder) +{ + HRESULT hres; + IFilterGraph2*fg2=NULL; + VideoWin *vw=(VideoWin*)Video::getInstance(); + if (dsgraphbuilder->QueryInterface(IID_IFilterGraph2,(void**)&fg2)!= S_OK) + { + Log::getInstance()->log("AudiooWin", Log::WARN , "Failed querying for FilterGraph2 Interface!"); + return 0; + } + IBaseFilter*audiofilter; + if (aud_type!=Audio::MP3) { + audiofilter = getAudioFilter(); + } else { + audiofilter = getMp3AudioFilter(); + } + if (hres=dsgraphbuilder->AddFilter(audiofilter,NULL) != S_OK) + { + Log::getInstance()->log("AudioWin", Log::WARN , "Failed adding Video Filter!"); + return 0; + } + IEnumPins *pinenum=NULL; + bool error=false; + if (audiofilter->EnumPins(&pinenum) == S_OK) + { + IPin *current=NULL; + ULONG fetch=0; + bool firststep=false; + while (pinenum->Next(1,¤t,&fetch)==S_OK) + { + PIN_DIRECTION dir; + if (current->QueryDirection(&dir)==S_OK) + { + if (dir == PINDIR_INPUT) + { + if (vw->getSourceFilter()->GetAudioPin()->Connect(current,NULL)==S_OK) + { + current->Release(); + firststep=true; + break; + } + } + } + current->Release(); + } + if (firststep==false) + { + Log::getInstance()->log("AudioWin", Log::WARN , "Audio Filter has no suitable input!"); + audiofilter->Release(); + return 0; + } + bool secondstep=false; + pinenum->Reset(); + while (pinenum->Next(1,¤t,&fetch)==S_OK) + { + PIN_DIRECTION dir; + if (current->QueryDirection(&dir)==S_OK) + { + if (dir == PINDIR_OUTPUT) + { + + if (fg2->RenderEx((IPin*)current/*video*/, + 0,NULL) ==S_OK) + { + current->Release(); + secondstep=true; + break; + } + } + } + current->Release(); + } + if (secondstep==false) + { + Log::getInstance()->log("AudioWin", Log::WARN , "Audio Filter has no suitable output!"); + audiofilter->Release(); + + return 0; + } + + audiofilter->Release(); + pinenum->Release(); + + } + + + + fg2->Release(); + return 1; +} + + +IBaseFilter *AudioWin::getAudioFilter() +{ + IBaseFilter *curfilter= NULL; + bool notset=false; + if (audiofilterselected == -1) + { + int i; + for (i = 0;i BindToObject(0,0,IID_IBaseFilter,(void**)&curfilter) == S_OK) + { + if (curfilter != NULL && notset) + { + VDR *vdr=VDR::getInstance(); + if (vdr != NULL) + { + vdr->configSave("DirectShow","AudioFilter", + audiofilterlist[audiofilterselected].displayname); + } + } + + moni->Release(); + delete [] name; + bindctx->Release(); + return curfilter; + } + bindctx->Release(); + delete [] name; + return NULL; + } + return NULL; +} + +IBaseFilter *AudioWin::getMp3AudioFilter() +{ + IBaseFilter *curfilter= NULL; + bool notset=false; + if (mp3audiofilterselected == -1) + { + int i; + for (i = 0;i BindToObject(0,0,IID_IBaseFilter,(void**)&curfilter) == S_OK) + { + if (curfilter != NULL && notset) + { + VDR *vdr=VDR::getInstance(); + if (vdr != NULL) + { + vdr->configSave("DirectShow","Mp3AudioFilter", + mp3audiofilterlist[mp3audiofilterselected].displayname); + } + } + + moni->Release(); + delete [] name; + bindctx->Release(); + return curfilter; + } + bindctx->Release(); + delete [] name; + return NULL; + } + return NULL; +} + + +bool AudioWin::addOptionPagesToWTB(WTabBar *wtb) +{ + Boxx *box=new WWinAudioFilter(); + wtb->addTab(tr("Audio Filter"), box); + + + box=new WWinMp3AudioFilter(); + wtb->addTab(tr("Mp3 Audio Filter"), box); + + + return true; +} + +const AudioFilterDescList *AudioWin::getAudioFilterList(int &selected) +{ + selected=audiofilterselected; + return &audiofilterlist; +} + +const AudioFilterDescList *AudioWin::getMp3AudioFilterList(int &selected) +{ + selected=mp3audiofilterselected; + return &mp3audiofilterlist; +} +bool AudioWin::selectMp3AudioFilter(int filter) +{ + mp3audiofilterselected=filter; + return true; + +} + +bool AudioWin::selectAudioFilter(int filter) +{ + audiofilterselected=filter; + return true; + +} + long long AudioWin::SetStartOffset(long long curreftime, bool *rsync){ VideoWin *vw=(VideoWin*)Video::getInstance(); return vw->SetStartAudioOffset(curreftime,rsync); diff --git a/audiowin.h b/audiowin.h index 9942124..3176236 100644 --- a/audiowin.h +++ b/audiowin.h @@ -24,6 +24,18 @@ #include "defines.h" #include "log.h" #include "audio.h" +#include +#include +#include "dssourcefilter.h" + +#include + +struct AudioFilterDesc { + char * displayname; + char * friendlyname; +}; +using namespace std; +typedef vector AudioFilterDescList; class AudioWin : public Audio { @@ -48,10 +60,21 @@ class AudioWin : public Audio int unMute(); int write(char *buf, int len); + bool loadOptionsfromServer(VDR* vdr); + bool saveOptionstoServer(); + bool addOptionPagesToWTB(WTabBar *wtb); + // Writing Data to Audiodevice virtual void PrepareMediaSample(const MediaPacketList&, UINT samplepos); virtual UINT DeliverMediaSample(const UCHAR* buffer, UINT *samplepos); UINT DeliverMediaPacket(MediaPacket packet, const UCHAR* buffer, UINT *samplepos); + + int dsInitAudioFilter(IGraphBuilder* dsgraphbuilder); + const AudioFilterDescList *getAudioFilterList(int &selected); + bool selectAudioFilter(int filter); + + const AudioFilterDescList *getMp3AudioFilterList(int &selected); + bool selectMp3AudioFilter(int filter); virtual bool supportsAc3(); private: @@ -61,8 +84,17 @@ class AudioWin : public Audio virtual void ResetTimeOffsets(); private: + IBaseFilter *getAudioFilter(); + IBaseFilter *getMp3AudioFilter(); + void initFilterDatabase(); + void initMp3FilterDatabase(); + AudioFilterDescList audiofilterlist; + AudioFilterDescList mp3audiofilterlist; + int audiofilterselected; + int mp3audiofilterselected; bool firstsynched; long winvolume; + UCHAR aud_type; #ifdef DEV int test(); #endif @@ -70,4 +102,3 @@ private: #endif - diff --git a/boxx.cc b/boxx.cc index d546633..c9fe60a 100644 --- a/boxx.cc +++ b/boxx.cc @@ -337,6 +337,25 @@ void Boxx::drawPixel(UINT x, UINT y, Colour& colour) } } +void Boxx::startFastDraw() +{ + if (parent) parent->startFastDraw(); + else + { + surface->startFastDraw(); + } +} + +void Boxx::endFastDraw() +{ + if (parent) parent->endFastDraw(); + else + { + surface->endFastDraw(); + } +} + + int Boxx::charWidth(char c) { if (parent) return parent->charWidth(c); diff --git a/boxx.h b/boxx.h index 560904c..1889519 100644 --- a/boxx.h +++ b/boxx.h @@ -52,9 +52,14 @@ class Boxx virtual void draw(); virtual int handleCommand(int); virtual void processMessage(Message*); + virtual bool mouseMove(int x, int y) {return false;}; + virtual bool mouseLBDOWN(int x, int y) {return false;}; void setBackgroundColour(Colour& colour); void setVisible(bool isVisible); + virtual void deactivateAllControls(){}; + + // Drawing functions level 1 void fillColour(Colour& colour); @@ -69,6 +74,10 @@ class Boxx void drawTextCentre(const char* text, int x, int y, Colour& colour); void drawPixel(UINT x, UINT y, Colour& colour); + /* This is for system which need a locking of the drawing surface to speed up drawing */ + void startFastDraw(); + void endFastDraw(); + int charWidth(char c); // Following 4 used by mouse stuff only, except 1 getWidth/getHeight? in orig. vtabsman @@ -82,6 +91,8 @@ class Boxx UINT getHeight(); bool getVisible(); + + void add(Boxx*); // a boxx has a set of child boxxs void remove(Boxx*); diff --git a/colour.cc b/colour.cc index 3db474e..32719f1 100644 --- a/colour.cc +++ b/colour.cc @@ -26,6 +26,7 @@ Real colours Colour Colour::BLACK(0, 0, 0); Colour Colour::RED(255, 0, 0); Colour Colour::GREEN(0, 255, 0); +Colour Colour::YELLOW(255, 255, 0); Colour Colour::VIDEOBLUE(0, 0, 150); Colour Colour::VIEWBACKGROUND(0, 0, 100); Colour Colour::TABVIEWBACKGROUND(0, 0, 120); diff --git a/command.cc b/command.cc index 0d0bf9d..3dfa445 100644 --- a/command.cc +++ b/command.cc @@ -18,7 +18,9 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +#ifndef WIN32 #include +#endif #include "command.h" @@ -28,6 +30,7 @@ #include "led.h" #include "video.h" +#include "audio.h" #include "vdr.h" #include "vvolume.h" #include "vserverselect.h" @@ -545,6 +548,7 @@ void Command::doJustConnected(VConnect* vconnect) { I18n::initialize(); Video* video = Video::getInstance(); + Audio* audio = Audio::getInstance(); boxstack->remove(vconnect); VInfo* vi = new VInfo(); @@ -728,21 +732,8 @@ void Command::doJustConnected(VConnect* vconnect) remote->setRemoteType(Remote::OLDREMOTE); } - // Set remote keys - config = vdr->configLoad("General", "Remote keys"); - if (config) - { - logger->log("Command", Log::INFO, "Config General/Remote keys load"); - remote->LoadKeysConfig(config); - delete[] config; - } - else - { - logger->log("Command", Log::INFO, "Config General/Remote keys not found"); - remote->InitHWCListwithDefaults(); - } // Get TV aspect ratio @@ -824,7 +815,10 @@ void Command::doJustConnected(VConnect* vconnect) logger->log("Command", Log::INFO, "By default, enable WOL"); Wol::getInstance()->setEnabled(true); } - + /* device dependend config */ + audio->loadOptionsfromServer(vdr); + video->loadOptionsfromServer(vdr); + remote->loadOptionsfromServer(vdr); // config done // Save power state = on diff --git a/demuxeraudio.cc b/demuxeraudio.cc index f539474..72cf3fe 100644 --- a/demuxeraudio.cc +++ b/demuxeraudio.cc @@ -804,7 +804,7 @@ int DemuxerAudio::readHeader(UCHAR * hbuf,int len,bool writeInfo) { case 2: chmodStr=tr("Dual");break; case 3: chmodStr=tr("Mono");break; } - snprintf(info->info,sizeof(info->info)-1,"%s",chmodStr); + SNPRINTF(info->info,sizeof(info->info)-1,"%s",chmodStr); } if (isStarting) avrBitrate=curBitrate; isStarting=false; @@ -841,10 +841,25 @@ bool PacketBuffer::doSkip() { // just handle the real stream without dealing with the header int PacketBuffer::putInternal(UCHAR * wbuf, int len) { + /* Important, the type passed to stream must be a mediapacket type as defined in + Draintarget.h and not the device setting of the mvp, so we have to translate it here, + in order to get it working on windows + --MR */ + UCHAR mptype=0; + switch (streamtype) { + case Audio::MPEG1_PES: //? + case Audio::MPEG2_PES: //Important, this must be a PES ! + mptype=MPTYPE_MPEG_AUDIO; break; + default: + case Audio::MP3: //this can be any Mpeg1 Audio not only layer 3 not packed into PES + mptype=MPTYPE_MPEG_AUDIO_LAYER3;break; + }; if (bufferFull()) { - if (doSkip()) return 0; +#ifndef WIN32 + if (doSkip()) return 0;//NoSkip on Windows +#endif //we are still full - so try to write - int sent=audio->put(store+bytesWritten,framelen-bytesWritten,streamtype); + int sent=audio->put(store+bytesWritten,framelen-bytesWritten,/*streamtype*/mptype); //log->log("DemuxerAudio::PacketBuffer",Log::DEBUG,"written %d bytes to stream (still full) pp=%d, framelen=%d, written=%d",sent,partPacket,framelen, bytesWritten ); if (sent < (framelen - bytesWritten)) { //packet still not written @@ -861,8 +876,10 @@ int PacketBuffer::putInternal(UCHAR * wbuf, int len) memcpy(store+partPacket,wbuf,bytesConsumed); partPacket=framelen; //log->log("DemuxerAudio::PacketBuffer",Log::DEBUG,"stored packet %ld, length %d (last %d) for stream %p",numpackets,framelen,bytesConsumed,audio ); +#ifndef WIN32 //No Skip on Windows if (doSkip()) return bytesConsumed; - int sent=audio->put(store,framelen,streamtype); +#endif + int sent=audio->put(store,framelen,mptype); bytesWritten+=sent; //log->log("DemuxerAudio::PacketBuffer",Log::DEBUG,"written %d bytes to stream",sent ); if (bytesWritten < framelen) { @@ -969,6 +986,7 @@ int DemuxerAudio::put(UCHAR* wbuf, int len) log->log("DemuxerAudio",Log::DEBUG,"garbage found at packet %ld (bytes %ld) of length %d, " "framelen set to %d (last fl=%d)", readHeaders,globalBytesWritten,garbageBytes,buffer->getFramelen(),lastFramelen); +#ifndef WIN32 //hmm - we assume that he low level driver is more intelligent //and give him the data "as is" int written=buffer->putInternal(wbuf,garbageBytes); @@ -977,6 +995,10 @@ int DemuxerAudio::put(UCHAR* wbuf, int len) if (written != garbageBytes || hdr == NULL ) { break; } +#else //DS is not intelligent + globalBytesWritten+=garbageBytes; + bytesConsumed+=garbageBytes; +#endif //OK either all the "garbage" is written or //we found the next header as expected //continue with the next package @@ -1204,12 +1226,12 @@ char * id3_tag::toString(char *b, int len, bool withTitle) const { const char * del=" - "; if (strlen(year) == 0) del=""; if (withTitle){ - const char *tt=tr("Title"); - snprintf(b,len-1,"%s: %s\n%s: %s\n%s: %s%s%s\n%s: %s", + const char *tt=tr("Title"); + SNPRINTF(b,len-1,"%s: %s\n%s: %s\n%s: %s%s%s\n%s: %s", tt,title,ta,artist,tx,year,del,album,tn,track); } else { - snprintf(b,len-1,"%s: %s\n%s: %s%s%s\n%s: %s", +SNPRINTF(b,len-1,"%s: %s\n%s: %s%s%s\n%s: %s", ta,artist,tx,year,del,album,tn,track); } b[len-1]=0; diff --git a/draintarget.h b/draintarget.h index 2e473be..5e04641 100644 --- a/draintarget.h +++ b/draintarget.h @@ -28,6 +28,7 @@ #define MPTYPE_MPEG_AUDIO 0x01 #define MPTYPE_AC3 0x02 #define MPTYPE_AC3_PRE13 0x03 //old vdr recording compatmode +#define MPTYPE_MPEG_AUDIO_LAYER3 0x04 //for media mp3 playback struct MediaPacket { diff --git a/dssourcepin.cc b/dssourcepin.cc index 49d932a..cc12ba7 100644 --- a/dssourcepin.cc +++ b/dssourcepin.cc @@ -17,11 +17,20 @@ along with VOMP; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ -#include "dssourcepin.h" + #include "dssourcefilter.h" #include #include #include "draintarget.h" +#include "demuxeraudio.h" + +EXTERN_C const GUID DECLSPEC_SELECTANY MEDIATYPE_WaveFmt_Mpeg1Layer3= +{WAVE_FORMAT_MPEGLAYER3, +0x0000, 0x0010, 0x80, 0x00, 0x00, 0xaa, 0x00, 0x38, 0x9b, 0x71}; + +#include "dssourcepin.h" + + class DsSFEnumMediaTypes: public IEnumMediaTypes { public: @@ -478,6 +487,121 @@ bool DsSourcePin::supportsAc3() { } +HRESULT DsSourcePin::GetMediaTypeMp3Audio(int iPosition, AM_MEDIA_TYPE *pmt) +{ + HRESULT hr; + switch (iPosition) + { + /* case 0: { + ZeroMemory(pmt,sizeof(*pmt)); + pmt->lSampleSize = 1; + pmt->bFixedSizeSamples = TRUE; + pmt->majortype=MEDIATYPE_Audio; + MPEG1WAVEFORMAT wfe; + ZeroMemory(&wfe,sizeof(wfe)); + wfe.wfx.cbSize=22; + wfe.wfx.nSamplesPerSec=48000; + wfe.wfx.nChannels=2; + wfe.wfx.nAvgBytesPerSec=32000; + wfe.wfx.nBlockAlign=768; + wfe.wfx.wFormatTag=WAVE_FORMAT_MPEG; + wfe.wfx.wBitsPerSample=0; + wfe.fwHeadLayer=2; + wfe.dwHeadBitrate=256000; + wfe.fwHeadMode=ACM_MPEG_STEREO; + wfe.fwHeadModeExt=1; + wfe.wHeadEmphasis=1; + wfe.fwHeadFlags=ACM_MPEG_ID_MPEG1 |ACM_MPEG_ORIGINALHOME | ACM_MPEG_PROTECTIONBIT; + pmt->subtype=MEDIASUBTYPE_MPEG2_AUDIO; + pmt->formattype=FORMAT_WaveFormatEx; + pmt->cbFormat=sizeof(wfe); + pmt->pbFormat=(BYTE*)CoTaskMemAlloc(sizeof(wfe)); + memcpy(pmt->pbFormat,&wfe,sizeof(wfe)); + pmt->lSampleSize=0; + hr=S_OK; + } break;*/ + /* case 0: //MPEG2_AUDIO + { + ZeroMemory(pmt,sizeof(*pmt)); + pmt->lSampleSize = 1; + pmt->bFixedSizeSamples = TRUE; + pmt->majortype = MEDIATYPE_Audio; + WAVEFORMATEX wfe; + ZeroMemory(&wfe,sizeof(wfe)); + wfe.cbSize = 22; + wfe.nSamplesPerSec = 48000; + wfe.nChannels = 2; + wfe.nAvgBytesPerSec = 0;//32000; + wfe.nBlockAlign = 0;//768; + wfe.wFormatTag = WAVE_FORMAT_UNKNOWN; + wfe.wBitsPerSample = 0; + pmt->subtype = MEDIASUBTYPE_MPEG2_AUDIO; + pmt->formattype = FORMAT_WaveFormatEx; + pmt->cbFormat = sizeof(wfe); + pmt->pbFormat = (BYTE*)CoTaskMemAlloc(sizeof(wfe)); + memcpy(pmt->pbFormat,&wfe,sizeof(wfe)); + pmt->lSampleSize=0; + hr=S_OK; + } break;*/ + case 0: {//Mpeg1 + ZeroMemory(pmt,sizeof(*pmt)); + pmt->lSampleSize = 1; + pmt->bFixedSizeSamples = TRUE; + pmt->majortype = MEDIATYPE_Audio; + MPEGLAYER3WAVEFORMAT wfe; + ZeroMemory(&wfe,sizeof(wfe)); + wfe.wfx.cbSize = MPEGLAYER3_WFX_EXTRA_BYTES; + wfe.wfx.nSamplesPerSec =44100; //For the Fraunhofer decoder + wfe.wfx.nChannels = 2; + //wfe.wfx.nAvgBytesPerSec = 32000; + wfe.wfx.nAvgBytesPerSec = 0;//128*(1024/8); + wfe.wfx.nBlockAlign = 1; + wfe.wfx.wFormatTag = WAVE_FORMAT_MPEGLAYER3; + wfe.wfx.wBitsPerSample = 0; + wfe.wID=MPEGLAYER3_ID_MPEG; + wfe.nCodecDelay=1393; + wfe.nBlockSize=522; + wfe.nFramesPerBlock=1; + pmt->subtype=MEDIATYPE_WaveFmt_Mpeg1Layer3; + + + pmt->formattype=FORMAT_WaveFormatEx; + pmt->cbFormat=sizeof(wfe); + pmt->pbFormat=(BYTE*)CoTaskMemAlloc(sizeof(wfe)); + memcpy(pmt->pbFormat,&wfe,sizeof(wfe)); + pmt->lSampleSize=0; + hr=S_OK; + } break; + case 1: //MPEG2_AUDIO, this more less not right but works on some filters + { + ZeroMemory(pmt,sizeof(*pmt)); + pmt->lSampleSize = 1; + pmt->bFixedSizeSamples = TRUE; + pmt->majortype = MEDIATYPE_Audio; + WAVEFORMATEX wfe; + ZeroMemory(&wfe,sizeof(wfe)); + wfe.cbSize = 22; + wfe.nSamplesPerSec = 48000; + wfe.nChannels = 2; + wfe.nAvgBytesPerSec = 0;//32000; + wfe.nBlockAlign = 0;//768; + wfe.wFormatTag = WAVE_FORMAT_UNKNOWN; + wfe.wBitsPerSample = 0; + pmt->subtype = MEDIASUBTYPE_MPEG2_AUDIO; + pmt->formattype = FORMAT_WaveFormatEx; + pmt->cbFormat = sizeof(wfe); + pmt->pbFormat = (BYTE*)CoTaskMemAlloc(sizeof(wfe)); + memcpy(pmt->pbFormat,&wfe,sizeof(wfe)); + pmt->lSampleSize=0; + hr=S_OK; + } break; + default: { + hr=VFW_S_NO_MORE_ITEMS; + }break; + }; + return hr ; +} + HRESULT DsSourcePin::GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt) { @@ -512,7 +636,7 @@ HRESULT DsSourcePin::GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt) pmt->lSampleSize=0; hr=S_OK; } break;*/ - case 0: + case 0: //MPEG2_AUDIO { ZeroMemory(pmt,sizeof(*pmt)); pmt->lSampleSize = 1; @@ -523,8 +647,8 @@ HRESULT DsSourcePin::GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt) wfe.cbSize = 22; wfe.nSamplesPerSec = 48000; wfe.nChannels = 2; - wfe.nAvgBytesPerSec = 32000; - wfe.nBlockAlign = 768; + wfe.nAvgBytesPerSec = 0;//32000; + wfe.nBlockAlign = 0;//768; wfe.wFormatTag = WAVE_FORMAT_UNKNOWN; wfe.wBitsPerSample = 0; pmt->subtype = MEDIASUBTYPE_MPEG2_AUDIO; @@ -535,7 +659,7 @@ HRESULT DsSourcePin::GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt) pmt->lSampleSize=0; hr=S_OK; } break; - case 1: { + case 1: {//Mpeg1 ZeroMemory(pmt,sizeof(*pmt)); pmt->lSampleSize = 1; pmt->bFixedSizeSamples = TRUE; @@ -545,8 +669,9 @@ HRESULT DsSourcePin::GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt) wfe.wfx.cbSize = 22; wfe.wfx.nSamplesPerSec = 48000; wfe.wfx.nChannels = 2; - wfe.wfx.nAvgBytesPerSec = 32000; - wfe.wfx.nBlockAlign = 768; + //wfe.wfx.nAvgBytesPerSec = 32000; + wfe.wfx.nAvgBytesPerSec = 0; + //wfe.wfx.nBlockAlign = 768; wfe.wfx.wFormatTag = WAVE_FORMAT_UNKNOWN; wfe.wfx.wBitsPerSample = 0; /* wfe.fwHeadLayer=2; @@ -639,6 +764,10 @@ HRESULT DsSourcePin::GetMediaType(int iPosition, AM_MEDIA_TYPE *pmt) { switch (pinmode){ + case MPTYPE_MPEG_AUDIO_LAYER3: + return GetMediaTypeMp3Audio(iPosition,pmt); + break; + case MPTYPE_MPEG_AUDIO: return GetMediaTypeMpegAudio(iPosition,pmt); break; @@ -679,6 +808,22 @@ HRESULT DsSourcePin::CheckMediaType(const AM_MEDIA_TYPE *pmt) HRESULT res=S_FALSE; bool subtype=false; switch (pinmode) { + case MPTYPE_MPEG_AUDIO_LAYER3: + // subtype=(pmt->subtype==(MEDIASUBTYPE_MPEG2_AUDIO)); + // subtype=(pmt->subtype==MEDIASUBTYPE_MPEG1Payload) || subtype; + + subtype=(pmt->subtype==MEDIATYPE_WaveFmt_Mpeg1Layer3); + subtype=subtype || (pmt->subtype==MEDIASUBTYPE_MPEG2_AUDIO); + if (pmt->majortype==MEDIATYPE_Audio && subtype) + { + res = S_OK ; + } + else + { + res = S_FALSE ; + } + break; + case MPTYPE_MPEG_AUDIO: subtype=(pmt->subtype==(MEDIASUBTYPE_MPEG2_AUDIO)); subtype=(pmt->subtype==MEDIASUBTYPE_MPEG1Payload) || subtype; @@ -754,4 +899,3 @@ HRESULT DsSourcePin::DecideBufferSize(IMemAllocator *pa,ALLOCATOR_PROPERTIES *al return S_OK; } - diff --git a/dssourcepin.h b/dssourcepin.h index d6af62f..fa432af 100644 --- a/dssourcepin.h +++ b/dssourcepin.h @@ -25,6 +25,8 @@ #include +EXTERN_C const GUID FAR MEDIATYPE_WaveFmt_Mpeg1Layer3; + class DsSourceFilter; @@ -75,6 +77,7 @@ public: protected: virtual HRESULT CheckMediaType(const AM_MEDIA_TYPE *pmt); HRESULT GetMediaTypeMpegAudio(int iPosition, AM_MEDIA_TYPE *pmt); + HRESULT GetMediaTypeMp3Audio(int iPosition, AM_MEDIA_TYPE *pmt); HRESULT GetMediaTypeAc3(int iPosition, AM_MEDIA_TYPE *pmt); HRESULT GetMediaTypeMpegVideo(int iPosition, AM_MEDIA_TYPE *pmt); @@ -94,4 +97,3 @@ protected: #endif - diff --git a/media.cc b/media.cc index 25b1ac5..b966bc3 100644 --- a/media.cc +++ b/media.cc @@ -105,7 +105,9 @@ char * Media::getTimeString(char * buffer) const { if (! buffer) buffer=new char[TIMEBUFLEN]; struct tm ltime; time_t recStartTime = (time_t)getTime(); - struct tm *btime = localtime_r(&recStartTime,<ime); + struct tm *btime = localtime(&recStartTime); + memcpy(<ime,btime, sizeof(struct tm)); + btime=<ime; if (btime && recStartTime != 0) { #ifndef _MSC_VER strftime(buffer,TIMEBUFLEN, "%0g/%0m/%0d %0H:%0M ", btime); @@ -114,7 +116,7 @@ char * Media::getTimeString(char * buffer) const { #endif } else { - snprintf(buffer,TIMEBUFLEN,"00/00/00 00:00 "); + SNPRINTF(buffer,TIMEBUFLEN,"00/00/00 00:00 "); } return buffer; } diff --git a/message.h b/message.h index d08fa8c..c9d1ed1 100644 --- a/message.h +++ b/message.h @@ -73,6 +73,7 @@ class Message const static ULONG LAST_VIEW_CLOSE = 28; const static ULONG CHANGED_REMOTECONTROL = 29; const static ULONG DELETE_SELECTED_TIMER = 30; + const static ULONG CHANGED_DEVICEOPTIONS = 31; }; #endif diff --git a/objects.mk b/objects.mk index 8f89d10..08df825 100644 --- a/objects.mk +++ b/objects.mk @@ -15,4 +15,4 @@ OBJECTS1 = command.o log.o tcp.o dsock.o thread.o timers.o i18n.o mutex.o \ fonts/helvB24.o fonts/helvB18.o \ remote.o led.o mtd.o video.o audio.o osd.o surface.o \ vmedialist.o media.o vpicture.o vpicturebanner.o \ - vaudioplayer.o audioplayer.o demuxeraudio.o + vaudioplayer.o audioplayer.o demuxeraudio.o abstractoption.o diff --git a/remote.cc b/remote.cc index 7e6ea75..43fcd3c 100644 --- a/remote.cc +++ b/remote.cc @@ -19,9 +19,11 @@ */ #include "remote.h" - +#include "wremoteconfig.h" #include "i18n.h" #include "log.h" +#include "vdr.h" +#include "wtabbar.h" Remote* Remote::instance = NULL; @@ -418,3 +420,38 @@ char *Remote::CommandTranslateStr(UCHAR command) } return desc; } + +bool Remote::addOptionPagesToWTB(WTabBar *wtb) +{ + WRemoteConfig* wrc = new WRemoteConfig(); + wtb->addTab(tr("Remote Control"), wrc); + return true; +} + +bool Remote::loadOptionsfromServer(VDR* vdr) +{ + // Set remote keys + char * config; + config = vdr->configLoad("General", "Remote keys"); + + if (config) + { + Log::getInstance()->log("Remote", Log::INFO, "Config General/Remote keys load"); + LoadKeysConfig(config); + delete[] config; + } + else + { + Log::getInstance()->log("Remote", Log::INFO, "Config General/Remote keys not found"); + InitHWCListwithDefaults(); + } + return true; +} + +bool Remote::saveOptionstoServer() +{ + char *keyscon=SaveKeysConfig(); + VDR::getInstance()->configSave("General","Remote keys",keyscon); + delete [] keyscon; + return true; +} diff --git a/remote.h b/remote.h index 729713d..29143e7 100644 --- a/remote.h +++ b/remote.h @@ -25,17 +25,23 @@ #include #include "defines.h" +#include "abstractoption.h" + using namespace std; typedef map RemoteTranslationList; -class Remote +class Remote: public AbstractOption { public: Remote(); virtual ~Remote(); static Remote* getInstance(); + bool addOptionPagesToWTB(WTabBar *wtb); + bool loadOptionsfromServer(VDR* vdr); + bool saveOptionstoServer(); + void setRemoteType(UCHAR type); void setHWCtoCommand(ULLONG hcw,UCHAR command); void unsetHWC(ULLONG hcw); @@ -129,6 +135,7 @@ class Remote virtual UCHAR TranslateHWCFixed(ULLONG code); UCHAR TranslateHWCList(ULLONG code); UCHAR TranslateHWC(ULLONG code); + ULONG learnmode; static Remote* instance; diff --git a/stream.cc b/stream.cc index 556d7b3..0034b8f 100644 --- a/stream.cc +++ b/stream.cc @@ -81,17 +81,19 @@ int Stream::put(const UCHAR* inbuf, int len, UCHAR type) newPacket.disconti=false; newPacket.pts=0; newPacket.presentation_time=0; - //Extract the pts... - if ((inbuf[7] & 0x80) && len>14 ) { - newPacket.synched=true; - newPacket.pts=((ULLONG)(inbuf[9] & 0x0E) << 29 ) | - ( (ULLONG)(inbuf[10]) << 22 ) | - ( (ULLONG)(inbuf[11] & 0xFE) << 14 ) | - ( (ULLONG)(inbuf[12]) << 7 ) | - ( (ULLONG)(inbuf[13] & 0xFE) >> 1 ); - //ok we have the pts now convert it to a continously time code in 100ns units - newPacket.presentation_time=(ULLONG)(newPacket.pts*10000LL/90LL); - newPacket.presentation_time-=draintarget->SetStartOffset(newPacket.presentation_time,&newPacket.disconti); + if (type!=MPTYPE_MPEG_AUDIO_LAYER3) {//no PES + //Extract the pts... + if ((inbuf[7] & 0x80) && len>14 ) { + newPacket.synched=true; + newPacket.pts=((ULLONG)(inbuf[9] & 0x0E) << 29 ) | + ( (ULLONG)(inbuf[10]) << 22 ) | + ( (ULLONG)(inbuf[11] & 0xFE) << 14 ) | + ( (ULLONG)(inbuf[12]) << 7 ) | + ( (ULLONG)(inbuf[13] & 0xFE) >> 1 ); + //ok we have the pts now convert it to a continously time code in 100ns units + newPacket.presentation_time=(ULLONG)(newPacket.pts*10000LL/90LL); + newPacket.presentation_time-=draintarget->SetStartOffset(newPacket.presentation_time,&newPacket.disconti); + } } #endif diff --git a/surface.h b/surface.h index 56611ce..df8c313 100644 --- a/surface.h +++ b/surface.h @@ -64,6 +64,11 @@ class Surface virtual void readPixel(int x, int y, unsigned char* r, unsigned char* g, unsigned char* b)=0; virtual void screenShot(char* fileName)=0; + /* This is for system which need a locking of the drawing surface to speed up drawing */ + virtual void startFastDraw() {}; + virtual void endFastDraw() {}; + + virtual int blt(int fd, unsigned long shandle, int sx, int sy, int width, int height, unsigned long dhandle, int dx, int dy)=0; const static int SCREEN = 1; diff --git a/surfacewin.cc b/surfacewin.cc index dfaea4e..1156b68 100644 --- a/surfacewin.cc +++ b/surfacewin.cc @@ -29,6 +29,7 @@ SurfaceWin::SurfaceWin(int id) d3dtexture=NULL; d3dsurface=NULL; sheight=swidth=0; + fastdraw=false; event = CreateEvent(NULL,/*FALSE*/TRUE,FALSE,NULL); } @@ -128,24 +129,62 @@ int SurfaceWin::fillblt(int x, int y, int width, int height, unsigned int c) return 0; } + +void SurfaceWin::startFastDraw(){ + WaitForSingleObject(event,INFINITE); //since this might be called before surface + //allocation we will wait in this case, hopefully without deadlocks + if (!d3dsurface) { + return; //why does this happen + } + OsdWin* osd=((OsdWin*)(Osd::getInstance())); + LPDIRECT3DDEVICE9 d3ddev=osd->getD3dDev(); + if (screen==this) { + //This should not happen! + return ; + + } else { + osd->BeginPainting(); +// D3DLOCKED_RECT lockrect; + RECT rect={0,0,swidth,sheight}; + if (d3dsurface->LockRect(&lockrect,&rect,D3DLOCK_DISCARD)!=D3D_OK) { + osd->EndPainting(); + return ; + } + } + fastdraw=true; +} +void SurfaceWin::endFastDraw(){ + OsdWin* osd=((OsdWin*)(Osd::getInstance())); + if (d3dsurface->UnlockRect()!=D3D_OK) { + osd->EndPainting(); + return ; + } + osd->EndPainting(); + fastdraw=false; + } + + void SurfaceWin::drawPixel(int x, int y, unsigned int c) { //FixMe: locking for every single Pixel will be painfully slow + OsdWin* osd; + if (!fastdraw) { WaitForSingleObject(event,INFINITE); //since this might be called before surface //allocation we will wait in this case, hopefully without deadlocks if (!d3dsurface) { return; //why does this happen } - OsdWin* osd=((OsdWin*)(Osd::getInstance())); - LPDIRECT3DDEVICE9 d3ddev=osd->getD3dDev(); + osd=((OsdWin*)(Osd::getInstance())); + } if (x>=swidth || y>=sheight) return; //do not draw outside the surface if (screen==this) { //This should not happen! return ; } else { + if (!fastdraw) { osd->BeginPainting(); - D3DLOCKED_RECT lockrect; +// D3DLOCKED_RECT lockrect; RECT rect={x,y,x+1,y+1}; if (d3dsurface->LockRect(&lockrect,&rect,D3DLOCK_DISCARD)!=D3D_OK) { osd->EndPainting(); @@ -158,6 +197,11 @@ void SurfaceWin::drawPixel(int x, int y, unsigned int c) return ; } osd->EndPainting(); + } else { + unsigned int*row=(unsigned int*)(((char*)lockrect.pBits+lockrect.Pitch*y+4*x)); + row[0]=c; + } + } } @@ -221,7 +265,7 @@ void SurfaceWin::ReleaseSurface() if (temp_surf) temp_surf->Release(); if (temp_text) temp_text->Release(); } - +/* void SurfaceWin::drawJpeg(char *fileName,DWORD x, DWORD y,DWORD *width, DWORD *height){ WaitForSingleObject(event,INFINITE); //since this might be called before surface //allocation we will wait in this case, hopefully without deadlocks @@ -248,7 +292,7 @@ void SurfaceWin::drawJpeg(char *fileName,DWORD x, DWORD y,DWORD *width, DWORD *h &image_inf)!=D3D_OK) { Log::getInstance()->log("Surface", Log::DEBUG, "Could not open jpeg!"); - }*/ + }* if (D3DXLoadSurfaceFromResource( d3dsurface, NULL, @@ -268,3 +312,62 @@ void SurfaceWin::drawJpeg(char *fileName,DWORD x, DWORD y,DWORD *width, DWORD *h } +void SurfaceWin::drawJpeg(char *buffer,ULONG buflength,DWORD x, DWORD y,DWORD *width, DWORD *height){ + WaitForSingleObject(event,INFINITE); //since this might be called before surface + //allocation we will wait in this case, hopefully without deadlocks + if (!d3dsurface) { + return ; //why does this happen + } + OsdWin* osd=((OsdWin*)(Osd::getInstance())); + + + D3DXIMAGE_INFO image_inf; + osd->BeginPainting(); +// D3DXGetImageInfoFromFile(fileName,&image_inf); + D3DXGetImageInfoFromFileInMemory((void*)buffer,buflength,&image_inf); + RECT dest_rec={x,y,x+image_inf.Width, + y+image_inf.Height}; +/* if (D3DXLoadSurfaceFromFile( + d3dsurface, + NULL, + &dest_rec, + fileName, + NULL, + D3DX_FILTER_NONE, + 0, + &image_inf)!=D3D_OK) { + Log::getInstance()->log("Surface", Log::DEBUG, "Could not open jpeg!"); + + }*/ +/* if (D3DXLoadSurfaceFromResource( + d3dsurface, + NULL, + &dest_rec, + NULL, + fileName, + NULL, + D3DX_FILTER_NONE, + 0, + &image_inf)!=D3D_OK) { + Log::getInstance()->log("Surface", Log::DEBUG, "Could not open jpeg!"); + + }* + if (D3DXLoadSurfaceFromFileInMemory( + d3dsurface, + NULL, + &dest_rec, + (void*)buffer, + buflength, + NULL, + D3DX_FILTER_NONE, + 0, + &image_inf)!=D3D_OK) { + Log::getInstance()->log("Surface", Log::DEBUG, "Could not open jpeg!"); + + } + osd->EndPainting(); + *width=image_inf.Width; + *height=image_inf.Height; + +}*/ + diff --git a/surfacewin.h b/surfacewin.h index 45423d7..4b6972d 100644 --- a/surfacewin.h +++ b/surfacewin.h @@ -35,6 +35,9 @@ class SurfaceWin : public Surface int create(UINT width, UINT height); void display(); + void startFastDraw(); + void endFastDraw(); + int fillblt(int x, int y, int width, int height, unsigned int c); void drawPixel(int x, int y, unsigned int c); void drawHorzLine(int x1, int x2, int y, unsigned int c); @@ -44,15 +47,18 @@ class SurfaceWin : public Surface void screenShot(char* fileName); void ReleaseSurface(); int blt(int fd, unsigned long shandle, int sx, int sy, int width, int height, unsigned long dhandle, int dx, int dy); - void drawJpeg(char *fileName,DWORD x, DWORD y,DWORD *width, DWORD *height); +/* void drawJpeg(char *fileName,DWORD x, DWORD y,DWORD *width, DWORD *height); + void drawJpeg(char *buffer,ULONG buflength,DWORD x, DWORD y,DWORD *width, DWORD *height);*/ LPDIRECT3DSURFACE9 getD3dsurface() {WaitForSingleObject(event,INFINITE); return d3dsurface;}; LPDIRECT3DTEXTURE9 getD3dtexture() {return d3dtexture;}; private: LPDIRECT3DSURFACE9 d3dsurface; LPDIRECT3DTEXTURE9 d3dtexture; + D3DLOCKED_RECT lockrect; UINT sheight,swidth; HANDLE event; + bool fastdraw; }; #endif diff --git a/vaudioplayer.cc b/vaudioplayer.cc index fb0c1df..2557cbd 100644 --- a/vaudioplayer.cc +++ b/vaudioplayer.cc @@ -484,14 +484,14 @@ void VAudioplayer::drawBanner(){ banner=createBannerView(numlines); } bannerlines=numlines; - char buf[len]; + char *buf=new char [len]; if (playerError) { - snprintf(buf,len,"%s",first); + SNPRINTF(buf,len,"%s",first); } else { char tbuf[Media::TIMEBUFLEN]; if (playall) { - snprintf(buf,len,"%s\n" + SNPRINTF(buf,len,"%s\n" "%s:%s\n" "%s: %d/%d\n" "%s:%s\n" @@ -503,7 +503,7 @@ void VAudioplayer::drawBanner(){ tr("Time"),currentMedia->getTimeString(tbuf)); } else { - snprintf(buf,len,"%s\n" + SNPRINTF(buf,len,"%s\n" "%s:%s\n" "%s:%s\n" "%s:%s\n", @@ -523,6 +523,7 @@ void VAudioplayer::drawBanner(){ banner->rectangle(0, 0, banner->getWidth(), 30, Colour::TITLEBARBACKGROUND); banner->drawText(title, 5, 5, Colour::LIGHTTEXT); banner->drawPara(buf,5,32,Colour::LIGHTTEXT); + delete [] buf; int x=10; int ybottom=banner->getHeight(); banner->rectangle(0, ybottom - barRegion.h, banner->getWidth(), barRegion.h, Colour::TITLEBARBACKGROUND); @@ -573,13 +574,19 @@ void VAudioplayer::drawClocks() { time_t lengthSec=(time_t)(getPlayer()->getSonglen()); struct tm cpos; struct tm slen; - gmtime_r(¤tSec,&cpos); - gmtime_r(&lengthSec,&slen); +/* gmtime_r(¤tSec,&cpos); + gmtime_r(&lengthSec,&slen);*/ + cpos.tm_hour=currentSec/3600; + cpos.tm_min=(currentSec-cpos.tm_hour*3600)/60; + cpos.tm_sec=(currentSec-cpos.tm_hour*3600-cpos.tm_min*60); + slen.tm_hour=0; + slen.tm_min=0; + slen.tm_sec=0; char buffer[100]; if (currentSec >= lengthSec) { - snprintf(buffer,99, "-:--:-- / -:--:-- %03dk",getPlayer()->getCurrentBitrate()/1000); + SNPRINTF(buffer,99, "-:--:-- / -:--:-- %03dk",getPlayer()->getCurrentBitrate()/1000); } else { diff --git a/video.h b/video.h index 3842175..2e69d95 100644 --- a/video.h +++ b/video.h @@ -24,6 +24,7 @@ #include #include "defines.h" #include "draintarget.h" +#include "abstractoption.h" typedef struct _hmsf { @@ -33,7 +34,7 @@ typedef struct _hmsf UINT frames; } hmsf; -class Video: public DrainTarget +class Video: public DrainTarget, public AbstractOption { public: Video(); diff --git a/videowin.cc b/videowin.cc index eef1b6b..0d69fcd 100644 --- a/videowin.cc +++ b/videowin.cc @@ -24,6 +24,11 @@ #include "dsallocator.h" #include "vdr.h" #include "osdwin.h" +#include "audiowin.h" +#include "vtabsviewman.h" +#include "wwinvideofilter.h" +#include "wtabbar.h" +#include "i18n.h" void AdjustWindow(); @@ -62,10 +67,11 @@ VideoWin::VideoWin() pseudotvsize=0; videoposx=0; videoposy=0; + aud_type=Audio::MPEG2_PES; iframemode=false;//We are not in Iframe mode at begining -#ifdef NEW_DS_MECHANISMENS + videofilterselected=-1; -#endif + @@ -75,7 +81,6 @@ VideoWin::~VideoWin() { CleanupDS(); CloseHandle(filtermutex); -#ifdef NEW_DS_MECHANISMENS int i; for (i=0;iRelease(); - filtmap->Release(); - Log::getInstance()->log("VideoWin", Log::ERR , "Failed to create Bindctx!"); - return; - }*/ + LPOLESTR string; moni->GetDisplayName(0,0,&string); desc.displayname=new char[wcslen(string)+1]; @@ -270,24 +265,10 @@ void VideoWin::dstest() bag->Release(); } - IBaseFilter *filter; - if (moni->BindToObject(0,0,IID_IBaseFilter,(void**)&filter) == S_OK) - { - IAMDecoderCaps*desccaps; - if (filter->QueryInterface(IID_IAMDecoderCaps,(void**) &desccaps)==S_OK) - { - DWORD caps; - desccaps->GetDecoderCaps(AM_GETDECODERCAP_QUERY_VMR9_SUPPORT,&caps); - if (caps == DECODER_CAP_SUPPORTED) - { - desc.vmr9 = true; - } - desccaps->Release(); - } - filter->Release(); - } + + videofilterlist.push_back(desc); - + moni->Release(); @@ -295,26 +276,163 @@ void VideoWin::dstest() } int i; videofilterselected=-1; - for (i = 0;i Release(); + + + + filtmap->Release(); +} + +bool VideoWin::loadOptionsfromServer(VDR* vdr) +{ + char *name=vdr->configLoad("DirectShow","VideoFilter"); + + if (name != NULL) { - if (videofilterlist[i].vmr9) + for (int i = 0;i log("VideoWin", Log::ERR , "No video filter found!"); - } - - myenum->Release(); + } + return true; +} +bool VideoWin::saveOptionstoServer() +{ + VDR::getInstance()->configSave("DirectShow", + "VideoFilter",videofilterlist[videofilterselected].displayname); + return true; +} - filtmap->Release(); +IBaseFilter *VideoWin::getVideoFilter() +{ + IBaseFilter *curfilter= NULL; + if (videofilterselected == -1) + { + int i; + for (i = 0;i BindToObject(0,0,IID_IBaseFilter,(void**)&curfilter) == S_OK) + { + IAMDecoderCaps* desccaps=NULL; + if (curfilter->QueryInterface(IID_IAMDecoderCaps,(void**) &desccaps)==S_OK) + { + DWORD caps; + desccaps->GetDecoderCaps(AM_GETDECODERCAP_QUERY_VMR9_SUPPORT,&caps); + if (caps == DECODER_CAP_SUPPORTED) + { + videofilterlist[i].vmr9tested = true; + videofilterlist[i].vmr9 = true; + videofilterselected = i; + } + else + { + videofilterlist[i].vmr9tested = true; + videofilterlist[i].vmr9 = false; + + curfilter->Release(); + curfilter=NULL; + } + } + desccaps->Release(); + } + moni->Release(); + } + delete [] name; + bindctx->Release(); + } + if (videofilterlist[i].vmr9) break; + + } + if (curfilter != NULL) + { + VDR *vdr=VDR::getInstance(); + if (vdr != NULL) + { + vdr->configSave("DirectShow","VideoFilter", + videofilterlist[videofilterselected].displayname); + } + return curfilter; + } + } + else + { + IBindCtx *bindctx=NULL; + if (CreateBindCtx(0,&bindctx)!=S_OK) return NULL; + IMoniker * moni=NULL; + LPCOLESTR name=new WCHAR[strlen(videofilterlist[videofilterselected].displayname)+1]; + mbstowcs((wchar_t*)name,videofilterlist[videofilterselected].displayname, + strlen(videofilterlist[videofilterselected].displayname)+1); + ULONG eater; + if (MkParseDisplayName(bindctx,name,&eater,&moni)==S_OK) + { + if (moni->BindToObject(0,0,IID_IBaseFilter,(void**)&curfilter) == S_OK) + { + IAMDecoderCaps* desccaps=NULL; + if (curfilter->QueryInterface(IID_IAMDecoderCaps,(void**) &desccaps)==S_OK) + { + DWORD caps; + desccaps->GetDecoderCaps(AM_GETDECODERCAP_QUERY_VMR9_SUPPORT,&caps); + if (caps == DECODER_CAP_SUPPORTED) + { + videofilterlist[videofilterselected].vmr9tested = true; + videofilterlist[videofilterselected].vmr9 = true; + } + else + { + videofilterlist[videofilterselected].vmr9tested = true; + videofilterlist[videofilterselected].vmr9 = false; + Log::getInstance()->log("VideoWin", Log::WARN ,"Filter does not support VMR9, but is selected, manual selection!"); + } + } + moni->Release(); + delete [] name; + bindctx->Release(); + return curfilter; + } + moni->Release(); + } + bindctx->Release(); + delete [] name; + return NULL; + } + return NULL; + } -#endif + #ifdef DS_DEBUG // This stuff would not included in vomp due to lincemse restrcitions #include "dshelper.h" @@ -328,6 +446,77 @@ int VideoWin::play() return 1; } +bool VideoWin::addOptionPagesToWTB(WTabBar *wtb) +{ + Boxx *box=new WWinVideoFilter(); + wtb->addTab(tr("Video Filter"), box); + return true; +} + +const VideoFilterDescList *VideoWin::getVideoFilterList(int &selected) +{ + selected=videofilterselected; + return &videofilterlist; +} + +bool VideoWin::selectVideoFilter(int filter) +{ + IBindCtx *bindctx=NULL; + if (CreateBindCtx(0,&bindctx)!=S_OK) return NULL; + IMoniker * moni=NULL; + LPCOLESTR name=new WCHAR[strlen(videofilterlist[filter].displayname)+1]; + mbstowcs((wchar_t*)name,videofilterlist[filter].displayname, + strlen(videofilterlist[filter].displayname)+1); + ULONG eater; + bool success=false; + if (MkParseDisplayName(bindctx,name,&eater,&moni)==S_OK) + { + IBaseFilter* curfilter=NULL; + if (moni->BindToObject(0,0,IID_IBaseFilter,(void**)&curfilter) == S_OK) + { + IAMDecoderCaps* desccaps=NULL; + if (curfilter->QueryInterface(IID_IAMDecoderCaps,(void**) &desccaps)==S_OK) + { + DWORD caps; + HRESULT hres=desccaps->GetDecoderCaps(AM_GETDECODERCAP_QUERY_VMR9_SUPPORT,&caps); + if (caps == DECODER_CAP_SUPPORTED) + { + videofilterlist[filter].vmr9tested = true; + videofilterlist[filter].vmr9 = true; + success=true; + } + else + { + videofilterlist[filter].vmr9tested = true; + videofilterlist[filter].vmr9 = false; + success=false; + } + desccaps->Release(); + } else { + videofilterlist[filter].vmr9tested = true; + videofilterlist[filter].vmr9 = false; + success=false; + } + + curfilter->Release(); + + } + moni->Release(); + } + bindctx->Release(); + delete [] name; + if (success) + { + videofilterselected=filter; + return true; + } + else + { + return false; + } +} + + int VideoWin::dsInitVideoFilter() { #ifdef DO_VIDEO @@ -380,7 +569,9 @@ int VideoWin::dsInitVideoFilter() CleanupDS(); return 0; } - if (hres=fg2->RenderEx((IPin*)sourcefilter->GetVideoPin()/*video*/, +/*#ifndef NEW_DS_MECHANISMENS + + if (hres=fg2->RenderEx((IPin*)sourcefilter->GetVideoPin()/*video*, AM_RENDEREX_RENDERTOEXISTINGRENDERERS,NULL) != S_OK) { Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering Video!"); @@ -389,9 +580,98 @@ int VideoWin::dsInitVideoFilter() CleanupDS(); return 0; } + +#else*/ + IBaseFilter*videofilter=getVideoFilter(); + if (hres=dsgraphbuilder->AddFilter(videofilter,NULL) != S_OK) + { + Log::getInstance()->log("VideoWin", Log::WARN , "Failed adding Video Filter!"); + ReleaseMutex(filtermutex); + CleanupDS(); + return 0; + } + IEnumPins *pinenum=NULL; + bool error=false; + if (videofilter->EnumPins(&pinenum) == S_OK) + { + IPin *current=NULL; + ULONG fetch=0; + bool firststep=false; + + while (pinenum->Next(1,¤t,&fetch)==S_OK) + { + PIN_DIRECTION dir; + if (current->QueryDirection(&dir)==S_OK) + { + if (dir == PINDIR_INPUT) + { + if (sourcefilter->GetVideoPin()->Connect(current,NULL)==S_OK) + { + current->Release(); + firststep=true; + break; + } + } + } + current->Release(); + } + if (firststep==false) + { + Log::getInstance()->log("VideoWin", Log::WARN , "Video Filter has no suitable input!"); + videofilter->Release(); + ReleaseMutex(filtermutex); + CleanupDS(); + return 0; + } + bool secondstep=false; + pinenum->Reset(); + while (pinenum->Next(1,¤t,&fetch)==S_OK) + { + PIN_DIRECTION dir; + if (current->QueryDirection(&dir)==S_OK) + { + if (dir == PINDIR_OUTPUT) + { + + if (fg2->RenderEx((IPin*)current/*video*/, + AM_RENDEREX_RENDERTOEXISTINGRENDERERS,NULL) ==S_OK) + { + current->Release(); + secondstep=true; + break; + } + } + } + current->Release(); + } + if (secondstep==false) + { + Log::getInstance()->log("VideoWin", Log::WARN , "Video Filter has no suitable output!"); + videofilter->Release(); + ReleaseMutex(filtermutex); + CleanupDS(); + return 0; + } + + videofilter->Release(); + pinenum->Release(); + + } + + + fg2->Release(); + return 1; } -#endif +#endif + +} + +int VideoWin::setAudioStreamType(UCHAR type) +{ + aud_type=type; + if (!initted) return 0; + return 1; } int VideoWin::dsplay() @@ -414,7 +694,11 @@ int VideoWin::dsplay() #endif firstsynched=false; - lastaudiomode=MPTYPE_MPEG_AUDIO; + if (aud_type==Audio::MP3) { + lastaudiomode=MPTYPE_MPEG_AUDIO_LAYER3; + } else { + lastaudiomode=MPTYPE_MPEG_AUDIO; + } //lastaudiomode=MPTYPE_AC3; sourcefilter=new DsSourceFilter(); //Creating our Source filter for pushing Data // to DirectShow @@ -425,14 +709,23 @@ int VideoWin::dsplay() CleanupDS(); return 0; } - - if (hres=dsgraphbuilder->Render((IPin*)sourcefilter->GetAudioPin()/*audio*/)!=S_OK) + sourcefilter->GetAudioPin()->SetPinMode(lastaudiomode); + /*if (hres=dsgraphbuilder->Render((IPin*)sourcefilter->GetAudioPin()/*audio*)!=S_OK) + { + Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering audio!"); + ReleaseMutex(filtermutex); + CleanupDS(); + return 0; + }*/ + if (((AudioWin*)Audio::getInstance())->dsInitAudioFilter(dsgraphbuilder)==0) { Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering audio!"); ReleaseMutex(filtermutex); CleanupDS(); return 0; } + + if (dsInitVideoFilter()==0) { return 0; @@ -488,59 +781,7 @@ int VideoWin::EnterIframePlayback() } #ifdef DO_VIDEO if (videoon) { - //We alloc the vmr9 as next step - if (hres=CoCreateInstance(CLSID_VideoMixingRenderer9,0, - CLSCTX_INPROC_SERVER,IID_IBaseFilter,(void**) &dsvmrrenderer)!=S_OK) { - Log::getInstance()->log("VideoWin", Log::WARN ,"Failed creating VMR9 renderer!"); - ReleaseMutex(filtermutex); - CleanupDS(); - return 0; - } - /*VMR 9 stuff**/ - if (hres=dsgraphbuilder->AddFilter(dsvmrrenderer,L"VMR9")!=S_OK) { - Log::getInstance()->log("VideoWin", Log::WARN ,"Failed adding VMR9 renderer!"); - ReleaseMutex(filtermutex); - CleanupDS(); - return 0; - } - IVMRFilterConfig9* vmrfilconfig; - if (dsvmrrenderer->QueryInterface(IID_IVMRFilterConfig9,(void**)&vmrfilconfig)!=S_OK) { - ReleaseMutex(filtermutex); - CleanupDS(); - Log::getInstance()->log("VideoWin", Log::WARN ,"Failed getting VMR9 Filterconfig interface!"); - - return 0; - } - vmrfilconfig->SetRenderingMode(VMR9Mode_Renderless); - vmrfilconfig->Release(); - - if (dsvmrrenderer->QueryInterface(IID_IVMRSurfaceAllocatorNotify9,(void**)& dsvmrsurfnotify)!=S_OK) { - Log::getInstance()->log("VideoWin", Log::WARN ,"Failed getting VMR9 Surface Allocator interface!"); - ReleaseMutex(filtermutex); - CleanupDS(); - return 0; - } - allocatorvmr=new DsAllocator(); - dsvmrsurfnotify->AdviseSurfaceAllocator(NULL,allocatorvmr); - allocatorvmr->AdviseNotify(dsvmrsurfnotify); - - /*VMR 9 stuff end */ - IFilterGraph2*fg2=NULL; - if (dsgraphbuilder->QueryInterface(IID_IFilterGraph2,(void**)&fg2)!=S_OK) { - Log::getInstance()->log("VideoWin", Log::WARN , "Failed querying for FilterGraph2 Interface!"); - ReleaseMutex(filtermutex); - CleanupDS(); - return 0; - } - if (hres=fg2->RenderEx((IPin*)sourcefilter->GetVideoPin()/*video*/, - AM_RENDEREX_RENDERTOEXISTINGRENDERERS,NULL)!=S_OK) { - Log::getInstance()->log("VideoWin", Log::WARN , "Failed rendering Video!"); - fg2->Release(); - ReleaseMutex(filtermutex); - CleanupDS(); - return 0; - } - fg2->Release(); + dsInitVideoFilter(); } #endif /* if (hres=CoCreateInstance(CLSID_SystemClock,NULL,CLSCTX_INPROC_SERVER, @@ -771,6 +1012,7 @@ UINT VideoWin::DeliverMediaPacket(MediaPacket packet, const UCHAR* buffer, UINT *samplepos) { + /*First Check, if we have an audio sample*/ if (!isdsinited()) return 0; #ifdef DO_VIDEO @@ -1084,7 +1326,7 @@ void VideoWin::displayIFrame(const UCHAR* buffer, UINT length) ms_length=ms->GetSize(); ms->GetPointer(&ms_buf); } - if (packet_length-headerstrip>0) { + if (packet_length>headerstrip) { memcpy(ms_buf+write_pos, buffer+read_pos+headerstrip, packet_length-headerstrip); write_pos += packet_length-headerstrip; } @@ -1145,4 +1387,3 @@ int VideoWin::test2() - diff --git a/videowin.h b/videowin.h index aa8fb77..d435b83 100644 --- a/videowin.h +++ b/videowin.h @@ -33,13 +33,14 @@ #include "video.h" //#define DS_DEBUG -//#define NEW_DS_MECHANISMENS +#define NEW_DS_MECHANISMENS #ifdef NEW_DS_MECHANISMENS struct VideoFilterDesc { char * displayname; char * friendlyname; bool vmr9; + bool vmr9tested; }; using namespace std; typedef vector VideoFilterDescList; @@ -70,6 +71,9 @@ class VideoWin : public Video int setPosition(int x, int y); int sync(); int play(); + bool loadOptionsfromServer(VDR* vdr); + bool saveOptionstoServer(); + bool addOptionPagesToWTB(WTabBar *wtb); int dsplay(); bool InIframemode() {return iframemode;}; int stop(); @@ -96,6 +100,8 @@ class VideoWin : public Video UINT DeliverMediaPacket(MediaPacket packet, const UCHAR* buffer, UINT *samplepos); virtual bool supportsAc3(); + + private: MediaPacket mediapacket; public: @@ -105,6 +111,7 @@ class VideoWin : public Video int getCurrentVideoMediaSample(IMediaSample** ms); int DeliverVideoMediaSample(); + int setAudioStreamType(UCHAR type); virtual long long SetStartOffset(long long curreftime, bool *rsync); long long SetStartAudioOffset(long long curreftime, bool *rsync); @@ -125,6 +132,11 @@ class VideoWin : public Video int lastAType() {return lastaudiomode;}; bool changeAType(int type,IMediaSample* ms); + + const VideoFilterDescList *getVideoFilterList(int &selected); + bool selectVideoFilter(int filter); + DsSourceFilter* getSourceFilter() {return sourcefilter;}; + #ifdef DEV int test(); int test2(); @@ -132,8 +144,9 @@ class VideoWin : public Video private: int EnterIframePlayback(); #ifdef NEW_DS_MECHANISMENS - void dstest(); - VideoFilterDescList videofilterlist; + void dstest(); + void initFilterDatabase(); + IBaseFilter *getVideoFilter(); VideoFilterDescList videofilterlist; int videofilterselected; #endif int dsInitVideoFilter(); @@ -171,6 +184,7 @@ private: unsigned int videoposy; int lastaudiomode; int audiovolume; + UCHAR aud_type; #ifdef DS_DEBUG DWORD graphidentifier; #endif diff --git a/vmedialist.cc b/vmedialist.cc index e29a745..4ac606b 100644 --- a/vmedialist.cc +++ b/vmedialist.cc @@ -21,8 +21,9 @@ #include #include #include +#ifndef WIN32 #include "unistd.h" - +#endif #include "vmedialist.h" #include "vpicture.h" @@ -433,7 +434,7 @@ void VMediaList::doShowingBar() default: break; } - snprintf(showing, 250,tr("%i to %i of %i"), + SNPRINTF(showing, 250,tr("%i to %i of %i"), topOption, sl.getBottomOption(), sl.getNumOptions()); // Box b; diff --git a/vompwin.rc b/vompwin.rc index 40f2dd5..a5af354 100644 --- a/vompwin.rc +++ b/vompwin.rc @@ -40,9 +40,9 @@ BEGIN VK_RETURN, VOMP_FULL_SCREEN, VIRTKEY, ALT, NOINVERT END -vdr.jpg RCDATA other\vdr.jpg -wallpaperNTSC.jpg RCDATA other\wallpaperNTSC.jpg -wallpaperPAL.jpg RCDATA other\wallpaperPAL.jpg +/vdr.jpg RCDATA other\vdr.jpg +/wallpaperNTSC.jpg RCDATA other\wallpaperNTSC.jpg +/wallpaperPAL.jpg RCDATA other\wallpaperPAL.jpg VOMPMENU MENU BEGIN @@ -96,4 +96,3 @@ BEGIN END - diff --git a/vopts.cc b/vopts.cc index 76a237c..b45c886 100644 --- a/vopts.cc +++ b/vopts.cc @@ -22,6 +22,7 @@ #include "colour.h" #include "video.h" +#include "audio.h" #include "i18n.h" #include "remote.h" #include "boxstack.h" @@ -101,14 +102,18 @@ VOpts::VOpts() wop->addOptionLine(option); - WRemoteConfig* wrc = new WRemoteConfig(); - tabbar.addTab(tr("Remote Control"), wrc); - panes[1] = wrc; +/* WRemoteConfig* wrc = new WRemoteConfig(); + tabbar.addTab(tr("Remote Control"), wrc);*/ + Remote::getInstance()->addOptionPagesToWTB(&tabbar); + // panes[1] = wrc; + + Video::getInstance()->addOptionPagesToWTB(&tabbar); + Audio::getInstance()->addOptionPagesToWTB(&tabbar); wop = new WOptionPane(); tabbar.addTab(tr("Timers"), wop); - panes[2] = wop; + panes[1] = wop; option = new Option(9, "Default start margin (minutes)", "Timers", "Start margin", Option::TYPE_INT, 20, 5, 0, NULL); options.push_back(option); @@ -126,7 +131,7 @@ VOpts::VOpts() wop = new WOptionPane(); tabbar.addTab(tr("Advanced"), wop); - panes[3] = wop; + panes[2] = wop; option = new Option(8, "VDR-Pri 0=OK !See forums!", "General", "Live priority", Option::TYPE_INT, 100, 0, 0, NULL); options.push_back(option); @@ -141,7 +146,7 @@ VOpts::VOpts() VOpts::~VOpts() { - for (int i = 0; i < numPanes; i++) delete panes[i]; + // for (int i = 0; i < numPanes; i++) delete panes[i]; //Move to TabBar, Marten delete[] panes; for(vector::iterator j = options.begin(); j != options.end(); j++) delete *j; @@ -174,13 +179,18 @@ void VOpts::doSave() { VDR* vdr = VDR::getInstance(); + Remote::getInstance()->saveOptionstoServer(); //Remote + Video::getInstance()->saveOptionstoServer(); //Video + Audio::getInstance()->saveOptionstoServer(); //Remote + // Damn, and the dynamic idea was going *so* well... + //Whats about a check with typeid operator? WOptionPane* wop; wop = (WOptionPane*)panes[0]; wop->saveOpts(); - wop = (WOptionPane*)panes[2]; + wop = (WOptionPane*)panes[1]; wop->saveOpts(); - wop = (WOptionPane*)panes[3]; + wop = (WOptionPane*)panes[2]; wop->saveOpts(); @@ -291,3 +301,29 @@ void VOpts::doSave() } } +void VOpts::processMessage(Message* m) +{ + if (m->message == Message::MOUSE_MOVE) + { + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (tabbar.mouseMove(x,y)) { + BoxStack::getInstance()->update(this); + } + + } + else if (m->message == Message::MOUSE_LBDOWN) + { + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (tabbar.mouseLBDOWN(x,y)) { + BoxStack::getInstance()->update(this); + } else if (x<0 || y <0 || x>(int)getWidth() || y>(int)getHeight()) + { + BoxStack::getInstance()->handleCommand(Remote::BACK); //simulate cancel press + } + + + } +} + diff --git a/vopts.h b/vopts.h index e9cfaef..c6d1acd 100644 --- a/vopts.h +++ b/vopts.h @@ -35,7 +35,8 @@ class VOpts : public TBBoxx VOpts(); ~VOpts(); - int handleCommand(int command); + int handleCommand(int command); + void processMessage(Message* m); private: void doSave(); diff --git a/vpicture.cc b/vpicture.cc index 25badaa..c46aa62 100644 --- a/vpicture.cc +++ b/vpicture.cc @@ -75,7 +75,7 @@ VPicture::VPicture(VMediaList *p) setSize(video->getScreenWidth(), video->getScreenHeight()); createBuffer(); jpeg.setSurface(surface); - jpeg.setDimensions(area.w,area.h); + jpeg.setDimensions(area.w,area.h); banner=NULL; fullname=NULL; filename=NULL; @@ -109,13 +109,14 @@ void VPicture::draw() Log::getInstance()->log("VPicture::draw", Log::DEBUG, "needDraw=%d,p=%p", needDraw,this); // View::draw(); + if (mediaError) { drawText(mediaError,20,area.h-10,Colour::LIGHTTEXT); return; } if (needDraw) { jpeg.draw(); - } + } } @@ -317,15 +318,16 @@ void VPicture::showBanner(bool loading,int shortDisplay) { banner->fillColour(infoBack); if (! loading) { int len=strlen(filename)+Media::TIMEBUFLEN+20; - char buf[len]; + char *buf=new char[len]; char tbuf[Media::TIMEBUFLEN]; - snprintf(buf,len,"%c%02ds%c %s %s ", + SNPRINTF(buf,len,"%c%02ds%c %s %s ", slideshow?' ':'[', showtime, slideshow?' ':']', currentMedia->getTimeString(tbuf), filename); banner->setText(buf); + delete [] buf; } else { banner->setText(filename); @@ -397,7 +399,7 @@ void VPicture::showInfo(){ info->setPosition(100, 150); char buf[INFOBUF]; char tbuf[Media::TIMEBUFLEN]; - snprintf(buf,INFOBUF,"%s= %s\n%s= %ld x %ld\n%s= %ld kBytes\n%s= %s\n%s= %ld\n%s= 1/%ld", + SNPRINTF(buf,INFOBUF,"%s= %s\n%s= %ld x %ld\n%s= %ld kBytes\n%s= %s\n%s= %ld\n%s= 1/%ld", tr("Directory"), parent->getDirname(), tr("Format(px)"),jpeg.getJpegInfo(WJpeg::JPEG_WIDTH),jpeg.getJpegInfo(WJpeg::JPEG_HEIGHT), tr("Filesize"),jpeg.getJpegInfo(WJpeg::JPEG_SIZE)/1000, diff --git a/vpicturebanner.cc b/vpicturebanner.cc index 85c4015..3fd6901 100644 --- a/vpicturebanner.cc +++ b/vpicturebanner.cc @@ -58,9 +58,10 @@ void VPictureBanner::draw() // View::draw(); if (loading) { if (info) { - char buf[strlen(info)+100]; + char *buf=new char[strlen(info)+100]; sprintf(buf,"%s %s",tr("Loading"),info); drawText(buf,5,area.h-25,Colour::LIGHTTEXT); + delete buf; } else drawText(tr("Loading"),5,3,Colour::LIGHTTEXT); } diff --git a/vtimeredit.cc b/vtimeredit.cc index 4ca1149..380647d 100644 --- a/vtimeredit.cc +++ b/vtimeredit.cc @@ -231,7 +231,25 @@ int VTimerEdit::handleCommand(int command) void VTimerEdit::processMessage(Message* m) { - if (m->message == Message::MOUSE_LBDOWN) + if (m->message == Message::MOUSE_MOVE) + { + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (buttonBack.mouseMove(x,y)) { + selectedButton=0; + buttonDelete.setActive(false); + buttonBack.draw(); + buttonDelete.draw(); + BoxStack::getInstance()->update(this); + } else if (buttonDelete.mouseMove(x,y)) { + selectedButton=1; + buttonBack.setActive(false); + buttonBack.draw(); + buttonDelete.draw(); + BoxStack::getInstance()->update(this); + } + + } else if (m->message == Message::MOUSE_LBDOWN) { BoxStack::getInstance()->handleCommand(Remote::OK); //simulate OK press } diff --git a/vvideolive.cc b/vvideolive.cc index 5d6ccee..06e1864 100644 --- a/vvideolive.cc +++ b/vvideolive.cc @@ -82,14 +82,17 @@ VVideoLive::VVideoLive(ChannelList* tchanList, ULONG tstreamType, VChannelList* } Log::getInstance()->log("VVideoLive", Log::DEBUG, "Do WSS: %u", dowss); - wss.setFormat(video->getFormat()); - wss.setWide(true); - add(&wss); - - wssRegion.x = 0; - wssRegion.y = 6; - wssRegion.w = video->getScreenWidth(); - wssRegion.h = 2; + if (dowss) + { + wss.setFormat(video->getFormat()); + wss.setWide(true); + add(&wss); + + wssRegion.x = 0; + wssRegion.y = 6; + wssRegion.w = video->getScreenWidth(); + wssRegion.h = 2; + } } VVideoLive::~VVideoLive() diff --git a/vvideorec.cc b/vvideorec.cc index e85ad5e..9faad22 100644 --- a/vvideorec.cc +++ b/vvideorec.cc @@ -111,14 +111,17 @@ VVideoRec::VVideoRec(Recording* rec) } Log::getInstance()->log("VVideoRec", Log::DEBUG, "Do WSS: %u", dowss); - wss.setFormat(video->getFormat()); - wss.setWide(true); - add(&wss); - - wssRegion.x = 0; - wssRegion.y = 0; - wssRegion.w = video->getScreenWidth(); - wssRegion.h = 300; + if (dowss) + { + wss.setFormat(video->getFormat()); + wss.setWide(true); + add(&wss); + + wssRegion.x = 0; + wssRegion.y = 0; + wssRegion.w = video->getScreenWidth(); + wssRegion.h = 300; + } } VVideoRec::~VVideoRec() diff --git a/wbutton.cc b/wbutton.cc index 03faf47..ae0806e 100644 --- a/wbutton.cc +++ b/wbutton.cc @@ -91,25 +91,21 @@ int WButton::getTag() bool WButton::mouseMove(int x, int y) { -/* - if ((x-offsetX)>=area.x && (y-offsetY)>=area.y - && (x-offsetX)<=area.w && (y-offsetY)<=area.h && !active) + if ((x-getRootBoxOffsetX())>=0 && (y-getRootBoxOffsetY())>=0 + && (x-getRootBoxOffsetX())<=(int)area.w && (y-getRootBoxOffsetY())<=(int)area.h && !active) { setActive(1); return true; } -*/ return false; } bool WButton::mouseLBDOWN(int x, int y) { -/* - if ((x-offsetX)>=area.x && (y-offsetY)>=area.y - && (x-offsetX)<=area.w && (y-offsetY)<=area.h && active) + if ((x-getRootBoxOffsetX())>=0 && (y-getRootBoxOffsetY())>=0 + && (x-getRootBoxOffsetX())<=(int)area.w && (y-getRootBoxOffsetY())<=(int)area.h && active) { return true; } -*/ return false; } diff --git a/winmain.cc b/winmain.cc index 882259e..34da3a1 100644 --- a/winmain.cc +++ b/winmain.cc @@ -41,6 +41,7 @@ #include "osdwin.h" #include "boxstack.h" #include "command.h" +#include "wol.h" void sighandler(int signalReceived); void shutdown(int code); @@ -58,6 +59,8 @@ Command* command; VDR* vdr; Video* video; Audio* audio; +Wol* wol; + bool wnd_fullscreen=false; bool wnd_topmost=false; RECT wnd_fs_rect={20,20,768+20,576+20}; @@ -146,6 +149,7 @@ INT WINAPI WinMain( HINSTANCE hinst , HINSTANCE previnst, LPSTR cmdline, int cmd audio = new AudioWin(); boxstack = new BoxStack(); command = new Command(); + wol = new Wol(); if (!logger || !remote || !mtd || !led || !osd || !video || !audio || !boxstack || !command) { @@ -855,6 +859,11 @@ void shutdown(int code) delete remote; logger->log("Core", Log::NOTICE, "Remote module shut down"); } + if (wol) + { + delete wol; + logger->log("Core", Log::NOTICE, "WOL module shut down"); + } if (logger) { diff --git a/wjpeg.cc b/wjpeg.cc index 4b1f55d..6deb08d 100644 --- a/wjpeg.cc +++ b/wjpeg.cc @@ -17,7 +17,7 @@ along with VOMP; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ - +#include "boxx.h" #include "wjpeg.h" #include @@ -25,14 +25,49 @@ #include "log.h" #include "surface.h" + extern "C" void jpeg_memio_src (j_decompress_ptr cinfo, void * userdata); extern "C" void jpeg_memio_cleanup (j_decompress_ptr cinfo); + +#ifdef WIN32 +ULONG WindowsResourceJpegReader::initRead(const char *filename) +{ + HRSRC res=FindResource(NULL,filename,RT_RCDATA); + hres=LoadResource(NULL,res); + buffer=LockResource(hres); + size=SizeofResource(NULL,res); + //CloseHandle(hres); + return size; +} + + ULONG WindowsResourceJpegReader::readChunk(ULONG offset,ULONG len,char **buf) +{ + if (offset>size) return 0; + ULONG toread=min(size-offset,len); + char* buffy=(char*)malloc(toread); + memcpy(buffy,((char*)buffer)+offset,toread); + *buf=buffy; + return toread; +} + + WindowsResourceJpegReader::~WindowsResourceJpegReader(){ + buffer=NULL; + size=0; + FreeResource(hres); + +} +#endif + WJpeg::WJpeg(){ fileName=NULL; +#ifndef WIN32 reader=NULL; +#else + reader=&winread; +#endif useImageDimensions=true; jheight=0; jwidth=0; @@ -55,7 +90,15 @@ int WJpeg::init(char* tfileName,bool useImage, JpegReader *rdr) fileName = new char[strlen(tfileName)+1]; strcpy(fileName,tfileName); } + if (rdr!=NULL) { reader=rdr; + } else { +#ifdef WIN32 + reader=&winread; +#else + reader=NULL; +#endif + } useImageDimensions=useImage; return 1; } @@ -97,6 +140,8 @@ void WJpeg::setRotate(int amount) { rotate=amount; } + + extern "C" { @@ -180,7 +225,7 @@ void WJpeg::drawPixel(int x, int y,int w,int h,int xpos, int ypos,Colour c){ } int WJpeg::drawJpeg() { -#ifndef WIN32 +//#ifndef WIN32 Log* logger = Log::getInstance(); unsigned char* buffer =NULL; struct jpeg_decompress_struct cinfo; @@ -204,7 +249,11 @@ int WJpeg::drawJpeg() { jpeg_create_decompress(&cinfo); if (fileName && ! reader) { jsize=0; //TODO: compute size for local files - jerr.infile=fopen(fileName, "r"); +#ifdef WIN32 + jerr.infile=fopen(fileName+1, "rb"); +#else + jerr.infile=fopen(fileName, "rb"); +#endif if (jerr.infile == NULL) { logger->log("BJpeg", Log::ERR, "Can't open JPEG"); @@ -275,9 +324,9 @@ int WJpeg::drawJpeg() { } //if our image is smaller - center it if (! useImageDimensions) { - xpos=(getWidth()-picturew)/2; + xpos=(((int)getWidth())-picturew)/2; if (xpos <0) xpos=0; - ypos=(getHeight()-pictureh)/2; + ypos=(((int)getHeight())-pictureh)/2; if (ypos <0) ypos=0; } //center point for rotation @@ -314,7 +363,8 @@ int WJpeg::drawJpeg() { logger->log("BJpeg", Log::DEBUG, "header w=%d,h=%d",cinfo.output_width,cinfo.output_height); #ifndef USE_BUFFER - unsigned char lbuf[linelen]; + //unsigned char lbuf[linelen]; + unsigned char *lbuf=new unsigned char[linelen]; unsigned char * ptr=lbuf; #else unsigned char * ptr=buffer; @@ -323,6 +373,8 @@ int WJpeg::drawJpeg() { int rowsread = 0; Colour c; + startFastDraw();//Tell the surface, that we will draw a lot of pixel, + //so that performance, can be optimized while (cinfo.output_scanline < cinfo.output_height) { // logger->log("BJpeg", Log::DEBUG, "%i", rowsread); @@ -340,6 +392,7 @@ int WJpeg::drawJpeg() { #endif } + endFastDraw(); logger->log("BJpeg", Log::DEBUG, "Done all jpeg_read"); @@ -354,7 +407,8 @@ int WJpeg::drawJpeg() { Colour c; UINT x, y, xoff; unsigned char* p; - + surface->startFastDraw();//Tell the surface, that we will draw a lot of pixel, + //so that performance, can be optimized for (y = 0; y < numlines; y++) { p = bufferPointers[y]; @@ -375,18 +429,35 @@ int WJpeg::drawJpeg() { drawPixel(x, y, w,h,xpos,ypos,c); } } - + surface->endFastDraw(); + delete [] lbuf; free(buffer); #endif logger->log("BJpeg", Log::DEBUG, "deleted buffer"); -#else +/*#else DWORD width,height; width=height=1; + if (!reader) + { ((SurfaceWin*)surface)->drawJpeg(fileName+1,offsetX,offsetY,&width,&height);//This should went into the abstract base classes? //Windows has a problem with the leading / fixme + } else { + ULONG jsize; + jsize=reader->initRead(fileName); + char *buffer; + if (jsize==reader->readChunk(0,jsize,&buffer)) + { + ((SurfaceWin*)surface)->drawJpeg(buffer,jsize,offsetX,offsetY,&width,&height);//This should went into the abstract base classes? + free(buffer); + } - setDimensions(width, height); -#endif + } + + // setDimensions(width, height); + jwidth=width; + jheight=height; + +#endif*/ return 0; } diff --git a/wjpeg.h b/wjpeg.h index cebde65..a4539d0 100644 --- a/wjpeg.h +++ b/wjpeg.h @@ -23,18 +23,28 @@ #include #include -#ifndef WIN32 + +#ifdef WIN32 + +#include +#include + + +//#define NEED_FAR_POINTERS +#define XMD_H //workaround some compiling issues +#endif + +//#ifndef WIN32 extern "C" { #include } -#else +/*#else //TODO find a replacement on WIN32 -#endif - -#include "boxx.h" +#endif*/ class Surface; +class Boxx; //a reader to be implemented by the caller class JpegReader { @@ -50,6 +60,18 @@ class JpegReader { virtual ULONG readChunk(ULONG offset,ULONG len,char **buf)=0; virtual ~JpegReader(){}; }; +#ifdef WIN32 +class WindowsResourceJpegReader: public JpegReader { + public: + virtual ULONG initRead(const char *filename); + virtual ULONG readChunk(ULONG offset,ULONG len,char **buf); + virtual ~WindowsResourceJpegReader(); +protected: + HGLOBAL hres; + LPVOID buffer; + DWORD size; +}; +#endif class WJpeg : public Boxx { @@ -57,7 +79,7 @@ class WJpeg : public Boxx // temp for boxx void setSurface(Surface* tsurface) {}; - void setDimensions(int width, int height) {}; + void setDimensions(int width, int height) {area.w=width;area.h=height;}; void setBackgroundColour(Colour& colour) {}; @@ -98,6 +120,9 @@ class WJpeg : public Boxx void drawPixel(int x, int y,int w,int h,int xpos, int ypos,Colour c); char* fileName; JpegReader *reader; +#ifdef WIN32 + WindowsResourceJpegReader winread; +#endif bool useImageDimensions; ULONG jsize; ULONG jheight; diff --git a/wol.cc b/wol.cc index 0af301b..a8f940e 100644 --- a/wol.cc +++ b/wol.cc @@ -24,12 +24,20 @@ #include #include +#ifndef WIN32 #include #include #include #include -#include "wol.h" +#else +#define ETH_ALEN 6 +#include +#include +#include +#include +#endif +#include "wol.h" #include "log.h" #define _PATH_PROCNET_ARP "/proc/net/arp" @@ -43,6 +51,9 @@ Wol::Wol() bEtherKnown = false; wolEnabled = true; logger = Log::getInstance(); +#ifdef WIN32 +// goo; +#endif } Wol::~Wol() @@ -58,7 +69,7 @@ void Wol::setEnabled(bool tEnabled) { wolEnabled = tEnabled; } - +#ifndef WIN32 /* Display the contents of the ARP cache in the kernel. */ int Wol::find_ether(char *name) { @@ -93,6 +104,46 @@ int Wol::find_ether(char *name) fclose(fp); return 0; } +#else +int Wol::find_ether(char *name) +{ + sockaddr_in sock_address; + int sockname_len=sizeof(sock_address); + WSAStringToAddress(name,AF_INET,NULL,(sockaddr*)&sock_address,&sockname_len); + + DWORD ip=sock_address.sin_addr.s_addr;; + ULONG size=0; + PMIB_IPNETTABLE table; + + GetIpNetTable(NULL,&size,TRUE); + table=(PMIB_IPNETTABLE)new char[size]; + if (table==NULL) return -1; + if (GetIpNetTable(table,&size,TRUE)!=NOERROR) + { + logger->log("Wol", Log::NOTICE, "Error getting IPtable"); + delete [] table; + return -1; + } + for (int x=0;xdwNumEntries;x++) + { + if (table->table[x].dwAddr==ip) { + char *ethp=ether_addr; + for (int i=0;itable[x].dwPhysAddrLen;i++) { + ethp+=sprintf(ethp,"%X:",table->table[x].bPhysAddr[i]); + } + delete [] table; + logger->log("Wol", Log::NOTICE, "Found etheraddr %s", ether_addr); + return 1; + } + + } + + delete [] table; + return 0; + + +} +#endif /* Input an Ethernet address and convert to binary. */ int Wol::convertToBinary(char *bufp, unsigned char *addr) @@ -184,12 +235,17 @@ int Wol::doWakeUp() } /* Set socket options */ +#ifndef WIN32 if (setsockopt (packet, SOL_SOCKET, SO_BROADCAST, (caddr_t) &optval, sizeof (optval)) < 0) +#else + if (setsockopt (packet, SOL_SOCKET, SO_BROADCAST, (char*)&optval, + sizeof (optval)) < 0) +#endif { fprintf (stderr, "setsocket failed %s\n", strerror (errno)); - close (packet); + CLOSESOCKET(packet); return (-1); } @@ -208,17 +264,17 @@ int Wol::doWakeUp() *ptr++ = ethaddr [i]; /* Send the packet out */ - if (sendto (packet, buf, 102, 0, (struct sockaddr *)&sap, sizeof (sap)) < 0) + if (sendto (packet,(char*) buf, 102, 0, (struct sockaddr *)&sap, sizeof (sap)) < 0) { fprintf (stderr, " sendto failed, %s\n", strerror(errno)); - close (packet); + CLOSESOCKET(packet); return (-1); } logger->log("Wol", Log::NOTICE, "Send wakeonlan to server"); - close (packet); + CLOSESOCKET(packet); return (0); } diff --git a/woptionbox.cc b/woptionbox.cc index 76a0101..24edb24 100644 --- a/woptionbox.cc +++ b/woptionbox.cc @@ -21,7 +21,9 @@ #include "woptionbox.h" #include "colour.h" +#ifndef WIN32 #include "unistd.h" +#endif WOptionBox::WOptionBox() { @@ -186,25 +188,25 @@ void WOptionBox::setSelected(int toSelect) bool WOptionBox::mouseMove(int x, int y) { -/* - if ((x-offsetX)>=area.x && (y-offsetY)>=area.y - && (x-offsetX)<=area.w && (y-offsetY)<=area.h && !active) + + if ((x-getRootBoxOffsetX())>=0 && (y-getRootBoxOffsetY())>=0 + && (x-getRootBoxOffsetX())<=(int)area.w && (y-getRootBoxOffsetY())<=(int)area.h && !active) { setActive(1); return true; } - */ + return false; } bool WOptionBox::mouseLBDOWN(int x, int y) { -/* - if ((x-offsetX)>=area.x && (y-offsetY)>=area.y - && (x-offsetX)<=area.w && (y-offsetY)<=area.h && active) + + if ((x-getRootBoxOffsetX())>=0 && (y-getRootBoxOffsetY())>=0 + && (x-getRootBoxOffsetX())<=(int)area.w && (y-getRootBoxOffsetY())<=(int)area.h && active) { return true; } - */ + return false; } diff --git a/woptionpane.cc b/woptionpane.cc index 3b3e109..e54ac46 100644 --- a/woptionpane.cc +++ b/woptionpane.cc @@ -105,6 +105,15 @@ void WOptionPane::addOptionLine(Option* option) } +void WOptionPane::deactivateAllControls() +{ + if (selectedOption >= 0) { + optionBoxes[selectedOption]->setActive(0); + selectedOption = -1; + } +} + + int WOptionPane::handleCommand(int command) { switch(command) @@ -164,6 +173,40 @@ int WOptionPane::handleCommand(int command) return 0; } +bool WOptionPane::mouseMove(int x, int y) +{ + UINT i; + for (i=0;imouseMove(x,y)) { + if ( selectedOption!=(int)i) { + if (selectedOption != -1 ) optionBoxes[selectedOption]->setActive(0); + selectedOption=i; + return true; + } else { + return false; + } + } + } + + return false; +} + +bool WOptionPane::mouseLBDOWN(int x, int y) +{ + UINT i; + for (i=0;imouseLBDOWN(x,y)) { + if ( selectedOption==(int)i) { + optionBoxes[selectedOption]->cycle(); + return true; + } else { + return false; + } + } + } + return false; +} + diff --git a/woptionpane.h b/woptionpane.h index 1120c8c..6ccca1d 100644 --- a/woptionpane.h +++ b/woptionpane.h @@ -38,6 +38,9 @@ class WOptionPane : public Boxx int handleCommand(int command); void saveOpts(); void draw(); + void deactivateAllControls(); + bool mouseMove(int x, int y); + bool mouseLBDOWN(int x, int y); private: int numOptions; diff --git a/wremoteconfig.cc b/wremoteconfig.cc index cbda1d9..147c56d 100644 --- a/wremoteconfig.cc +++ b/wremoteconfig.cc @@ -24,6 +24,7 @@ #include "wsymbol.h" #include "colour.h" #include "i18n.h" +#include "boxstack.h" WRemoteConfig::WRemoteConfig() { @@ -98,6 +99,26 @@ void WRemoteConfig::draw() } } +bool WRemoteConfig::mouseLBDOWN(int x, int y) +{ + if (sl.mouseLBDOWN(x,y)) + { + BoxStack::getInstance()->handleCommand(Remote::OK); //simulate OK press + return true; + } + return false; +} + +bool WRemoteConfig::mouseMove(int x, int y) +{ + if (sl.mouseMove(x,y)) + { + sl.setShowSelOption(true); + sl.draw(); + return true; + } + return false; +} /* void WRemoteConfig::processMessage(Message* m) { diff --git a/wremoteconfig.h b/wremoteconfig.h index 37c1823..5d74205 100644 --- a/wremoteconfig.h +++ b/wremoteconfig.h @@ -32,6 +32,9 @@ class WRemoteConfig : public Boxx public: WRemoteConfig(); ~WRemoteConfig(); + + bool mouseMove(int x, int y); + bool mouseLBDOWN(int x, int y); void setSize(UINT w, UINT h); int handleCommand(int command); diff --git a/wsymbol.cc b/wsymbol.cc index 863b01e..b736268 100644 --- a/wsymbol.cc +++ b/wsymbol.cc @@ -873,3 +873,13 @@ void WSymbol::draw() } } } + +bool WSymbol::mouseLBDOWN(int x, int y) +{ + if ((x-getRootBoxOffsetX())>=0 && (y-getRootBoxOffsetY())>=0 + && (x-getRootBoxOffsetX())<=32&& (y-getRootBoxOffsetY())<=32) + { + return true; + } + return false; +} diff --git a/wsymbol.h b/wsymbol.h index 364ef68..4cd732f 100644 --- a/wsymbol.h +++ b/wsymbol.h @@ -33,6 +33,8 @@ class WSymbol : public Boxx UCHAR nextSymbol; Colour nextColour; + bool mouseLBDOWN(int x, int y); + const static UCHAR VOLUME = 0; const static UCHAR TEST = 1; const static UCHAR TEST2 = 2; diff --git a/wtabbar.cc b/wtabbar.cc index ef54b9b..2a1b06b 100644 --- a/wtabbar.cc +++ b/wtabbar.cc @@ -46,6 +46,7 @@ WTabBar::~WTabBar() for (UINT i = 0; i < tabs.size(); i++) { delete tabs[i].button; + delete tabs[i].pane; //moved from vopts MR } } @@ -246,3 +247,57 @@ bool WTabBar::right() return true; } +bool WTabBar::mouseMove(int x, int y) { + if (tabs[visiblePane].pane->mouseMove(x,y)) { + if (buttonBarActive){ + buttonBarActive = false; + tabs[visiblePane].button->dim(); + symbolLeft.nextColour = Colour::BUTTONBACKGROUND; + symbolRight.nextColour = Colour::BUTTONBACKGROUND; + + } + draw(); + return true; + } + return false; +} + +bool WTabBar::mouseLBDOWN(int x, int y) { + UINT i; + for (i=0;igetVisible()) { + if (tabs[i].button->mouseMove(x,y)) { + tabs[visiblePane].button->setActive(false); + tabs[visiblePane].pane->setVisible(false); + tabs[visiblePane].pane->deactivateAllControls(); + visiblePane=i; + tabs[visiblePane].button->setActive(true); + tabs[visiblePane].pane->setVisible(true); + tabs[visiblePane].pane->deactivateAllControls(); + buttonBarActive = true; + draw(); + return true; + } + } + } + if (tabs[visiblePane].pane->mouseLBDOWN(x,y)) { + buttonBarActive = false; + tabs[visiblePane].button->dim(); + symbolLeft.nextColour = Colour::BUTTONBACKGROUND; + symbolRight.nextColour = Colour::BUTTONBACKGROUND; + draw(); + return true; + } + if (symbolLeft.mouseLBDOWN(x,y)) { + left(); + draw(); + return true; + } + if (symbolRight.mouseLBDOWN(x,y)) { + right(); + draw(); + return true; + } + return false; +} + diff --git a/wtabbar.h b/wtabbar.h index 3868309..0bbd294 100644 --- a/wtabbar.h +++ b/wtabbar.h @@ -43,6 +43,8 @@ class WTabBar : public Boxx ~WTabBar(); void addTab(const char* name, Boxx* boxx); int handleCommand(int command); + bool mouseMove(int x, int y) ; + bool mouseLBDOWN(int x, int y); private: bool left(); diff --git a/wwinaudiofilter.cc b/wwinaudiofilter.cc new file mode 100644 index 0000000..56e1a5f --- /dev/null +++ b/wwinaudiofilter.cc @@ -0,0 +1,238 @@ +/* + Copyright 2004-2007 Chris Tallon, Marten Richter + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "wwinaudiofilter.h" +#include "audiowin.h" +#include "i18n.h" +#include "remote.h" +#include "boxstack.h" + +WWinAudioFilter::WWinAudioFilter() +{ + add(&sl); + initSelectList(true); + sl.setShowSelOption(false); + sl.setPosition(15,30+15); +} + +WWinAudioFilter::~WWinAudioFilter() +{ + +} + +void WWinAudioFilter::initSelectList(bool startup) +{ + ULONG selection=0; + ULONG top=0; + if (!startup) + { + selection=sl.getCurrentOption(); + top=sl.getTopOption(); + + } + sl.addColumn(0); + + ULONG i; + AudioWin *aw=(AudioWin*) Audio::getInstance(); + int filselected; + const AudioFilterDescList *list=aw->getAudioFilterList(filselected); + for (i = 0; i < list->size();i++) + { + const char * name = (*list)[i].friendlyname; + if (name!=NULL) + { + char * desc=new char [strlen(name)+1]; + strcpy(desc,name); + sl.addOption(desc,i,0); + } + + } + if (!startup) + { + sl.hintSetCurrent(selection); + sl.hintSetTop(top); + } +} + +void WWinAudioFilter::setSize(UINT w, UINT h) +{ + Boxx::setSize(w, h); + sl.setSize(area.w - 240, area.h - 30-15-30); +} + +void WWinAudioFilter::draw() +{ + Boxx::draw(); + + drawText(tr("Selected Filter:"), 15, 15, Colour::LIGHTTEXT); + int filselected; + AudioWin *aw=(AudioWin*) Audio::getInstance(); + const AudioFilterDescList *list=aw->getAudioFilterList(filselected); + if (filselected!=-1) drawText((*list)[filselected].friendlyname,215,15,Colour::LIGHTTEXT); + sl.draw(); + +/* if (!(*list)[sl.getCurrentOptionData()].vmr9tested) + { + rectangle(area.w - 220, 160, 200, 20, Colour::YELLOW); + drawText(tr("VMR 9 support: ?"), area.w - 220, 160, Colour::DARKTEXT); + } + else if ((*list)[sl.getCurrentOptionData()].vmr9) + { + rectangle(area.w - 220, 160, 200, 20, Colour::GREEN); + drawText(tr("VMR 9 support: yes"), area.w - 220, 160, Colour::DARKTEXT); + } + else + { + rectangle(area.w - 220, 160, 200, 20, Colour::RED); + drawText(tr("VMR 9 support: no"), area.w - 220, 160, Colour::DARKTEXT); + } */ + + drawText(tr("Press [ok] to select filter! "), 15, area.h - 30, Colour::LIGHTTEXT); + +} + + +bool WWinAudioFilter::mouseLBDOWN(int x, int y) +{ + if (sl.mouseLBDOWN(x,y)) + { + BoxStack::getInstance()->handleCommand(Remote::OK); //simulate OK press + return true; + } + return false; +} + +bool WWinAudioFilter::mouseMove(int x, int y) +{ + if (sl.mouseMove(x,y)) + { + sl.setShowSelOption(true); + sl.draw(); + return true; + } + return false; +} +/* +void WWinAudioFilter::processMessage(Message* m) +{ + Log::getInstance()->log("VRecordingList", Log::DEBUG, "Got message value %lu", m->message); + + if (m->message == Message::MOUSE_MOVE) + { + if (sl.mouseMove((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + sl.setShowSelOption(true); + sl.draw(); + draw(); + viewman->updateView(this); + } + } + else if (m->message == Message::MOUSE_LBDOWN) + { + if (sl.mouseLBDOWN((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + ViewMan::getInstance()->handleCommand(Remote::OK); //simulate OK press + } + else + { + //check if press is outside this view! then simulate cancel + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (x<0 || y <0 || x>getWidth() || y>getHeight()) + { + ViewMan::getInstance()->handleCommand(Remote::BACK); //simulate cancel press + } + } + } + +}*/ + +/* +void WWinAudioFilter::doSave() +{ + Message* m = new Message(); + m->message = Message::CHANGED_DEVICEOPTIONS; + m->to = parent; + m->parameter = 0; + Command::getInstance()->postMessageNoLock(m); + +}*/ + + +int WWinAudioFilter::handleCommand(int command) +{ + + switch(command) + { + case Remote::DF_UP: + case Remote::UP: + { + if (sl.getCurrentOption() != 0) + { + sl.up(); + sl.setShowSelOption(true); + return 1; + } + else + { + sl.setShowSelOption(false); + return 4; //Control to vopts control + } + } + case Remote::DF_DOWN: + case Remote::DOWN: + { + Log::getInstance()->log("P", Log::DEBUG, "1"); + sl.down(); + sl.setShowSelOption(true); + return 1; + } + case Remote::SKIPBACK: + { + sl.pageUp(); + sl.draw(); + return 1; + } + case Remote::SKIPFORWARD: + { + sl.pageDown(); + sl.draw(); + return 1; + } + case Remote::OK: + { + AudioWin*aw=(AudioWin*)Audio::getInstance(); + aw->selectAudioFilter(sl.getCurrentOptionData()); + + return 1; + } + case Remote::BACK: + { + return 0; + + } + + + + } + // stop command getting to any more views + return 0; +} + diff --git a/wwinaudiofilter.h b/wwinaudiofilter.h new file mode 100644 index 0000000..fc0d02e --- /dev/null +++ b/wwinaudiofilter.h @@ -0,0 +1,56 @@ +/* + Copyright 2004-2005 Chris Tallon + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef WWINAUDIOFILTER_H +#define WWINAUDIOFILTER_H + +#include +#include +#include + + +#include "boxx.h" +#include "wselectlist.h" + +class WWinAudioFilter : public Boxx +{ + public: + WWinAudioFilter (); + ~WWinAudioFilter (); + + void setSize(UINT w, UINT h); + + int handleCommand(int command); + bool mouseMove(int x, int y) ; + bool mouseLBDOWN(int x, int y); + void draw(); + + + private: + WSelectList sl; + + void initSelectList(bool startup); + + + + +}; + +#endif diff --git a/wwinmp3audiofilter.cc b/wwinmp3audiofilter.cc new file mode 100644 index 0000000..24feabd --- /dev/null +++ b/wwinmp3audiofilter.cc @@ -0,0 +1,249 @@ +/* + Copyright 2004-2007 Chris Tallon, Marten Richter + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "wwinmp3audiofilter.h" +#include "audiowin.h" +#include "i18n.h" +#include "remote.h" +#include "boxstack.h" + +WWinMp3AudioFilter::WWinMp3AudioFilter() +{ + add(&sl); + initSelectList(true); + sl.setShowSelOption(false); + sl.setPosition(15,30+15); + + + +} + +WWinMp3AudioFilter::~WWinMp3AudioFilter() +{ + +} + +void WWinMp3AudioFilter::initSelectList(bool startup) +{ + ULONG selection=0; + ULONG top=0; + if (!startup) + { + selection=sl.getCurrentOption(); + top=sl.getTopOption(); + + } + sl.addColumn(0); + + ULONG i; + AudioWin *aw=(AudioWin*) Audio::getInstance(); + int filselected; + const AudioFilterDescList *list=aw->getMp3AudioFilterList(filselected); + for (i = 0; i < list->size();i++) + { + const char * name = (*list)[i].friendlyname; + if (name!=NULL) + { + char * desc=new char [strlen(name)+1]; + strcpy(desc,name); + sl.addOption(desc,i,0); + } + + } + if (!startup) + { + sl.hintSetCurrent(selection); + sl.hintSetTop(top); + } +} + +void WWinMp3AudioFilter::setSize(UINT w, UINT h) +{ + Boxx::setSize(w, h); + sl.setSize(area.w - 240, area.h - 30-15-30); +} + + +void WWinMp3AudioFilter::draw() +{ + Boxx::draw(); + + drawText(tr("Selected Filter:"), 15, 15, Colour::LIGHTTEXT); + int filselected; + AudioWin *aw=(AudioWin*) Audio::getInstance(); + const AudioFilterDescList *list=aw->getMp3AudioFilterList(filselected); + if (filselected!=-1) drawText((*list)[filselected].friendlyname,215,15,Colour::LIGHTTEXT); + sl.draw(); + +/* if (!(*list)[sl.getCurrentOptionData()].vmr9tested) + { + rectangle(area.w - 220, 160, 200, 20, Colour::YELLOW); + drawText(tr("VMR 9 support: ?"), area.w - 220, 160, Colour::DARKTEXT); + } + else if ((*list)[sl.getCurrentOptionData()].vmr9) + { + rectangle(area.w - 220, 160, 200, 20, Colour::GREEN); + drawText(tr("VMR 9 support: yes"), area.w - 220, 160, Colour::DARKTEXT); + } + else + { + rectangle(area.w - 220, 160, 200, 20, Colour::RED); + drawText(tr("VMR 9 support: no"), area.w - 220, 160, Colour::DARKTEXT); + } */ + + drawText(tr("Press [ok] to select filter! "), 15, area.h - 30, Colour::LIGHTTEXT); + + + + + +} + +bool WWinMp3AudioFilter::mouseLBDOWN(int x, int y) +{ + if (sl.mouseLBDOWN(x,y)) + { + BoxStack::getInstance()->handleCommand(Remote::OK); //simulate OK press + return true; + } + return false; +} + +bool WWinMp3AudioFilter::mouseMove(int x, int y) +{ + if (sl.mouseMove(x,y)) + { + sl.setShowSelOption(true); + sl.draw(); + return true; + } + return false; +} + +/* +void WWinMp3AudioFilter::processMessage(Message* m) +{ + Log::getInstance()->log("VRecordingList", Log::DEBUG, "Got message value %lu", m->message); + + if (m->message == Message::MOUSE_MOVE) + { + if (sl.mouseMove((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + sl.setShowSelOption(true); + sl.draw(); + draw(); + viewman->updateView(this); + } + } + else if (m->message == Message::MOUSE_LBDOWN) + { + if (sl.mouseLBDOWN((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + ViewMan::getInstance()->handleCommand(Remote::OK); //simulate OK press + } + else + { + //check if press is outside this view! then simulate cancel + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (x<0 || y <0 || x>getWidth() || y>getHeight()) + { + ViewMan::getInstance()->handleCommand(Remote::BACK); //simulate cancel press + } + } + } + +}*/ + + +/*void WWinMp3AudioFilter::doSave() +{ + Message* m = new Message(); + m->message = Message::CHANGED_DEVICEOPTIONS; + m->to = parent; + m->parameter = 0; + Command::getInstance()->postMessageNoLock(m); + +}*/ + + +int WWinMp3AudioFilter::handleCommand(int command) +{ + + switch(command) + { + case Remote::DF_UP: + case Remote::UP: + { + if (sl.getCurrentOption() != 0) + { + sl.up(); + sl.setShowSelOption(true); + return 1; + } + else + { + sl.setShowSelOption(false); + return 4; //Control to vpots control + } + } + case Remote::DF_DOWN: + case Remote::DOWN: + { + + sl.down(); + sl.setShowSelOption(true); + return 1; + } + case Remote::SKIPBACK: + { + sl.pageUp(); + sl.draw(); + + return 1; + } + case Remote::SKIPFORWARD: + { + sl.pageDown(); + sl.draw(); + + + return 1; + } + case Remote::OK: + { + AudioWin*aw=(AudioWin*)Audio::getInstance(); + aw->selectMp3AudioFilter(sl.getCurrentOptionData()); + + return 1; + } + case Remote::BACK: + { + return 0; + + } + + + + } + // stop command getting to any more views + return 0; +} +//#endif diff --git a/wwinmp3audiofilter.h b/wwinmp3audiofilter.h new file mode 100644 index 0000000..0ed051f --- /dev/null +++ b/wwinmp3audiofilter.h @@ -0,0 +1,54 @@ +/* + Copyright 2004-2005 Chris Tallon + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef WWINMP3AUDIOFILTER_H +#define WWINMP3AUDIOFILTER_H + +#include +#include +#include + + +#include "boxx.h" +#include "wselectlist.h" + +class WWinMp3AudioFilter : public Boxx +{ + public: + WWinMp3AudioFilter (); + ~WWinMp3AudioFilter (); + + void setSize(UINT w, UINT h); + + int handleCommand(int command); + bool mouseMove(int x, int y) ; + bool mouseLBDOWN(int x, int y); + void draw(); + + + private: + WSelectList sl; + + void initSelectList(bool startup); + + +}; + +#endif diff --git a/wwinvideofilter.cc b/wwinvideofilter.cc new file mode 100644 index 0000000..283682d --- /dev/null +++ b/wwinvideofilter.cc @@ -0,0 +1,232 @@ +/* + Copyright 2004-2007 Chris Tallon, Marten Richter + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "wwinvideofilter.h" +#include "videowin.h" +#include "i18n.h" +#include "remote.h" +#include "boxstack.h" + +WWinVideoFilter::WWinVideoFilter() +{ + add(&sl); + initSelectList(true); + sl.setShowSelOption(false); + sl.setPosition(15,30+15); +} + +WWinVideoFilter::~WWinVideoFilter() +{ + +} + +void WWinVideoFilter::initSelectList(bool startup) +{ + ULONG selection=0; + ULONG top=0; + if (!startup) + { + selection=sl.getCurrentOption(); + top=sl.getTopOption(); + } + + sl.addColumn(0); + + ULONG i; + VideoWin *vw=(VideoWin*) Video::getInstance(); + int filselected; + const VideoFilterDescList *list=vw->getVideoFilterList(filselected); + for (i = 0; i < list->size();i++) + { + const char * name = (*list)[i].friendlyname; + if (name!=NULL) + { + char * desc=new char [strlen(name)+1]; + strcpy(desc,name); + sl.addOption(desc,i,0); + } + + } + if (!startup) + { + sl.hintSetCurrent(selection); + sl.hintSetTop(top); + } +} + +void WWinVideoFilter::setSize(UINT w, UINT h) +{ + Boxx::setSize(w, h); + sl.setSize(area.w - 240, area.h - 30-15-30); +} + +void WWinVideoFilter::draw() +{ + Boxx::draw(); + + drawText(tr("Selected Filter:"), 15, 15, Colour::LIGHTTEXT); + int filselected; + VideoWin *vw=(VideoWin*) Video::getInstance(); + const VideoFilterDescList *list=vw->getVideoFilterList(filselected); + if (filselected!=-1) drawText((*list)[filselected].friendlyname,215,15,Colour::LIGHTTEXT); + sl.draw(); + + if (!(*list)[sl.getCurrentOptionData()].vmr9tested) + { + rectangle(area.w - 220, 160, 200, 20, Colour::YELLOW); + drawText(tr("VMR 9 support: ?"), area.w - 220, 160, Colour::DARKTEXT); + } + else if ((*list)[sl.getCurrentOptionData()].vmr9) + { + rectangle(area.w - 220, 160, 200, 20, Colour::GREEN); + drawText(tr("VMR 9 support: yes"), area.w - 220, 160, Colour::DARKTEXT); + } + else + { + rectangle(area.w - 220, 160, 200, 20, Colour::RED); + drawText(tr("VMR 9 support: no"), area.w - 220, 160, Colour::DARKTEXT); + } + + drawText(tr("Press [ok] to select filter! "), 15, area.h - 30, Colour::LIGHTTEXT); + +} + +bool WWinVideoFilter::mouseLBDOWN(int x, int y) +{ + if (sl.mouseLBDOWN(x,y)) + { + BoxStack::getInstance()->handleCommand(Remote::OK); //simulate OK press + return true; + } + return false; +} + +bool WWinVideoFilter::mouseMove(int x, int y) +{ + if (sl.mouseMove(x,y)) + { + sl.setShowSelOption(true); + sl.draw(); + return true; + } + return false; +} + +/* +void WWinVideoFilter::processMessage(Message* m) +{ + Log::getInstance()->log("VRecordingList", Log::DEBUG, "Got message value %lu", m->message); + + if (m->message == Message::MOUSE_MOVE) + { + if (sl.mouseMove((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + sl.setShowSelOption(true); + sl.draw(); + draw(); + viewman->updateView(this); + } + } + else if (m->message == Message::MOUSE_LBDOWN) + { + if (sl.mouseLBDOWN((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY())) + { + ViewMan::getInstance()->handleCommand(Remote::OK); //simulate OK press + } + else + { + //check if press is outside this view! then simulate cancel + int x=(m->parameter>>16)-getScreenX(); + int y=(m->parameter&0xFFFF)-getScreenY(); + if (x<0 || y <0 || x>getWidth() || y>getHeight()) + { + ViewMan::getInstance()->handleCommand(Remote::BACK); //simulate cancel press + } + } + } + +}*/ + +/* +void WWinVideoFilter::doSave() +{ + Message* m = new Message(); + m->message = Message::CHANGED_DEVICEOPTIONS; + m->to = parent; + m->parameter = 0; + Command::getInstance()->postMessageNoLock(m); + +}*/ + + +int WWinVideoFilter::handleCommand(int command) +{ + + switch(command) + { + case Remote::DF_UP: + case Remote::UP: + { + if (sl.getCurrentOption() != 0) + { + sl.up(); + sl.setShowSelOption(true); + return 1; + } + else + { + sl.setShowSelOption(false); + return 4; //Control to vopts control + } + } + case Remote::DF_DOWN: + case Remote::DOWN: + { + sl.down(); + sl.setShowSelOption(true); + return 1; + } + case Remote::SKIPBACK: + { + sl.pageUp(); + return 1; + } + case Remote::SKIPFORWARD: + { + sl.pageDown(); + return 1; + } + case Remote::OK: + { + VideoWin*vw=(VideoWin*)Video::getInstance(); + vw->selectVideoFilter(sl.getCurrentOptionData()); + return 1; + } + case Remote::BACK: + { + return 0; + + } + + } + + return 0; +} + diff --git a/wwinvideofilter.h b/wwinvideofilter.h new file mode 100644 index 0000000..8c4ac3b --- /dev/null +++ b/wwinvideofilter.h @@ -0,0 +1,55 @@ +/* + Copyright 2004-2005 Chris Tallon + + This file is part of VOMP. + + VOMP 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. + + VOMP 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 VOMP; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef WWINVIDEOFILTER_H +#define WWINVIDEOFILTER_H + +#include +#include +#include + + +#include "boxx.h" +#include "wselectlist.h" + +class WWinVideoFilter : public Boxx +{ + public: + WWinVideoFilter (); + ~WWinVideoFilter (); + + void setSize(UINT w, UINT h); + + int handleCommand(int command); + bool mouseMove(int x, int y) ; + bool mouseLBDOWN(int x, int y); + void draw(); + + + private: + WSelectList sl; + + void initSelectList(bool startup); + + + +}; + +#endif -- 2.39.2