#vomp_options+= -DVOMP_HAS_EXIT
+
ifeq ($(vomp_platform),mvp)
$(info MVP crosscompiler)
include ../crosstool/cross-var
ifeq ($(vomp_platform),raspberry)
$(info Raspberry pi flags)
LDFLAGS = -Wall -Wl,--format=binary -Wl,other/vdrhires.jpg -Wl,other/wallpaper720p.jpg -Wl,--format=default
-LIBS = -L/opt/vc/lib -lpthread -lrt -lEGL -lOpenVG -lopenmaxil -lbcm_host -lavformat -lavcodec -lavutil
+LIBS = -L/opt/vc/lib -lpthread -lrt -lEGL -lOpenVG -lopenmaxil -lbcm_host -lavformat -lavcodec -lavutil -lavresample
OBJECTS += main.o threadp.o osdvector.o surfacevector.o osdopenvg.o ledraspberry.o mtdraspberry.o videoomx.o audioomx.o imageomx.o wjpegsimple.o remotelinux.o
-LIBS+= -lfreetype -lMagick++
+LIBS+= -ldl -lfontconfig -lfreetype -lMagick++
CROSSLIBS =
INCLUDES = -DVOMP_PLATTFORM_RASPBERRY -I/opt/vc/include -I/opt/vc/include/interface/vcos/pthreads -I/usr/include/freetype2 -I/usr/include/ImageMagick
CXXFLAGS_DEV += -D__STDC_CONSTANT_MACROS
ifeq ($(vomp_platform),crossraspberry)
$(info Raspberry pi flags cross compiler)
LDFLAGS = -Wall -Wl,--format=binary -Wl,other/vdrhires.jpg -Wl,other/wallpaper720p.jpg -Wl,--format=default -Wl,--verbose -Xlinker --rpath-link=rpi-root/usr/lib/arm-linux-gnueabihf -Xlinker --rpath-link=rpi-root/lib/arm-linux-gnueabihf -Xlinker --rpath-link=rpi-root/opt/vc/lib
-LIBS = -Lrpi-root/opt/vc/lib -Lrpi-root/lib -Lrpi-root/usr/lib -Lrpi-root/lib/arm-linux-gnueabihf -Lrpi-root/usr/lib/arm-linux-gnueabihf -Lrpi-root/usr/local/lib -lpthread -lrt -lEGL -lOpenVG -lopenmaxil -lbcm_host -lavformat -lavcodec -lavutil -ldl -lfontconfig
+LIBS = -Lrpi-root/opt/vc/lib -Lrpi-root/lib -Lrpi-root/usr/lib -Lrpi-root/lib/arm-linux-gnueabihf -Lrpi-root/usr/lib/arm-linux-gnueabihf -Lrpi-root/usr/local/lib -lpthread -lrt -lEGL -lOpenVG -lopenmaxil -lbcm_host -lavformat -lavcodec -lavutil -lavresample -ldl -lfontconfig
OBJECTS += main.o threadp.o osdvector.o surfacevector.o osdopenvg.o ledraspberry.o mtdraspberry.o videoomx.o audioomx.o imageomx.o wjpegsimple.o remotelinux.o
-LIBS+= -lfreetype -lMagick++
+LIBS+= -lfreetype -lMagick++
CROSSLIBS =
INCLUDES = -DVOMP_PLATTFORM_RASPBERRY -Irpi-root/opt/vc/include -Irpi-root/opt/vc/include/interface/vcos/pthreads -Irpi-root/usr/include -Irpi-root/usr/include/freetype2 -Irpi-root/usr/include/ImageMagick
CXXFLAGS_DEV += -D__STDC_CONSTANT_MACROS -mfloat-abi=hard
#include "osdopenvg.h"
#include <bcm_host.h>
+extern "C" {
+#include "libavutil/channel_layout.h"
+#include "libavutil/opt.h"
+}
+
AudioOMX::AudioOMX()
{
initted = 0;
mp23codec_libav=NULL;
mp23codec_context_libav=NULL;
-#ifdef USE_LIBRESAMPLE
+
resam_con_libav=NULL;
-#endif
+
+
decompress_buffer=NULL;
decompress_buffer_size=0;
libav_mutex.Unlock();
return 0;
}
-#ifdef USE_LIBRESAMPLE
+
resam_con_libav = avresample_alloc_context();
if (resam_con_libav == NULL) {
Log::getInstance()->log("Audio", Log::DEBUG,
av_opt_set_int(resam_con_libav, "out_channel_layout", AV_CH_LAYOUT_STEREO, 0); // our standard format
av_opt_set_int(resam_con_libav, "out_sample_rate",48000,0);
av_opt_set_int(resam_con_libav, "out_sample_fmt",AV_SAMPLE_FMT_S16,0);
+ av_opt_set_int(resam_con_libav, "matrix_encoding",AV_MATRIX_ENCODING_DPLII,0);
av_opt_set_int(resam_con_libav, "in_sample_rate",48000,0);
av_opt_set_int(resam_con_libav, "in_sample_fmt",AV_SAMPLE_FMT_S16,0);
av_opt_set_int(resam_con_libav, "in_channel_layout", AV_CH_LAYOUT_5POINT1, 0); //just an example
-#endif
+
av_init_packet(&incoming_paket_libav);
decode_frame_libav=avcodec_alloc_frame();
avcodec_close(mp23codec_context_libav);
av_free(mp23codec_context_libav);
mp23codec_context_libav = NULL;
-#ifdef USE_LIBRESAMPLE
- avresample_free(resam_con_libav);
+
+ avresample_free(&resam_con_libav);
resam_con_libav=NULL;
-#endif
+
}
libav_mutex.Unlock();
}
return size;
}
-#ifndef USE_LIBRESAMPLE
-#define SQRT3_2 1.22474487139158904909
-void AudioOMX::getDownMixMatrix(unsigned long long channels,
- int *left_mat,int *right_mat)
-{
- int i,j;
- double downmix_matrix[2][64];
- for (i=0;i<64;i++) {
- for (j=0;j<2;j++) {
- downmix_matrix[j][i]=0.;
- }
- }
- downmix_matrix[0/*links*/][/*FRONT_LEFT*/0]=1.;
- downmix_matrix[1/*rechts*/][/*FRONT_RIGHT*/1]=1.;
- downmix_matrix[0/*links*/] [/*FRONT_CENTER*/2] = M_SQRT1_2;
- downmix_matrix[1/*rechts*/] [/*FRONT_CENTER*/2] = M_SQRT1_2;
-
- if (channels & (AV_CH_BACK_LEFT | AV_CH_SIDE_LEFT) ) {
- downmix_matrix[0/*links*/][/*BACK_CENTER*/8]=-M_SQRT1_2*M_SQRT1_2;
- downmix_matrix[1/*rechts*/][/*BACK_CENTER*/8]=M_SQRT1_2*M_SQRT1_2;
- } else {
- downmix_matrix[0/*links*/][/*BACK_CENTER*/8]=-M_SQRT1_2;
- downmix_matrix[1/*rechts*/][/*BACK_CENTER*/8]=M_SQRT1_2;
- }
- downmix_matrix[0/*links*/][/*BACK_LEFT*/4 ]=-M_SQRT1_2*SQRT3_2;
- downmix_matrix[1/*rechts*/][/*BACK_LEFT*/4]=M_SQRT1_2*M_SQRT1_2;
- downmix_matrix[0/*links*/][/*BACK_RIGHT*/5 ]=-M_SQRT1_2*M_SQRT1_2;
- downmix_matrix[1/*rechts*/][/*BACK_RIGHT*/5]=M_SQRT1_2*SQRT3_2;
- downmix_matrix[0/*links*/][/*SIDE_LEFT*/9 ]=-M_SQRT1_2*SQRT3_2;
- downmix_matrix[1/*rechts*/][/*SIDE_LEFT*/9]=M_SQRT1_2*M_SQRT1_2;
- downmix_matrix[0/*links*/][/*SIDE_RIGHT*/10 ]=-M_SQRT1_2*M_SQRT1_2;
- downmix_matrix[1/*rechts*/][/*SIDE_RIGHT*/10]=M_SQRT1_2*SQRT3_2;
- downmix_matrix[0/*links*/][/*FRONT_LEFT_OF_CENTER*/6]=1.;
- downmix_matrix[1/*rechts*/][/*FRONT_RIGHT_OF_CENTER*/7]=1.;
- downmix_matrix[0/*links*/][/*LOW_FREQUENCY*/3]=M_SQRT1_2;
- downmix_matrix[1/*rechts*/][/*LOW_FREQUENCY*/3]=M_SQRT1_2;
-
- for (i=0,j=0;i<64;i++) {
- if ((1ULL << i)& channels) {
- left_mat[j]=(int)(downmix_matrix[0][i]*(1<<16));
- right_mat[j]=(int)(downmix_matrix[1][i]*(1<<16));
- j++;
- }
- }
-}
-
-#endif
void AudioOMX::PrepareMediaSample(const MediaPacketList& mplist,UINT samplepos)
{
int dsize = av_samples_get_buffer_size(NULL,
/*current_context->channels*/2, decode_frame_libav->nb_samples,
- current_context->sample_fmt, 1);
+ AV_SAMPLE_FMT_S16, 1);
int dsize_in = av_samples_get_buffer_size(NULL,
current_context->channels, decode_frame_libav->nb_samples,
current_context->sample_fmt, 1);
}
//Log::getInstance()->log("Audio", Log::DEBUG,"memcpy in %d %d %d" ,dsize,current_context->sample_rate,cur_input_buf_omx->nFilledLen);
- if (current_context->channels==2) {
- memcpy(cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen,
- decode_frame_libav->data[0], dsize);
- }
-#ifndef USE_LIBRESAMPLE
- else if (current_context->channels==1) { //convert to stereo
- short* startbuffer=(short* )decode_frame_libav->data[0];
- short* endbuffer=(short* )(decode_frame_libav->data[0]+dsize/2);
- short* destbuffer=(short* )(cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen);
- while (startbuffer!=endbuffer) {
- unsigned short temp=*startbuffer;
- *destbuffer=temp;
- destbuffer++;
- *destbuffer=temp;
- destbuffer++;
- startbuffer++;
- }
- } else {
- unsigned int channels=current_context->channels;
- int left_mat[channels];
- int right_mat[channels];
- getDownMixMatrix(current_context->channel_layout,left_mat,right_mat);
-
- short* startbuffer=(short* )decode_frame_libav->data[0];
- short* endbuffer=(short* )(decode_frame_libav->data[0]+dsize_in);
- short* destbuffer=(short* )(cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen);
- while (startbuffer!=endbuffer) {
- short* cur_buf=startbuffer;
- short* cur_buf_end=startbuffer+channels;
- int work1=0.;
- int work2=0.;
- int *mat1=left_mat;
- int *mat2=right_mat;
- while (cur_buf!=cur_buf_end) {
- work1+= ((*mat1)*(*cur_buf));
- work2+= ((*mat2)*(*cur_buf));
- cur_buf++;
- mat1++;
- mat2++;
- }
- *destbuffer=work1>>16;
- destbuffer++;
- *destbuffer=work2>>16;
- destbuffer++;
- startbuffer+=channels;
- }
- }
-#else
- else {
- //untested for future use
- av_opt_set_int(resam_con_libav, "in_sample_rate",current_context->sample_rate,0);
- av_opt_set_int(resam_con_libav, "in_sample_fmt",current_context->sample_fmt,0);
- av_opt_set_int(resam_con_libav, "in_channel_layout",current_context->channel_layout, 0);
- int ret=avresample_open(resam_con_libav);
- if (ret<0) {
- Log::getInstance()->log("Audio", Log::ERR,"Opening AV resample failed %d",ret);
- } else {
- avresample_convert(resam_con_libav, cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen,
- dsize, decode_frame_libav->nb_samples,
- decode_frame_libav->data[0], dsize_in, decode_frame_libav->nb_samples);
- avresample_close(resam_con_libav);
- }
+ av_opt_set_int(resam_con_libav, "in_sample_rate",decode_frame_libav->sample_rate,0);
+ av_opt_set_int(resam_con_libav, "in_sample_fmt",decode_frame_libav->format,0);
+ av_opt_set_int(resam_con_libav, "in_channel_layout",decode_frame_libav->channel_layout, 0);
+ //Log::getInstance()->log("Audio", Log::ERR,"AV resampledata %d %d %d %d",current_context->channels,current_context->sample_rate,current_context->sample_fmt,current_context->channel_layout);
+ //Log::getInstance()->log("Audio", Log::ERR,"AV resampledata2 %d %d %d",decode_frame_libav->sample_rate,decode_frame_libav->format,decode_frame_libav->channel_layout);
+ int ret=avresample_open(resam_con_libav);
+ if (ret<0) {
+ Log::getInstance()->log("Audio", Log::ERR,"Opening AV resample failed %d",ret);
+ } else {
+ uint8_t *output=cur_input_buf_omx->pBuffer + cur_input_buf_omx->nFilledLen;
+
+ avresample_convert(resam_con_libav, &output,
+ dsize, decode_frame_libav->nb_samples,
+ decode_frame_libav->extended_data, decode_frame_libav->linesize[0], decode_frame_libav->nb_samples);
+ avresample_close(resam_con_libav);
}
-#endif
//Log::getInstance()->log("Audio", Log::DEBUG,"memcpy out");
cur_input_buf_omx->nFilledLen += dsize;
#include "audio.h"
#include "videoomx.h"
-//#define USE_LIBRESAMPLE // untested code for future use
extern "C" {
#include <libavcodec/avcodec.h>
#include <libavformat/avformat.h>
-#ifdef USE_LIBRESAMPLE
#include <libavresample/avresample.h>
-#endif
}
AVCodecContext *mp23codec_context_libav;
AVPacket incoming_paket_libav;
AVFrame *decode_frame_libav;
-#ifdef USE_LIBRESAMPLE
AVAudioResampleContext *resam_con_libav;
-#else
- void getDownMixMatrix(unsigned long long channels,int *left_mat,int *right_mat);
-#endif
+
UCHAR * decompress_buffer;
unsigned int decompress_buffer_size;
Section: unknown
Priority: extra
Maintainer: Marten Richter <marten.richter@freenet.de>
-Build-Depends: debhelper (>= 8.0.0), libcec-dev (>= 1.8.1), libraspberrypi-dev, libfreetype6-dev, libmagick++-dev, libavformat-dev, libavutil-dev, libavcodec-dev
+Build-Depends: debhelper (>= 8.0.0), libcec-dev (>= 1.8.1), libraspberrypi-dev, libfreetype6-dev, libmagick++-dev, libavformat-dev, libavutil-dev, libavcodec-dev, libavresample-dev
Standards-Version: 3.9.3
Homepage: www.loggytronic.com/vomp.php
Vcs-Git: http://git.vomp.tv/vompclient-raspi.git
Package: vompclient-raspi
Architecture: armhf
-Depends: ${shlibs:Depends}, ${misc:Depends}, libcec1 (>= 1.8.1), libraspberrypi-bin, libfreetype6, libmagick++5, libavformat53, libavutil51, libavcodec53
+Depends: ${shlibs:Depends}, ${misc:Depends}, libcec1 (>= 1.8.1), libraspberrypi-bin, libfreetype6, libmagick++5, libavformat54, libavutil51, libavcodec54, libavresample1
Description: vompclient for raspberry pi
This is the vompclient binary for the raspberry pi platform.
It connects to the server with the vdr software including
#include "seriesinfo.h"
#include "vdr.h"
+MovieInfo* Event::movieInfo = NULL;
+SeriesInfo* Event::seriesInfo = NULL;
+
Event::Event()
{
id = 0;
title = NULL;
subtitle = NULL;
description = NULL;
- movieInfo = NULL;
- seriesInfo = NULL;
+ index = -1;
+ movieID = 0;
+ seriesID =0;
}
Event::~Event()
if (title) delete[] title;
if (subtitle) delete[] subtitle;
if (description) delete[] description;
- if (movieInfo) delete movieInfo;
- if (seriesInfo) delete seriesInfo;
}
void Event::settitle(const char* s)
movieInfo = NULL;
seriesInfo = NULL;
- movieID = 0;
- seriesID =0;
- vdr->getScraperEventType(channelid, id, movieID, seriesID, episodeID);
- Log::getInstance()->log("Event", Log::DEBUG, "Got Scraper EventType %d %d, %d %d %d",
- id, channelid,
- movieID, seriesID, episodeID);
+
+ if (movieID == 0 && seriesID == 0) {
+ vdr->getScraperEventType(channelid, id, movieID, seriesID, episodeID);
+ Log::getInstance()->log("Event", Log::DEBUG, "Got Scraper EventType %d %d, %d %d %d",
+ id, channelid,
+ movieID, seriesID, episodeID);
+ }
if (!vdr->isConnected()) Command::getInstance()->connectionLost();
char* subtitle;
char* description;
- MovieInfo *movieInfo;
- SeriesInfo *seriesInfo;
+ int index;
+
+ static MovieInfo *movieInfo;
+ static SeriesInfo *seriesInfo;
int movieID;
int seriesID;
int episodeID;
-bool ImageOMX::decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem)
+unsigned char* ImageOMX::decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem)
{
- if (pictInfValid) return false; // does support only one image at a Time;
+ if (pictInfValid) return buffer; // does support only one image at a Time;
// Log::getInstance()->log("Image", Log::DEBUG,
// "decodePicture 1");
EGLPictureCreator * pictcreat =dynamic_cast<EGLPictureCreator*>(Osd::getInstance());
pthread_setcanceltype(oldcanceltype, NULL);
if (ret && freemem) free(buffer);
- return ret;
+ if (ret) return NULL;
+ else return buffer;
}
void init();
void shutdown();
- bool decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem);
+ unsigned char* decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem);
bool getDecodedPicture(struct OsdVector::PictureInfo& pict_inf);
void freeReference(void * ref);
demuxer.o demuxervdr.o demuxerts.o stream.o \
region.o colour.o boxstack.o boxx.o tbboxx.o \
vinfo.o vquestion.o vrecordinglist.o vrecordinglistclassic.o vrecordinglistadvanced.o vrecording.o \
- vepgsummary.o \
+ vepgsummary.o vepglistadvanced.o \
vmute.o vvolume.o vtimerlist.o vtimeredit.o vrecordingmenu.o \
vchannellist.o vwelcome.o vvideorec.o vepgsettimer.o \
vchannelselect.o vserverselect.o vconnect.o vepg.o vrecmove.o \
VGImage input=vgCreateImage(VG_A_8,command.param1, command.param2,
VG_IMAGE_QUALITY_NONANTIALIASED|
VG_IMAGE_QUALITY_FASTER|VG_IMAGE_QUALITY_BETTER);
+ //Log::getInstance()->log("OSD", Log::DEBUG, "Draw create palette %d %d %x %d",command.param1,command.param2,vgGetError(),input);
vgImageSubData(input,command.data,command.param1,
VG_A_8,0,0,command.param1, command.param2); // upload palettized image data
VGImage handle=vgCreateImage(VG_sRGBA_8888,command.param1, command.param2,
public:
MagickDecoder(OsdVector::PictureReader* treader): OsdVector::PictureDecoder(treader) {pictInfValid=false;};
- bool decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem);
+ unsigned char *decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem);
bool getDecodedPicture( struct OsdVector::PictureInfo& pict_inf);
bool pictInfValid;
};
-bool MagickDecoder::decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem)
+unsigned char * MagickDecoder::decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem)
{
- if (pictInfValid) return false; // does support only one image at a Time;
+ if (pictInfValid) return buffer; // does support only one image at a Time;
Image magicimage;
Blob *imageblob = new Blob();
-
+ Blob myblob;
try{
Log::getInstance()->log("MagickDecoder", Log::DEBUG, "decodePicture");
- Blob myblob;
+
if (freemem) myblob.updateNoCopy(buffer,length,Blob::MallocAllocator);
else myblob.update(buffer,length);
magicimage.read(myblob);
{
Log::getInstance()->log("MagickDecoder", Log::DEBUG, "Libmagick: %s",error_.what());
delete imageblob;
-
- return false;
+ Log::getInstance()->log("MagickDecoder", Log::DEBUG, "Libmagick: error mark2");
+ unsigned char* newbuffer=(unsigned char*) malloc(length);
+ memcpy(newbuffer,myblob.data(),length);
+ return newbuffer;
}
pictInf.reference = (void*) imageblob;
pictInf.width = magicimage.columns();
// I can handle everything, so the return value is always true
- return true;
+ return NULL;
}
void MagickDecoder::freeReference(void * ref)
{
//jpegs.clear();
styles.clear();
styles_ref.clear();
+ palettepics.clear();
tvmedias.clear();
loadindex_ref.clear();
} else ++litty;
}
+ list<ImageIndex>::iterator pitty=palettepics.begin();
+ while (pitty!=palettepics.end()) {
+ map<ImageIndex,int>::iterator curitty=images_ref.find((*pitty));
+ int count=(*curitty).second;
+ if (count==0) {
+ ImageIndex ref=(*curitty).first;
+ palettepics.erase(pitty++);
+ images_ref.erase(curitty++);
+ destroyImageRef(ref);
+ } else ++pitty;
+ }
+
map<pair<Colour*,unsigned int>,unsigned int>::iterator sitty=styles.begin();
while (sitty!=styles.end()) {
index = ((long long) tvmedia.getPrimaryID()) << 32LL;
reader.addStaticImage(tvmedia.getPrimaryID());
} break;
+ case 5:
+ index=VDR::getInstance()->loadTVMediaEventThumb(tvmedia);
+ break;
default:
index=VDR::getInstance()->loadTVMedia(tvmedia);
break;
{
ImageIndex image_handle;
image_handle=createImagePalette(width,height,image_data,palette_data);
+ palettepics.push_back(image_handle);
incImageRef(image_handle);
return image_handle;
}
ULONG length=vresp->getUserDataLength();
std::list<PictureDecoder*>::iterator itty=decoders.begin();
while (itty!=decoders.end()) {
- if ((*itty)->decodePicture(vresp->getStreamID(),
- userdata, length)){
+ userdata=(*itty)->decodePicture(vresp->getStreamID(), userdata, length);
+ if (!userdata){
decoded=true;
break;
}
itty++;
}
- if (!decoded ){
- free(vresp->getUserData());
+ if (!decoded && userdata ){
+ free(userdata);
}
}
//else osd->informPicture(vresp->getStreamID(), 0);
{
std::list<PictureDecoder*>::iterator itty=decoders.begin();
while (itty!=decoders.end()) {
- if ((*itty)->decodePicture(((long long) static_id) << 32LL,userdata, length, false)){
+ if (!(*itty)->decodePicture(((long long) static_id) << 32LL,userdata, length, false)){
decoded=true;
break;
}
virtual ~PictureDecoder() {};
// its is always guaranted, that after getDecodedPicture a call to decodePicture follows, if the return value was true;
- virtual bool decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem=true)=0;
+ virtual unsigned char * decodePicture(LoadIndex index, unsigned char * buffer, unsigned int length, bool freemem=true)=0;
virtual bool getDecodedPicture(struct PictureInfo& pict_inf)=0;
virtual void freeReference(void * ref)=0;
map<void *,ImageIndex> monobitmaps;
//map<string,ImageIndex> jpegs;
map<TVMediaInfo,ImageIndex> tvmedias;
+ list<ImageIndex> palettepics;
command_mutex.Lock();
ImageIndex image=0;
LoadIndex load_index=osd->getTVMediaRef(tvmedia,image);
+ if (width!=0 && height!=0) {
+ removeCommands(x,y,width,height);
+ }
if (image) {
//Log::getInstance()->log("SurfaceVector", Log::DEBUG, "TVMedia Add instru image %d %d", load_index,image);
commands.push_back(SVGCommand::PaintImage(x,y,width,height,image,0,corner));
tw*=scalex;
th*=scaley;
SVGCommand temp=SVGCommand::PaintImage(tx,ty,tw,th,image,0);
+ removeCommands(tx,ty,tw,th);
commands.push_back(temp);
command_mutex.Unlock();
}
command_mutex.Lock();
ImageIndex image=osd->getMonoBitmapRef(base,width,height);
unsigned int ref=osd->getStyleRef(nextColour);
+ removeCommands(dx,dy,width,height);
commands.push_back(SVGCommand::PaintImage(dx,dy,height,width,image,ref));
command_mutex.Unlock();
}
while (itty!=commands.end())
{
if ((*itty).Test(x,y,width,height) && (*itty).instr != DrawClipping) {
+ //Log::getInstance()->log("OSD", Log::DEBUG, "Remove command %d %g %g %g %g %d %d",(*itty).instr,
+ //(*itty).x,(*itty).y,(*itty).w,(*itty).h,(*itty).reference,(*itty).target.image);
osd->removeStyleRef((*itty).getRef()); // We remove the Style reference, so that osd can free stuff
ImageIndex ii=(*itty).getImageIndex();
if (ii) osd->removeImageRef(ii);
primary_id=jpeg_index;
}
+void TVMediaInfo::setPosterThumb(int channel, int eventid)
+{
+ type=5;
+ primary_id=channel;
+ secondary_id=eventid;
+}
+
+void TVMediaInfo::setChannelLogo(int channel)
+{
+ type=6;
+ primary_id=channel;
+}
+
bool operator<(const TVMediaInfo& rhs, const TVMediaInfo& lhs)
{
if (rhs.type==lhs.type) {
void setMovieInfo(const MovieInfo * mi);
void setSeriesInfo(const SeriesInfo * si);
void setPosterThumb(const char* recname);
+ void setPosterThumb(int channel, int eventid);
+ void setChannelLogo(int channel);
void setDefaultJpeg(int jpeg_index);
int getType() {return type;};
int getPrimaryID() {return primary_id;};
+ int getSecondaryID() {return secondary_id;};
private:
int type; // 1 movie or 2 series or 3 unknown recording or 4 static artwork
VDR_ResponsePacket* vresp = RequestResponse(&vrp);
if (vresp->noResponse()) { delete vresp; return NULL; }
-
+
// received a ulong(0) - schedules error in the plugin
if (vresp->serverError())
{
VEpg* VEpg::instance = NULL;
-VEpg::VEpg(void* tparent, UINT tcurrentChannelIndex, ULONG streamType)
+VEpg::VEpg(void* tparent, UINT tcurrentChannelIndex, ChannelList* tchanList)
{
instance = this;
currentChannelIndex = tcurrentChannelIndex;
boxstack = BoxStack::getInstance();
parent = tparent;
eventList = NULL;
- chanList = VDR::getInstance()->getChannelsList(streamType); //TODO want to be able to display video and radio together
+ chanList = tchanList;
e = 0;
eventLista.resize(gridRows);
if(listTop + listIndex >= UINT(chanListbox.getBottomOption()))
continue;
chan = (*chanList)[listTop + listIndex];
+ if (eventLista[listIndex])
+ {
+ (eventLista)[listIndex]->clear();
+ delete eventLista[listIndex];
+ }
eventLista[listIndex] = VDR::getInstance()->getChannelSchedule(chan->number, ltime - 1, window_width * 60 + 2); // ltime - 1 to get prog before window (allows cursor left past ltime). + 2 to get prog after window
}
}
class VEpg : public Boxx, public TimerReceiver
{
public:
- VEpg(void* parent, UINT currentChannel, ULONG streamType);
+ VEpg(void* parent, UINT currentChannel, ChannelList* tchanList);
~VEpg();
static VEpg* getInstance();
--- /dev/null
+/*
+ Copyright 2004-2007 Chris Tallon, 2014 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+*/
+
+#include "vepglistadvanced.h"
+
+#include "boxstack.h"
+#include "remote.h"
+#include "wsymbol.h"
+#include "boxstack.h"
+#include "vdr.h"
+#include "colour.h"
+#include "video.h"
+#include "i18n.h"
+#include "command.h"
+#include "log.h"
+#include "movieinfo.h"
+#include "seriesinfo.h"
+#include "event.h"
+#include "channel.h"
+#include "vepgsummary.h"
+#include "vepgsettimer.h"
+#include "vepg.h"
+
+#include <sstream>
+
+
+VEpgListAdvanced::VEpgListAdvanced(VVideoLiveTV *tvideolive, ChannelList* tchanList,ULONG initialChannelNumber)
+{
+ channelNumber = initialChannelNumber;
+ chanList = tchanList;
+ videolive = tvideolive;
+ boxstack = BoxStack::getInstance();
+
+ mode = OneChannel;
+
+ setSize(640, 500); //old setSize(570, 420);
+ createBuffer();
+
+ setPosition(40, 40);
+
+ setTitleBarOn(1);
+ setTitleBarColour(DrawStyle::TITLEBARBACKGROUND);
+
+ sl.setPosition(10, 30 + 5);
+ sl.setSize(area.w*42/100 - 20, area.h - 30 - 15 - 30);
+ sl.setLinesPerOption(2.4f);
+ add(&sl);
+
+ Region slarea=sl.getRegionR();
+
+ epg.setParaMode(true);
+ epg.setPosition(slarea.x +slarea.w+10 ,30+5);
+ epg.setSize(area.w -slarea.x -slarea.w -10, area.h - 30 - 15 - 30);
+ add(&epg);
+ epg.setText("");
+ epg.setBackgroundColour(DrawStyle::VIEWBACKGROUND);
+
+ epgTVmedia.setPosition(epg.getRegionR().w-100-10,10);
+ epgTVmedia.setSize(100,150/Osd::getInstance()->getPixelAspect());
+ epg.add(&epgTVmedia);
+
+ boxRed.setBackgroundColour(DrawStyle::RED);
+ boxRed.setPosition(165 /*54*/, sl.getY2()+8);
+ boxRed.setSize(18, 16);
+ add(&boxRed);
+
+ textRed.setPosition(boxRed.getX2(), sl.getY2()+4);
+ textRed.setSize(116, 30);
+
+ add(&textRed);
+
+ boxGreen.setBackgroundColour(DrawStyle::GREEN);
+ boxGreen.setPosition(165 +1*110, sl.getY2()+8);
+ boxGreen.setSize(18, 16);
+ add(&boxGreen);
+
+ textGreen.setPosition(boxGreen.getX2(), sl.getY2()+4);
+ textGreen.setSize(116, 30);
+ add(&textGreen);
+
+ boxYellow.setBackgroundColour(DrawStyle::YELLOW);
+ boxYellow.setPosition(165 +2*110, sl.getY2()+8);
+ boxYellow.setSize(18, 16);
+ add(&boxYellow);
+
+ textYellow.setPosition(boxYellow.getX2(), sl.getY2()+4);
+ textYellow.setSize(116, 30);
+ add(&textYellow);
+
+ boxBlue.setBackgroundColour(DrawStyle::BLUE);
+ boxBlue.setPosition(165 +3*110, sl.getY2()+8);
+ boxBlue.setSize(18, 16);
+ add(&boxBlue);
+
+ textBlue.setPosition(boxBlue.getX2(), sl.getY2()+4);
+ textBlue.setSize(116, 30);
+ add(&textBlue);
+
+ setButtonText();
+
+
+ updateEpgDataChannel();
+}
+
+VEpgListAdvanced::~VEpgListAdvanced()
+{
+ clearEventList();
+}
+
+
+void VEpgListAdvanced::setButtonText()
+{
+ switch (mode)
+ {
+ case OneChannel: {
+ textRed.setText(tr("Record"));
+ textGreen.setText(tr("Now"));
+ textYellow.setText(tr("Next"));
+ textBlue.setText(tr("Guide"));
+
+ } break;
+ case Now: {
+ textRed.setText(tr("Record"));
+ textGreen.setText(tr("Next"));
+ textYellow.setText(tr("Schedule"));
+ textBlue.setText(tr("Switch"));
+ } break;
+ case Next: {
+ textRed.setText(tr("Record"));
+ textGreen.setText(tr("Now"));
+ textYellow.setText(tr("Schedule"));
+ textBlue.setText(tr("Switch"));
+ } break;
+
+ };
+}
+
+void VEpgListAdvanced::doRed()
+{
+ doRecord();
+}
+
+void VEpgListAdvanced::doGreen()
+{
+ switch (mode)
+ {
+ case Now: {
+ doNext();
+ } break;
+ case OneChannel:
+ case Next: {
+ doNow();
+ } break;
+ };
+}
+
+void VEpgListAdvanced::doYellow()
+{
+ switch (mode)
+ {
+ case OneChannel: {
+ doNext();
+ } break;
+ case Next:
+ case Now: {
+ doProgramm();
+ } break;
+ };
+}
+
+void VEpgListAdvanced::doBlue()
+{
+ switch (mode)
+ {
+ case OneChannel: {
+ doGrid();
+ } break;
+ case Next:
+ case Now: {
+ doSwitch();
+ } break;
+ };
+}
+
+void VEpgListAdvanced::doNext()
+{
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "doNext");
+ if (mode!=OneChannel) {
+ Channel * chan=(*chanList)[ sl.getCurrentOptionData()];
+ channelNumber = chan->number;
+ }
+ mode=Next;
+ updateEpgDataNowNext(true);
+ setButtonText();
+ draw(true);
+ boxstack->update(this);
+}
+void VEpgListAdvanced::doNow()
+{
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "doNow");
+ if (mode!=OneChannel) {
+ Channel * chan=(*chanList)[ sl.getCurrentOptionData()];
+ channelNumber = chan->number;
+ }
+ mode=Now;
+ updateEpgDataNowNext(true);
+ setButtonText();
+ draw(true);
+ boxstack->update(this);
+}
+
+void VEpgListAdvanced::doProgramm()
+{
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "doProgram");
+ mode=OneChannel;
+
+ Channel * chan=(*chanList)[ sl.getCurrentOptionData()];
+ channelNumber = chan->number;
+ updateEpgDataChannel();
+ setButtonText();
+ draw(true);
+ boxstack->update(this);
+}
+
+void VEpgListAdvanced::doSwitch()
+{
+
+ if (videolive)
+ {
+ if (mode!=OneChannel) {
+ Channel * chan=(*chanList)[ sl.getCurrentOptionData()];
+ channelNumber = chan->number;
+ }
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "doSwitch %d", channelNumber);
+ Message* m = new Message(); // Must be done after this view deleted
+ m->from = this;
+ m->to = videolive;
+ m->message = Message::CHANNEL_CHANGE;
+ m->parameter = channelNumber;
+ m->tag = 0;
+ Command::getInstance()->postMessageNoLock(m);
+ }
+}
+
+void VEpgListAdvanced::doRecord()
+{
+ int channel;
+ Event* current = getCurrentOptionEvent(channel);
+ if (current)
+ {
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "Found the option you pointed at. %s %d", current->title, current->id);
+ unsigned int chanlistsize=chanList->size();
+ Channel * chan;
+ UINT listIndex;
+ for(listIndex = 0; listIndex < chanlistsize; listIndex++)
+ {
+ chan = (*chanList)[listIndex];
+ if (chan->number == channel) break;
+ }
+
+ Log::getInstance()->log("VEpgSummary", Log::DEBUG, "ID %lu TIME %lu DURATION %lu TITLE %s", current->id, current->time,
+ current->duration, current->title);
+ VEpgSetTimer* vs = new VEpgSetTimer(current, chan);
+ vs->draw();
+ BoxStack *boxstack=BoxStack::getInstance();
+ boxstack->add(vs);
+ boxstack->update(vs);
+ }
+
+}
+
+void VEpgListAdvanced::doGrid()
+{
+ Video* video=Video::getInstance();
+ video->setMode(Video::QUARTER);
+ video->setPosition(170, 5); //TODO add stack for these changes
+ if (mode!=OneChannel) {
+ Channel * chan=(*chanList)[ sl.getCurrentOptionData()];
+ channelNumber = chan->number;
+ }
+
+ VEpg* vepg = new VEpg(videolive, channelNumber, chanList);
+ vepg->draw();
+ boxstack->add(vepg);
+ boxstack->update(vepg);
+
+}
+
+void VEpgListAdvanced::clearEventList()
+{
+ std::vector<EventList*>::iterator itty = eventLista.begin();
+ while (itty!= eventLista.end()) {
+ if (*itty) {
+ (*itty)->clear();
+ delete (*itty);
+ }
+ itty++;
+ }
+ eventLista.clear();
+
+}
+
+
+/* Prototype
+ *
+ * if (!chanList) return;
+ Channel* chan;
+ for(UINT listIndex = 0; listIndex < gridRows; listIndex++)
+ {
+ if(listTop + listIndex >= UINT(chanListbox.getBottomOption()))
+ continue;
+ chan = (*chanList)[listTop + listIndex];
+ eventLista[listIndex] = VDR::getInstance()->getChannelSchedule(chan->number, ltime - 1, window_width * 60 + 2); // ltime - 1 to get prog before window (allows cursor left past ltime). + 2 to get prog after window
+ }
+
+ */
+
+void VEpgListAdvanced::updateEpgData()
+{
+ switch (mode)
+ {
+ case OneChannel: {
+ //updateEpgDataChannel();
+ } break;
+ case Next:
+ case Now: {
+ updateEpgDataNowNext(false);
+ } break;
+ };
+
+}
+
+void VEpgListAdvanced::updateEpgDataNowNext(bool changeState)
+{
+ int startupdate=0;
+ int endupdate=0;
+
+ unsigned int chanlistsize=chanList->size();
+ if (changeState) {
+ clearEventList();
+ eventLista.resize(chanList->size());
+ Channel* chan;
+ for(UINT listIndex = 0; listIndex < chanlistsize; listIndex++)
+ {
+ if (listIndex < 0) continue;
+ if (listIndex >= chanlistsize) continue;
+ chan = (*chanList)[listIndex];
+ if (chan->number == channelNumber) {
+ startupdate = listIndex-sl.getNumOptionsDisplayable()-2;
+ endupdate = listIndex+sl.getNumOptionsDisplayable()+2;
+ break;
+ }
+ }
+ } else {
+ startupdate=sl.getTopOption()-2;
+ endupdate=sl.getBottomOption()+1;
+ }
+
+ time_t now;
+ time(&now);
+
+ Channel* chan;
+ for(int listIndex = startupdate; listIndex < endupdate; listIndex++)
+ {
+ if (listIndex < 0) continue;
+ if (listIndex >= chanlistsize) continue;
+
+ chan = (*chanList)[listIndex];
+ if (!eventLista[listIndex]) eventLista[listIndex] = VDR::getInstance()->getChannelSchedule(chan->number, now, 4 * 60 *60);
+
+ }
+
+}
+
+void VEpgListAdvanced::updateEpgDataChannel()
+{
+ clearEventList();
+ eventLista.resize(1);
+ time_t now;
+ time(&now);
+ eventLista[0] = VDR::getInstance()->getChannelSchedule(channelNumber, now, 24 * 60 *60 *30); // one month
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "Eventlist %x %d", eventLista[0],channelNumber);
+
+}
+
+void VEpgListAdvanced::drawData(bool doIndexPop)
+{
+ switch (mode)
+ {
+ case OneChannel: {
+ drawDataChannel(doIndexPop);
+ } break;
+ case Next: {
+ drawDataNowNext(true, doIndexPop);
+ } break;
+ case Now: {
+ drawDataNowNext(false, doIndexPop);
+ } break;
+ };
+
+}
+
+void VEpgListAdvanced::drawDataChannel(bool doIndexPop)
+{
+ int saveIndex = sl.getCurrentOption();
+ int saveTop = sl.getTopOption();
+ sl.clear();
+ sl.addColumn(0);
+ sl.addColumn(25 );
+ sl.addColumn(25 + 7);
+ //sl.addColumn(118);
+
+ int first = 1;
+
+ char tempA[300]; // FIXME this is guesswork!
+ char tempB[300]; // FIXME
+ char tempC[300]; // FIXME
+ struct tm* btime;
+
+
+
+ Event* currentEvent;
+ EventList::iterator j;
+ EventList* eventList = eventLista[0];
+ if (eventList) {
+ for (j = eventList->begin(); j != eventList->end(); j++)
+ {
+ currentEvent = *j;
+ time_t eventStartTime = (time_t)currentEvent->time;
+ time_t eventEndTime = (time_t)(currentEvent->time + currentEvent->duration);
+
+ btime = localtime(&eventStartTime);
+ strftime(tempA, 299, "%d/%m/%y %H:%M ", btime);
+ btime = localtime(&eventEndTime);
+ strftime(tempB, 299, "- %H:%M ", btime);
+ //#endif
+ sprintf(tempC, "%s\n \t%s%s", currentEvent->title,tempA,tempB);
+ // New TVMedia stuff
+ TVMediaInfo *info= new TVMediaInfo();
+ info->setPosterThumb(channelNumber, currentEvent->id);
+ currentEvent->index = sl.addOption(tempC, currentEvent->id, first, info);
+ first = 0;
+ }
+ }
+
+ if (doIndexPop)
+ {
+ sl.hintSetCurrent(0);
+ }
+ else
+ {
+ sl.hintSetCurrent(saveIndex);
+ sl.hintSetTop(saveTop);
+ }
+ updateSelection();
+ sl.draw();
+ epg.draw();
+}
+
+void VEpgListAdvanced::drawDataNowNext(bool next, bool doIndexPop)
+{
+ int saveIndex = sl.getCurrentOption();
+ int saveTop = sl.getTopOption();
+ sl.clear();
+ sl.addColumn(0);
+ sl.addColumn(25 );
+ sl.addColumn(160);
+
+ int first = 1;
+
+ char tempA[300]; // FIXME this is guesswork!
+ char tempB[300]; // FIXME
+ char tempC[300]; // FIXME
+ struct tm* btime;
+
+
+
+ Event* currentEvent;
+ EventList::iterator j;
+ int minevents=1;
+ if (next) minevents++;
+ int setcurrenthelper =0;
+
+ unsigned int chanlistsize=chanList->size();
+ for(UINT listIndex = 0; listIndex < chanlistsize; listIndex++)
+ {
+ Channel* chan;
+ chan = (*chanList)[listIndex];
+
+ EventList* eventList = eventLista[listIndex];
+ if (eventList && eventList->size()>=minevents) {
+ j = eventList->begin();
+
+ currentEvent = j[minevents-1];
+ time_t eventStartTime = (time_t)currentEvent->time;
+ time_t eventEndTime = (time_t)(currentEvent->time + currentEvent->duration);
+
+ btime = localtime(&eventStartTime);
+ strftime(tempA, 299, "%H:%M ", btime);
+ btime = localtime(&eventEndTime);
+ strftime(tempB, 299, "- %H:%M ", btime);
+ //#endif
+ sprintf(tempC, "%s\n%s\t %s%s", currentEvent->title, chan->name,tempA,tempB);
+
+ } else {
+ sprintf(tempC, "\n%s", chan->name);
+
+ }
+ TVMediaInfo *info= new TVMediaInfo();
+ if ((*chanList)[listIndex]->number == channelNumber) {
+ first = 1;
+ setcurrenthelper = listIndex;
+ }
+ info->setChannelLogo((*chanList)[listIndex]->number);
+ currentEvent->index = sl.addOption(tempC, listIndex, first, info);
+ first = 0;
+ }
+
+ if (doIndexPop)
+ {
+ sl.hintSetCurrent(setcurrenthelper);
+ }
+ else
+ {
+ sl.hintSetCurrent(saveIndex);
+ sl.hintSetTop(saveTop);
+ }
+ updateSelection();
+ sl.draw();
+ epg.draw();
+}
+
+void VEpgListAdvanced::draw(bool doIndexPop)
+{
+
+ // Single channel mode
+ switch (mode) {
+ case OneChannel: {
+ char tempA[300];
+ unsigned int chanlistsize=chanList->size();
+ Channel * chan;
+ UINT listIndex;
+ for(listIndex = 0; listIndex < chanlistsize; listIndex++)
+ {
+ chan = (*chanList)[listIndex];
+ if (chan->number == channelNumber) break;
+ }
+ sprintf(tempA, tr("Schedule - %s"), (*chanList)[listIndex]->name);
+ setTitleText(tempA);
+ } break;
+ case Now: {
+ setTitleText(tr("Now"));
+ } break;
+ case Next: {
+ setTitleText(tr("Next"));
+ } break;
+ };
+
+
+
+
+ TBBoxx::draw();
+
+
+ char freeSpace[50];
+ struct tm* btime;
+ time_t now;
+ time(&now);
+ btime = localtime(&now);
+ strftime(freeSpace, 299, "%d/%m/%y", btime);
+ drawTextRJ(freeSpace, 560+70, 5, DrawStyle::LIGHTTEXT);
+ // Symbols
+
+ WSymbol w;
+ TEMPADD(&w);
+ w.nextSymbol = WSymbol::UP;
+ w.setPosition(20, area.h-35);
+ w.draw();
+ w.nextSymbol = WSymbol::DOWN;
+ w.setPosition(50, area.h-35);
+ w.draw();
+ w.nextSymbol = WSymbol::SKIPBACK;
+ w.setPosition(85, area.h-35);
+ w.draw();
+ w.nextSymbol = WSymbol::SKIPFORWARD;
+ w.setPosition(115, area.h-35);
+ w.draw();
+
+ drawTextRJ(tr("[ok] = info"), 560+70, 385+80, DrawStyle::LIGHTTEXT);
+
+ // All static stuff done
+ drawData(doIndexPop);
+
+}
+
+Event* VEpgListAdvanced::getCurrentOptionEvent(int& channel)
+{
+ // version for channel
+ Event* currentEvent = NULL;
+ EventList::iterator j;
+ EventList* eventList = NULL;
+ switch (mode)
+ {
+ case OneChannel: {
+ eventList = eventLista[0];
+ if (eventList) {
+ channel = channelNumber;
+ for (j = eventList->begin(); j != eventList->end(); j++)
+ {
+ currentEvent = *j;
+ if (currentEvent->index == sl.getCurrentOption()) return currentEvent;
+ }
+
+
+ } break;
+ case Next: {
+ eventList = eventLista[sl.getCurrentOptionData()];
+ channel = (*chanList)[sl.getCurrentOptionData()]->number;
+
+
+ if (eventList && eventList->size()>1) {
+ j = eventList->begin();
+ currentEvent = j[1];
+ } else {
+ currentEvent = NULL;
+ }
+ } break;
+ case Now: {
+ eventList = eventLista[sl.getCurrentOptionData()];
+ channel = (*chanList)[sl.getCurrentOptionData()]->number;
+
+ if (eventList && eventList->size()>0) {
+ j = eventList->begin();
+ currentEvent = j[0];
+ } else {
+ currentEvent = NULL;
+ }
+ } break;
+ };
+
+
+ }
+ return currentEvent;
+}
+
+
+
+void VEpgListAdvanced::updateSelection()
+{
+ updateEpgData();
+ int channel=0;
+ Event* toShow = getCurrentOptionEvent(channel);
+ if (toShow)
+ {
+ toShow->loadinfos(channel);
+ std::stringstream description;
+
+ description << "\n"<< toShow->title << "\n\n";
+ description << toShow->subtitle <<"\n";
+ description << toShow->description;
+
+ TVMedia poster;
+ poster.height=0;
+ if (toShow->movieInfo) {
+ poster=toShow->movieInfo->poster;
+ }
+ if (toShow->seriesInfo) {
+ if (toShow->seriesInfo->seasonposter.height) {
+ poster=toShow->seriesInfo->seasonposter;
+ }
+ else if (toShow->seriesInfo->posters.size()) {
+ poster=toShow->seriesInfo->posters[0];
+ }
+ }
+ if (poster.height) {
+ epgTVmedia.setTVMedia(poster.info, WTVMedia::ZoomHorizontal);
+ epgTVmedia.setVisible(true);
+ } else {
+ epgTVmedia.setVisible(false);
+ }
+
+ epg.setText(description.str().c_str());
+ } else {
+ epg.setText("");
+ epgTVmedia.setVisible(false);
+ }
+
+}
+
+int VEpgListAdvanced::handleCommand(int command)
+{
+ switch(command)
+ {
+ case Remote::DF_UP:
+ case Remote::UP:
+ {
+ sl.up();
+ quickUpdate();
+
+ boxstack->update(this);
+ return 2;
+ }
+ case Remote::DF_DOWN:
+ case Remote::DOWN:
+ {
+ sl.down();
+ quickUpdate();
+
+ boxstack->update(this);
+ return 2;
+ }
+ case Remote::SKIPBACK:
+ {
+ sl.pageUp();
+ quickUpdate();
+
+ boxstack->update(this);
+ return 2;
+ }
+ case Remote::SKIPFORWARD:
+ {
+ sl.pageDown();
+ quickUpdate();
+
+ boxstack->update(this);
+ return 2;
+ }
+ case Remote::RED:
+ {
+ doRed();
+ return 2;
+ }
+ case Remote::GREEN:
+ {
+ doGreen();
+ return 2;
+ }
+ case Remote::YELLOW:
+ {
+ doYellow();
+ return 2;
+ }
+ case Remote::BLUE:
+ {
+ doBlue();
+ return 2;
+ }
+ case Remote::OK:
+ {
+ if (sl.getNumOptions() == 0) return 2;
+
+
+ int channel;
+ Event* current = getCurrentOptionEvent(channel);
+ if (current)
+ {
+ Log::getInstance()->log("VEventListAdvanced", Log::DEBUG, "Found the option you pointed at. %s %d", current->title, current->id);
+ unsigned int chanlistsize=chanList->size();
+ Channel * chan;
+ UINT listIndex;
+ for(listIndex = 0; listIndex < chanlistsize; listIndex++)
+ {
+ chan = (*chanList)[listIndex];
+ if (chan->number == channel) break;
+ }
+
+ VEpgSummary* vr = new VEpgSummary(current, (*chanList)[listIndex]);
+ vr->draw();
+ boxstack->add(vr);
+ boxstack->update(vr);
+
+ return 2;
+ }
+ // should not get to here
+ return 1;
+ }
+ case Remote::BACK:
+ {
+ return 4;
+ }
+ }
+ // stop command getting to any more views
+ return 1;
+}
+
+void VEpgListAdvanced::processMessage(Message* m)
+{
+ Log::getInstance()->log("VEpgListAdvanced", 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()))
+ {
+ quickUpdate();
+ boxstack->update(this);
+ }
+ }
+ else if (m->message == Message::MOUSE_LBDOWN)
+ {
+ if (sl.mouseLBDOWN((m->parameter>>16)-getScreenX(),(m->parameter&0xFFFF)-getScreenY()))
+ {
+ boxstack->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>(int)getWidth() || y>(int)getHeight())
+ {
+ boxstack->handleCommand(Remote::BACK); //simulate cancel press
+ }
+ }
+ }
+}
+
+
+
+void VEpgListAdvanced::quickUpdate() { //only quick for plattform that need it!
+ updateSelection();
+#ifdef GRADIENT_DRAWING
+ draw();
+#else
+ sl.draw();
+ epg.draw();
+#endif
+}
--- /dev/null
+/*
+ Copyright 2004-2005 Chris Tallon, 2014 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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+*/
+
+#ifndef VEPGLIST_ADVANCED_H
+#define VEPGLIST_ADVANCED_H
+
+
+#include <stack>
+
+#include "tbboxx.h"
+#include "wtextbox.h"
+#include "wselectlist.h"
+#include "wtvmedia.h"
+
+class BoxStack;
+class VVideoLiveTV;
+
+class VEpgListAdvanced : public TBBoxx
+{
+ public:
+ VEpgListAdvanced(VVideoLiveTV *tvideolive, ChannelList* tchanList, ULONG initialChannelNumber);
+ virtual ~VEpgListAdvanced();
+
+ void draw(bool doIndexPop = false);
+ bool load();
+ void drawData(bool doIndexPop = false);
+
+ protected:
+
+ enum EpgMode {
+ OneChannel,
+ Now,
+ Next
+ };
+
+ enum EpgMode mode;
+
+ void quickUpdate();
+ void updateSelection();
+
+ void setButtonText();
+
+ void clearEventList();
+
+ void updateEpgData();
+ void updateEpgDataChannel();
+ void updateEpgDataNowNext(bool changestate);
+ void drawDataChannel(bool doIndexPop);
+ void drawDataNowNext(bool next, bool doIndexPop);
+
+ int handleCommand(int command);
+ void processMessage(Message* m);
+
+ void doRed();
+ void doGreen();
+ void doYellow();
+ void doBlue();
+
+ void doNext();
+ void doNow();
+ void doProgramm();
+ void doSwitch();
+ void doRecord();
+ void doGrid();
+
+ WTextbox epg;
+ WTVMedia epgTVmedia;
+
+ BoxStack* boxstack;
+ bool loading;
+
+ WSelectList sl;
+
+ Event* getCurrentOptionEvent(int& channel);
+
+ ChannelList* chanList;
+ ULONG channelNumber;
+ VVideoLiveTV *videolive;
+
+ Boxx boxRed;
+ Boxx boxGreen;
+ Boxx boxYellow;
+ Boxx boxBlue;
+
+ WTextbox textRed;
+ WTextbox textGreen;
+ WTextbox textYellow;
+ WTextbox textBlue;
+
+ std::vector<EventList*> eventLista;
+
+
+
+};
+
+#endif
epgTVmedia.setSize(130,195/Osd::getInstance()->getPixelAspect());
summary->add(&epgTVmedia);
if (movieview) movieview->add(&epgTVmedia);
- if (seriesview) movieview->add(&epgTVmedia);
+ if (seriesview) seriesview->add(&epgTVmedia);
TVMedia poster;
poster.height=0;
if (event->movieInfo) {
#include "log.h"
#include "vteletextview.h"
#include "vepgsummary.h"
+#include "vepglistadvanced.h"
VVideoLiveTV::VVideoLiveTV(ChannelList* tchanList, ULONG initialChannelNumber, VChannelList* tvchannelList)
: osdBack(0, 0, 0, 128)
{
if (osd.getVisible()) clearScreen();
- video->setMode(Video::QUARTER);
- video->setPosition(170, 5); //TODO need to deal with 4:3 switching
+ if (!Command::getInstance()->advMenues()) {
+ video->setMode(Video::QUARTER);
+ video->setPosition(170, 5); //TODO need to deal with 4:3 switching
- VEpg* vepg = new VEpg(this, currentChannelIndex, streamType);
- vepg->draw();
- boxstack->add(vepg);
- boxstack->update(vepg);
+ VEpg* vepg = new VEpg(this, currentChannelIndex, chanList);
+ vepg->draw();
+ boxstack->add(vepg);
+ boxstack->update(vepg);
+ } else {
+ Channel* currentChannel = (*chanList)[osdChannelIndex];
+ VEpgListAdvanced *vepg= new VEpgListAdvanced(this, chanList, currentChannel->number);
+ vepg->draw();
+ boxstack->add(vepg);
+ boxstack->update(vepg);
+ }
}
void VVideoLiveTV::setNowNextData()
return options[selectedOption].data;
}
+int WSelectList::getNumOptionsDisplayable()
+{
+ return numOptionsDisplayable;
+}
+
bool WSelectList::mouseAndroidScroll(int x, int y,int sx, int sy)
{
/* int fontHeight = getFontHeight();
int getTopOption();
int getNumOptions();
int getBottomOption(); // actually returns bottom + 1 i.e. the one just past display ?!
+ int getNumOptionsDisplayable();
int getCurrentOption();
ULONG getCurrentOptionData();