mirror of
https://github.com/joel16/VitaShell.git
synced 2025-02-17 02:18:41 +00:00
Improved mp3 player.
This commit is contained in:
parent
7cc84caf9c
commit
45dfc6093d
2
Makefile
2
Makefile
@ -2,7 +2,7 @@ TITLE_ID = VITASHELL
|
||||
TARGET = VitaShell
|
||||
OBJS = main.o init.o io_process.o package_installer.o network_update.o context_menu.o archive.o photo.o audioplayer.o file.o text.o hex.o sfo.o \
|
||||
uncommon_dialog.o message_dialog.o ime_dialog.o config.o theme.o language.o utils.o sha1.o \
|
||||
minizip/unzip.o minizip/ioapi.o bm.o audio/vita_audio.o audio/id3.o audio/mp3player.o \
|
||||
minizip/unzip.o minizip/ioapi.o bm.o audio/vita_audio.o audio/player.o audio/id3.o audio/mp3player.o audio/mp3xing.o \
|
||||
libmad/bit.o libmad/decoder.o libmad/fixed.o libmad/frame.o \
|
||||
libmad/huffman.o libmad/layer12.o libmad/layer3.o \
|
||||
libmad/stream.o libmad/synth.o libmad/timer.o
|
||||
|
12
audio/id3.c
12
audio/id3.c
@ -322,10 +322,10 @@ void ParseID3v2_2(const char *mp3path, struct ID3Tag *id3tag)
|
||||
sceIoLseek(fp, 1, SCE_SEEK_CUR);
|
||||
sceIoLseek(fp, 5, SCE_SEEK_CUR);
|
||||
id3tag->ID3EncapsulatedPictureType = JPEG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 0x100);
|
||||
if (id3tag->ID3EncapsulatedPictureOffset < 0){
|
||||
id3tag->ID3EncapsulatedPictureType = PNG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 0x100);
|
||||
}
|
||||
tag_length = tag_length - (id3tag->ID3EncapsulatedPictureOffset - sceIoLseek(fp, 0, SCE_SEEK_CUR));
|
||||
id3tag->ID3EncapsulatedPictureLength = tag_length-6;
|
||||
@ -432,10 +432,10 @@ void ParseID3v2_3(const char *mp3path, struct ID3Tag *id3tag)
|
||||
sceIoLseek(fp, 1, SCE_SEEK_CUR);
|
||||
sceIoLseek(fp, 12, SCE_SEEK_CUR);
|
||||
id3tag->ID3EncapsulatedPictureType = JPEG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 0x100);
|
||||
if (id3tag->ID3EncapsulatedPictureOffset < 0){
|
||||
id3tag->ID3EncapsulatedPictureType = PNG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 0x100);
|
||||
}
|
||||
tag_length = tag_length - (id3tag->ID3EncapsulatedPictureOffset - sceIoLseek(fp, 0, SCE_SEEK_CUR));
|
||||
id3tag->ID3EncapsulatedPictureLength = tag_length-13;
|
||||
@ -535,10 +535,10 @@ void ParseID3v2_4(const char *mp3path, struct ID3Tag *id3tag)
|
||||
sceIoLseek(fp, 1, SCE_SEEK_CUR);
|
||||
sceIoLseek(fp, 12, SCE_SEEK_CUR);
|
||||
id3tag->ID3EncapsulatedPictureType = JPEG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchJPGstart(fp, 0x100);
|
||||
if (id3tag->ID3EncapsulatedPictureOffset < 0){
|
||||
id3tag->ID3EncapsulatedPictureType = PNG_IMAGE;
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 20);
|
||||
id3tag->ID3EncapsulatedPictureOffset = searchPNGstart(fp, 0x100);
|
||||
}
|
||||
tag_length = tag_length - (id3tag->ID3EncapsulatedPictureOffset - sceIoLseek(fp, 0, SCE_SEEK_CUR));
|
||||
id3tag->ID3EncapsulatedPictureLength = tag_length-13;
|
||||
|
50
audio/info.h
Normal file
50
audio/info.h
Normal file
@ -0,0 +1,50 @@
|
||||
// LightMP3
|
||||
// Copyright (C) 2007,2008 Sakya
|
||||
// sakya_tg@yahoo.it
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation; either version 2 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
#ifndef __info_h
|
||||
#define __info_h (1)
|
||||
|
||||
struct fileInfo{
|
||||
int fileType;
|
||||
int defaultCPUClock;
|
||||
int needsME;
|
||||
double fileSize;
|
||||
char layer[12];
|
||||
int kbit;
|
||||
long instantBitrate;
|
||||
long hz;
|
||||
char mode[52];
|
||||
char emphasis[20];
|
||||
long length;
|
||||
char strLength[12];
|
||||
long frames;
|
||||
long framesDecoded;
|
||||
int encapsulatedPictureType;
|
||||
int encapsulatedPictureOffset;
|
||||
int encapsulatedPictureLength;
|
||||
char coverArtImageName[264];
|
||||
|
||||
//Tag/comments:
|
||||
char album[260];
|
||||
char title[260];
|
||||
char artist[260];
|
||||
char genre[260];
|
||||
char year[12];
|
||||
char trackNumber[8];
|
||||
};
|
||||
|
||||
#endif
|
1264
audio/mp3player.c
1264
audio/mp3player.c
File diff suppressed because it is too large
Load Diff
@ -1,36 +1,56 @@
|
||||
// mp3player.h: headers for psp mp3player code
|
||||
// LightMP3
|
||||
// Copyright (C) 2007 Sakya
|
||||
// sakya_tg@yahoo.it
|
||||
//
|
||||
// All public functions for mp3player
|
||||
// This program is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation; either version 2 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////
|
||||
#ifndef _MP3PLAYER_H_
|
||||
#define _MP3PLAYER_H_
|
||||
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
#include <mad.h>
|
||||
//#include "../../codec.h"
|
||||
|
||||
// The following variables are maintained and updated by the tracker during playback
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
// Function prototypes for public functions
|
||||
// void MP3setStubs(codecStubs * stubs);
|
||||
extern int MP3_defaultCPUClock;
|
||||
|
||||
//private functions
|
||||
void MP3_Init(int channel);
|
||||
int MP3_Play();
|
||||
void MP3_Pause();
|
||||
int MP3_Stop();
|
||||
void MP3_End();
|
||||
void MP3_FreeTune();
|
||||
int MP3_LoadBuffer();
|
||||
int MP3_Load(char *filename);
|
||||
void MP3_GetTimeString(char *dest);
|
||||
int MP3_EndOfStream();
|
||||
void MP3_Init(int channel);
|
||||
int MP3_Play();
|
||||
void MP3_Pause();
|
||||
int MP3_Stop();
|
||||
void MP3_End();
|
||||
void MP3_FreeTune();
|
||||
int MP3_Load(char *filename);
|
||||
void MP3_GetTimeString(char *dest);
|
||||
int MP3_EndOfStream();
|
||||
struct fileInfo *MP3_GetInfo();
|
||||
struct fileInfo MP3_GetTagInfoOnly(char *filename);
|
||||
int MP3_GetStatus();
|
||||
float MP3_GetPercentage();
|
||||
void MP3_setVolumeBoostType(char *boostType);
|
||||
void MP3_setVolumeBoost(int boost);
|
||||
int MP3_getVolumeBoost();
|
||||
int MP3_getPlayingSpeed();
|
||||
int MP3_setPlayingSpeed(int playingSpeed);
|
||||
int MP3_setMute(int onOff);
|
||||
void MP3_fadeOut(float seconds);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
//Functions for filter (equalizer):
|
||||
int MP3_setFilter(double tFilter[32], int copyFilter);
|
||||
void MP3_enableFilter();
|
||||
void MP3_disableFilter();
|
||||
int MP3_isFilterEnabled();
|
||||
int MP3_isFilterSupported();
|
||||
|
||||
//Manage suspend:
|
||||
int MP3_suspend();
|
||||
int MP3_resume();
|
||||
|
||||
double MP3_getFilePosition();
|
||||
void MP3_setFilePosition(double position);
|
||||
|
111
audio/mp3xing.c
Normal file
111
audio/mp3xing.c
Normal file
@ -0,0 +1,111 @@
|
||||
// LightMP3
|
||||
// Copyright (C) 2009 Sakya
|
||||
// sakya_tg@yahoo.it
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation; either version 2 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "mp3xing.h"
|
||||
/*
|
||||
4-x Not used till string "Xing" (58 69 6E 67). This string is used as a main VBR file identifier. If it is not found, file is supposed to be CBR. This string can be placed at different locations according to values of MPEG and CHANNEL (ya, these from a few lines upwards):
|
||||
36-39 "Xing" for MPEG1 and CHANNEL != mono (mostly used)
|
||||
21-24 "Xing" for MPEG1 and CHANNEL == mono
|
||||
21-24 "Xing" for MPEG2 and CHANNEL != mono
|
||||
13-16 "Xing" for MPEG2 and CHANNEL == mono
|
||||
|
||||
After "Xing" string there are placed flags, number of frames in file and a size of file in Bytes. Each of these items has 4 Bytes and it is stored as 'int' number in memory. The first is the most significant Byte and the last is the least.
|
||||
Following schema is for MPEG1 and CHANNEL != mono:
|
||||
40-43 Flags
|
||||
Value Name Description
|
||||
00 00 00 01 Frames Flag set if value for number of frames in file is stored
|
||||
00 00 00 02 Bytes Flag set if value for filesize in Bytes is stored
|
||||
00 00 00 04 TOC Flag set if values for TOC (see below) are stored
|
||||
00 00 00 08 VBR Scale Flag set if values for VBR scale are stored
|
||||
All these values can be stored simultaneously.
|
||||
|
||||
44-47 Frames
|
||||
Number of frames in file (including the first info one)
|
||||
|
||||
48-51 Bytes
|
||||
File length in Bytes
|
||||
|
||||
52-151 TOC (Table of Contents)
|
||||
Contains of 100 indexes (one Byte length) for easier lookup in file. Approximately solves problem with moving inside file.
|
||||
Each Byte has a value according this formula:
|
||||
(TOC[i] / 256) * fileLenInBytes
|
||||
So if song lasts eg. 240 sec. and you want to jump to 60. sec. (and file is 5 000 000 Bytes length) you can use:
|
||||
TOC[(60/240)*100] = TOC[25]
|
||||
and corresponding Byte in file is then approximately at:
|
||||
(TOC[25]/256) * 5000000
|
||||
|
||||
If you want to trim VBR file you should also reconstruct Frames, Bytes and TOC properly.
|
||||
|
||||
152-155 VBR Scale
|
||||
I dont know exactly system of storing of this values but this item probably doesnt have deeper meaning.
|
||||
*/
|
||||
|
||||
int xingSearchFrame(unsigned char *buffer, int startPos, int maxSearch)
|
||||
{
|
||||
int i = 0;
|
||||
for (i=0; i<maxSearch; i++)
|
||||
{
|
||||
if(!memcmp(buffer, XING_GUID, 4))
|
||||
return startPos;
|
||||
startPos++;
|
||||
buffer++;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int xingGetFlags(unsigned char *buffer, int startPos)
|
||||
{
|
||||
buffer += startPos + 4;
|
||||
return buffer[0] + buffer[1] + buffer[2] + buffer[3];
|
||||
}
|
||||
|
||||
int xingGetFrameNumber(unsigned char *buffer, int startPos)
|
||||
{
|
||||
buffer += startPos + 8;
|
||||
char hexStr[9] = "";
|
||||
sprintf(hexStr, "%2.2X%2.2X%2.2X%2.2X", buffer[0], buffer[1], buffer[2], buffer[3]);
|
||||
return strtol(hexStr, NULL, 16);
|
||||
}
|
||||
|
||||
int xingGetFileSize(unsigned char *buffer, int startPos)
|
||||
{
|
||||
buffer += startPos + 12;
|
||||
char hexStr[9] = "";
|
||||
sprintf(hexStr, "%2.2X%2.2X%2.2X%2.2X", buffer[0], buffer[1], buffer[2], buffer[3]);
|
||||
return strtol(hexStr, NULL, 16);
|
||||
}
|
||||
|
||||
|
||||
int parse_xing(unsigned char *buffer, int startPos, struct xing *xing)
|
||||
{
|
||||
int pos = xingSearchFrame(buffer, startPos, XING_BUFFER_SIZE - 4);
|
||||
if (pos < 0)
|
||||
return 0;
|
||||
|
||||
xing->flags = xingGetFlags(buffer, pos);
|
||||
if (xing->flags & 1)
|
||||
xing->frames = xingGetFrameNumber(buffer, pos);
|
||||
if (xing->flags & 2)
|
||||
xing->bytes = xingGetFileSize(buffer, pos);
|
||||
|
||||
/*if (xing->flags & 4)
|
||||
if (xing->flags & 8)*/
|
||||
return 1;
|
||||
}
|
44
audio/mp3xing.h
Normal file
44
audio/mp3xing.h
Normal file
@ -0,0 +1,44 @@
|
||||
// LightMP3
|
||||
// Copyright (C) 2009 Sakya
|
||||
// sakya_tg@yahoo.it
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or modify
|
||||
// it under the terms of the GNU General Public License as published by
|
||||
// the Free Software Foundation; either version 2 of the License, or
|
||||
// (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
#ifndef __mp3xing_h
|
||||
#define __mp3xing_h (1)
|
||||
|
||||
#include <mad.h>
|
||||
|
||||
#define XING_BUFFER_SIZE 300
|
||||
#define XING_GUID (unsigned char [4]) \
|
||||
{ 0x58, 0x69, 0x6E, 0x67 }
|
||||
|
||||
struct xing {
|
||||
int flags;
|
||||
unsigned long frames;
|
||||
unsigned long bytes;
|
||||
unsigned char toc[100];
|
||||
long scale;
|
||||
};
|
||||
|
||||
enum {
|
||||
XING_FRAMES = 0x0001,
|
||||
XING_BYTES = 0x0002,
|
||||
XING_TOC = 0x0004,
|
||||
XING_SCALE = 0x0008
|
||||
};
|
||||
|
||||
int parse_xing(unsigned char *buffer, int startPos, struct xing *xing);
|
||||
|
||||
#endif
|
139
audio/player.c
Normal file
139
audio/player.c
Normal file
@ -0,0 +1,139 @@
|
||||
/*
|
||||
VitaShell
|
||||
Copyright (C) 2015-2016, TheFloW
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <psp2/io/fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "player.h"
|
||||
|
||||
int MAX_VOLUME_BOOST=15;
|
||||
int MIN_VOLUME_BOOST=-15;
|
||||
int MIN_PLAYING_SPEED=-119;
|
||||
int MAX_PLAYING_SPEED=119;
|
||||
|
||||
//Seek next valid frame
|
||||
//NOTE: this function comes from Music prx 0.55 source
|
||||
// all credits goes to joek2100.
|
||||
int SeekNextFrameMP3(SceUID fd)
|
||||
{
|
||||
int offset = 0;
|
||||
unsigned char buf[1024];
|
||||
unsigned char *pBuffer;
|
||||
int i;
|
||||
int size = 0;
|
||||
|
||||
offset = sceIoLseek32(fd, 0, SCE_SEEK_CUR);
|
||||
sceIoRead(fd, buf, sizeof(buf));
|
||||
if (!strncmp((char*)buf, "ID3", 3) || !strncmp((char*)buf, "ea3", 3)) //skip past id3v2 header, which can cause a false sync to be found
|
||||
{
|
||||
//get the real size from the syncsafe int
|
||||
size = buf[6];
|
||||
size = (size<<7) | buf[7];
|
||||
size = (size<<7) | buf[8];
|
||||
size = (size<<7) | buf[9];
|
||||
|
||||
size += 10;
|
||||
|
||||
if (buf[5] & 0x10) //has footer
|
||||
size += 10;
|
||||
}
|
||||
|
||||
sceIoLseek32(fd, offset, SCE_SEEK_SET); //now seek for a sync
|
||||
while(1)
|
||||
{
|
||||
offset = sceIoLseek32(fd, 0, SCE_SEEK_CUR);
|
||||
size = sceIoRead(fd, buf, sizeof(buf));
|
||||
|
||||
if (size <= 2)//at end of file
|
||||
return -1;
|
||||
|
||||
if (!strncmp((char*)buf, "EA3", 3))//oma mp3 files have non-safe ints in the EA3 header
|
||||
{
|
||||
sceIoLseek32(fd, (buf[4]<<8)+buf[5], SCE_SEEK_CUR);
|
||||
continue;
|
||||
}
|
||||
|
||||
pBuffer = buf;
|
||||
for( i = 0; i < size; i++)
|
||||
{
|
||||
//if this is a valid frame sync (0xe0 is for mpeg version 2.5,2+1)
|
||||
if ( (pBuffer[i] == 0xff) && ((pBuffer[i+1] & 0xE0) == 0xE0))
|
||||
{
|
||||
offset += i;
|
||||
sceIoLseek32(fd, offset, SCE_SEEK_SET);
|
||||
return offset;
|
||||
}
|
||||
}
|
||||
//go back two bytes to catch any syncs that on the boundary
|
||||
sceIoLseek32(fd, -2, SCE_SEEK_CUR);
|
||||
}
|
||||
}
|
||||
|
||||
short volume_boost(short *Sample, unsigned int *boost) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setVolume(int channel, int volume) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int setMute(int channel, int onOff) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void fadeOut(int channel, float seconds) {
|
||||
|
||||
}
|
||||
|
||||
int initAudioLib() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int endAudioLib() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void initFileInfo(struct fileInfo *info){
|
||||
info->fileType = -1;
|
||||
info->defaultCPUClock = 0;
|
||||
info->needsME = 0;
|
||||
info->fileSize = 0;
|
||||
strcpy(info->layer, "");
|
||||
info->kbit = 0;
|
||||
info->instantBitrate = 0;
|
||||
info->hz = 0;
|
||||
strcpy(info->mode, "");
|
||||
strcpy(info->emphasis, "");
|
||||
info->length = 0;
|
||||
strcpy(info->strLength, "");
|
||||
info->frames = 0;
|
||||
info->framesDecoded = 0;
|
||||
info->encapsulatedPictureType = 0;
|
||||
info->encapsulatedPictureOffset = 0;
|
||||
info->encapsulatedPictureLength = 0;
|
||||
|
||||
strcpy(info->album, "");
|
||||
strcpy(info->title, "");
|
||||
strcpy(info->artist, "");
|
||||
strcpy(info->genre, "");
|
||||
strcpy(info->year, "");
|
||||
strcpy(info->trackNumber, "");
|
||||
strcpy(info->coverArtImageName, "");
|
||||
}
|
59
audio/player.h
Normal file
59
audio/player.h
Normal file
@ -0,0 +1,59 @@
|
||||
/*
|
||||
VitaShell
|
||||
Copyright (C) 2015-2016, TheFloW
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef __PLAYER_H__
|
||||
#define __PLAYER_H__
|
||||
|
||||
#include "info.h"
|
||||
|
||||
#define OPENING_OK 0
|
||||
#define ERROR_OPENING -1
|
||||
#define ERROR_INVALID_SAMPLE_RATE -2
|
||||
#define ERROR_MEMORY -3
|
||||
#define ERROR_CREATE_THREAD -4
|
||||
|
||||
#define MP3_TYPE 0
|
||||
#define OGG_TYPE 1
|
||||
#define AT3_TYPE 2
|
||||
#define FLAC_TYPE 3
|
||||
#define AAC_TYPE 4
|
||||
#define WMA_TYPE 5
|
||||
#define UNK_TYPE -1
|
||||
|
||||
#define FASTFORWARD_VOLUME 0x2200
|
||||
#define MAX_IMAGE_DIMENSION 300*1024
|
||||
#define DEFAULT_THREAD_STACK_SIZE 256*1024
|
||||
|
||||
extern int MAX_VOLUME_BOOST;
|
||||
extern int MIN_VOLUME_BOOST;
|
||||
extern int MIN_PLAYING_SPEED;
|
||||
extern int MAX_PLAYING_SPEED;
|
||||
|
||||
int SeekNextFrameMP3(SceUID fd);
|
||||
|
||||
short volume_boost(short *Sample, unsigned int *boost);
|
||||
int setVolume(int channel, int volume);
|
||||
int setMute(int channel, int onOff);
|
||||
void fadeOut(int channel, float seconds);
|
||||
|
||||
int initAudioLib();
|
||||
int endAudioLib();
|
||||
|
||||
void initFileInfo(struct fileInfo *info);
|
||||
|
||||
#endif
|
@ -42,6 +42,10 @@ static vitaAudioChannelInfo vitaAudioStatus[VITA_NUM_AUDIO_CHANNELS];
|
||||
|
||||
static volatile int vitaAudioTerminate = 0;
|
||||
|
||||
int vitaAudioSetFrequency(int channel, unsigned short freq) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void vitaAudioSetChannelCallback(int channel, vitaAudioCallback callback, void *data)
|
||||
{
|
||||
volatile vitaAudioChannelInfo *pci = &vitaAudioStatus[channel];
|
||||
|
139
audioplayer.c
139
audioplayer.c
@ -24,39 +24,158 @@
|
||||
#include "utils.h"
|
||||
|
||||
#include "audio/id3.h"
|
||||
#include "audio/info.h"
|
||||
#include "audio/mp3player.h"
|
||||
|
||||
int audioPlayer(char *file, int type, FileList *list, FileListEntry *entry, int *base_pos, int *rel_pos) {
|
||||
struct ID3Tag id3tag;
|
||||
ParseID3(file, &id3tag);
|
||||
struct fileInfo *fileinfo = NULL;
|
||||
vita2d_texture *tex = NULL;
|
||||
|
||||
void getMp3Info(char *file) {
|
||||
char *buffer = NULL;
|
||||
|
||||
fileinfo = MP3_GetInfo();
|
||||
|
||||
if (tex) {
|
||||
vita2d_free_texture(tex);
|
||||
tex = NULL;
|
||||
}
|
||||
|
||||
switch (fileinfo->encapsulatedPictureType) {
|
||||
case JPEG_IMAGE:
|
||||
case PNG_IMAGE:
|
||||
{
|
||||
SceUID fd = sceIoOpen(file, SCE_O_RDONLY, 0);
|
||||
if (fd >= 0) {
|
||||
char *buffer = malloc(fileinfo->encapsulatedPictureLength);
|
||||
if (buffer) {
|
||||
sceIoLseek32(fd, fileinfo->encapsulatedPictureOffset, SCE_SEEK_SET);
|
||||
sceIoRead(fd, buffer, fileinfo->encapsulatedPictureLength);
|
||||
sceIoClose(fd);
|
||||
|
||||
if (fileinfo->encapsulatedPictureType == JPEG_IMAGE)
|
||||
tex = vita2d_load_JPEG_buffer(buffer, fileinfo->encapsulatedPictureLength);
|
||||
|
||||
if (fileinfo->encapsulatedPictureType == PNG_IMAGE)
|
||||
tex = vita2d_load_PNG_buffer(buffer);
|
||||
|
||||
free(buffer);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int audioPlayer(char *file, int type, FileList *list, FileListEntry *entry, int *base_pos, int *rel_pos) {
|
||||
MP3_Init(0);
|
||||
MP3_Load(file);
|
||||
MP3_Play();
|
||||
|
||||
getMp3Info(file);
|
||||
|
||||
while (1) {
|
||||
readPad();
|
||||
|
||||
if (MP3_EndOfStream())
|
||||
break;
|
||||
|
||||
// Cancel
|
||||
if (pressed_buttons & SCE_CTRL_CANCEL) {
|
||||
break;
|
||||
}
|
||||
|
||||
// Previous/next song.
|
||||
if (MP3_EndOfStream() || pressed_buttons & SCE_CTRL_LTRIGGER || pressed_buttons & SCE_CTRL_RTRIGGER) {
|
||||
int available = 0;
|
||||
|
||||
int old_base_pos = *base_pos;
|
||||
int old_rel_pos = *rel_pos;
|
||||
FileListEntry *old_entry = entry;
|
||||
|
||||
int previous = pressed_buttons & SCE_CTRL_LTRIGGER;
|
||||
if (MP3_EndOfStream())
|
||||
previous = 0;
|
||||
|
||||
while (previous ? entry->previous : entry->next) {
|
||||
entry = previous ? entry->previous : entry->next;
|
||||
|
||||
if (previous) {
|
||||
if (*rel_pos > 0) {
|
||||
(*rel_pos)--;
|
||||
} else {
|
||||
if (*base_pos > 0) {
|
||||
(*base_pos)--;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if ((*rel_pos + 1) < list->length) {
|
||||
if ((*rel_pos + 1) < MAX_POSITION) {
|
||||
(*rel_pos)++;
|
||||
} else {
|
||||
if ((*base_pos + *rel_pos + 1) < list->length) {
|
||||
(*base_pos)++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!entry->is_folder) {
|
||||
char path[MAX_PATH_LENGTH];
|
||||
snprintf(path, MAX_PATH_LENGTH, "%s%s", list->path, entry->name);
|
||||
int type = getFileType(path);
|
||||
if (type == FILE_TYPE_MP3) {
|
||||
MP3_End();
|
||||
MP3_Init(0);
|
||||
MP3_Load(path);
|
||||
MP3_Play();
|
||||
getMp3Info(path);
|
||||
available = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!available) {
|
||||
*base_pos = old_base_pos;
|
||||
*rel_pos = old_rel_pos;
|
||||
entry = old_entry;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Start drawing
|
||||
startDrawing(NULL);
|
||||
|
||||
char string[32];
|
||||
MP3_GetTimeString(string);
|
||||
pgf_draw_textf(SHELL_MARGIN_X, SCREEN_HEIGHT - 3.0f * SHELL_MARGIN_Y, PHOTO_ZOOM_COLOR, FONT_SIZE, string);
|
||||
// Draw shell info
|
||||
drawShellInfo(file);
|
||||
|
||||
pgf_draw_textf(SHELL_MARGIN_X, START_Y + (0 * FONT_Y_SPACE), 0xFFFFFFFF, FONT_SIZE, fileinfo->artist);
|
||||
pgf_draw_textf(SHELL_MARGIN_X, START_Y + (1 * FONT_Y_SPACE), 0xFFFFFFFF, FONT_SIZE, fileinfo->title);
|
||||
pgf_draw_textf(SHELL_MARGIN_X, START_Y + (2 * FONT_Y_SPACE), 0xFFFFFFFF, FONT_SIZE, fileinfo->album);
|
||||
|
||||
// Picture
|
||||
if (tex)
|
||||
vita2d_draw_texture_scale(tex, SHELL_MARGIN_X, 200.0f, 1.0f, 1.0f);
|
||||
|
||||
// Time
|
||||
char string[12];
|
||||
MP3_GetTimeString(string);
|
||||
|
||||
pgf_draw_textf(SHELL_MARGIN_X, SCREEN_HEIGHT - 3.0f * SHELL_MARGIN_Y, PHOTO_ZOOM_COLOR, FONT_SIZE, "%s/%s", string, fileinfo->strLength);
|
||||
/*
|
||||
//float percent = MP3_GetPercentage();
|
||||
float width = uncommon_dialog.width - 2.0f * SHELL_MARGIN_X;
|
||||
vita2d_draw_rectangle(uncommon_dialog.x + SHELL_MARGIN_X, string_y + 10.0f, width, UNCOMMON_DIALOG_PROGRESS_BAR_HEIGHT, PROGRESS_BAR_BG_COLOR);
|
||||
vita2d_draw_rectangle(uncommon_dialog.x + SHELL_MARGIN_X, string_y + 10.0f, uncommon_dialog.progress * width / 100.0f, UNCOMMON_DIALOG_PROGRESS_BAR_HEIGHT, PROGRESS_BAR_COLOR);
|
||||
*/
|
||||
// End drawing
|
||||
endDrawing();
|
||||
}
|
||||
|
||||
MP3_Stop();
|
||||
if (tex) {
|
||||
vita2d_free_texture(tex);
|
||||
tex = NULL;
|
||||
}
|
||||
|
||||
MP3_End();
|
||||
|
||||
return 0;
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user