Multiple updates for DTSCv2 Filtering.

This commit is contained in:
Erik Zandvliet 2013-05-22 15:48:26 +02:00
parent 22295d3b5d
commit 6e95dbe10b
2 changed files with 73 additions and 61 deletions

View file

@ -719,6 +719,9 @@ bool DTSC::File::reachedEOF(){
/// If the packet could not be read for any reason, the reason is printed to stderr. /// If the packet could not be read for any reason, the reason is printed to stderr.
/// Reading the packet means the file position is increased to the next packet. /// Reading the packet means the file position is increased to the next packet.
void DTSC::File::seekNext(){ void DTSC::File::seekNext(){
fseek(F,currentPositions.begin()->seekPos, SEEK_SET);
seek_time(currentPositions.begin()->seekTime + 1, currentPositions.begin()->trackID);
currentPositions.erase(currentPositions.begin());
lastreadpos = ftell(F); lastreadpos = ftell(F);
if (fread(buffer, 4, 1, F) != 1){ if (fread(buffer, 4, 1, F) != 1){
if (feof(F)){ if (feof(F)){
@ -773,21 +776,6 @@ void DTSC::File::seekNext(){
}else{ }else{
jsonbuffer = JSON::fromDTMI(strbuffer); jsonbuffer = JSON::fromDTMI(strbuffer);
} }
if (jsonbuffer.isMember("keyframe")){
if (selectedTracks.size()){
if (metadata["tracks"][selectedTracks[0]]["keybpos"][currframe].asInt() != lastreadpos){
currframe++;
currtime = jsonbuffer["time"].asInt();
#if DEBUG >= 6
if (metadata["tracks"][selectedTracks[0]]["keybpos"][currframe].asInt() != lastreadpos){
std::cerr << "Found a new frame " << currframe << " @ " << lastreadpos << "b/" << currtime << "ms" << std::endl;
} else{
std::cerr << "Passing frame " << currframe << " @ " << lastreadpos << "b/" << currtime << "ms" << std::endl;
}
#endif
}
}
}
} }
/// Returns the byte positon of the start of the last packet that was read. /// Returns the byte positon of the start of the last packet that was read.
@ -805,55 +793,54 @@ JSON::Value & DTSC::File::getJSON(){
return jsonbuffer; return jsonbuffer;
} }
/// Attempts to seek to the given frame number within the file. bool DTSC::File::seek_time(int ms, int trackNo){
/// Returns true if successful, false otherwise. seekPos tmpPos;
bool DTSC::File::seek_frame(int frameno){ tmpPos.trackID = trackNo;
int bytePos = -1; for (int i = 0; i < metadata["tracks"][trackMapping[trackNo]]["keynum"].size(); i++){
int replaceBytePos = -1; if (metadata["tracks"][trackMapping[trackNo]]["keytime"][i].asInt() > ms){
for (int i = 0; i < metadata["tracks"][selectedTracks[0]]["keynum"].size(); i++){
if (metadata["tracks"][selectedTracks[0]]["keynum"][i].asInt() == frameno){
bytePos = metadata["tracks"][selectedTracks[0]]["keybpos"][i].asInt();
break; break;
} }
if (metadata["tracks"][selectedTracks[0]]["keynum"][i].asInt() < frameno){ tmpPos.seekTime = metadata["tracks"][trackMapping[trackNo]]["keytime"][i].asInt();
replaceBytePos = metadata["tracks"][selectedTracks[0]]["keybpos"][i].asInt(); tmpPos.seekPos = metadata["tracks"][trackMapping[trackNo]]["keybpos"][i].asInt();
}
bool foundPacket = false;
while ( !foundPacket){
//Seek to first packet after ms.
seek_bpos(tmpPos.seekPos);
//read the header
char header[20];
fread((void*)header, 20, 1, F);
//check if packetID matches, if not, skip size + 8 bytes.
int packSize = ntohl(((int*)header)[1]);
int packID = ntohl(((int*)header)[2]);
if (packID != trackNo){
tmpPos.seekPos += 8 + packSize;
continue;
}
//get timestamp of packet, if too large, break, if not, skip size bytes.
long long unsigned int myTime = ((long long unsigned int)ntohl(((int*)header)[3]) << 32);
myTime += ntohl(((int*)header)[4]);
if (myTime >= ms){
tmpPos.seekTime = myTime;
foundPacket = true;
}else{
tmpPos.seekPos += 8 + packSize;
continue;
} }
} }
if (bytePos == -1){ currentPositions.insert(tmpPos);
bytePos = replaceBytePos; fprintf(stderr, "TrackID %d, Time seek %d -- retrieved bytepos %d, timestamp %d\n", trackNo, ms, tmpPos.seekPos, tmpPos.seekTime);
}
if (bytePos > -1){
if (fseek(F, bytePos, SEEK_SET) == 0){
#if DEBUG >= 5
std::cerr << "Seek direct from " << currframe << " @ " << metadata["tracks"][selectedTracks[0]]["keybpos"][currframe].asInt() << " to " << frameno << " @ " << bytePos << std::endl;
#endif
currframe = frameno;
return true;
}
}
return false;
} }
/// Attempts to seek to the given time in ms within the file. /// Attempts to seek to the given time in ms within the file.
/// Returns true if successful, false otherwise. /// Returns true if successful, false otherwise.
bool DTSC::File::seek_time(int ms){ bool DTSC::File::seek_time(int ms){
currtime = 0; currentPositions.clear();
currframe = 1; seekPos tmpPos;
int bytePos = -1; for (std::set<int>::iterator it = selectedTracks.begin(); it != selectedTracks.end(); it++){
for (int i = 0; i < metadata["tracks"][selectedTracks[0]]["keynum"].size(); i++){ seek_time(ms,(*it));
if (metadata["tracks"][selectedTracks[0]]["keytime"][i].asInt() > ms){
break;
}
if (metadata["tracks"][selectedTracks[0]]["keytime"][i].asInt() > currtime){
currtime = metadata["tracks"][selectedTracks[0]]["keytime"][i].asInt();
currframe = i + 1;
}
bytePos = metadata["tracks"][selectedTracks[0]]["keybpos"][i].asInt();
} }
if (fseek(F, bytePos, SEEK_SET) == 0){ return true;
return true;
}
return false;
} }
bool DTSC::File::seek_bpos(int bpos){ bool DTSC::File::seek_bpos(int bpos){
@ -872,10 +859,6 @@ void DTSC::File::writePacket(JSON::Value & newPacket){
writePacket(newPacket.toNetPacked()); writePacket(newPacket.toNetPacked());
} }
void DTSC::File::selectTracks(std::vector<std::string> & trackIDs){
selectedTracks = trackIDs;
}
bool DTSC::File::atKeyframe(){ bool DTSC::File::atKeyframe(){
if (getJSON().isMember("keyframe")){ if (getJSON().isMember("keyframe")){
return true; return true;
@ -892,6 +875,11 @@ bool DTSC::File::atKeyframe(){
return inHeader; return inHeader;
} }
void DTSC::File::selectTracks(std::set<int> & tracks){
currentPositions.clear();
selectedTracks = tracks;
}
/// Close the file if open /// Close the file if open
DTSC::File::~File(){ DTSC::File::~File(){
if (F){ if (F){

View file

@ -64,6 +64,29 @@ namespace DTSC {
extern char Magic_Packet[]; ///< The magic bytes for a DTSC packet extern char Magic_Packet[]; ///< The magic bytes for a DTSC packet
extern char Magic_Packet2[]; ///< The magic bytes for a DTSC packet version 2 extern char Magic_Packet2[]; ///< The magic bytes for a DTSC packet version 2
/// A simple structure used for ordering byte seek positions.
struct seekPos {
bool operator < (const seekPos& rhs) const {
if (seekTime < rhs.seekTime){
return true;
}else{
if (seekTime == rhs.seekTime){
if (seekPos < rhs.seekPos){
return true;
}else{
if (trackID < rhs.trackID){
return true;
}
}
}
}
return false;
}
long long unsigned int seekTime;
long long unsigned int seekPos;
unsigned int trackID;
};
/// A simple wrapper class that will open a file and allow easy reading/writing of DTSC data from/to it. /// A simple wrapper class that will open a file and allow easy reading/writing of DTSC data from/to it.
class File{ class File{
public: public:
@ -83,13 +106,13 @@ namespace DTSC {
void seekNext(); void seekNext();
std::string & getPacket(); std::string & getPacket();
JSON::Value & getJSON(); JSON::Value & getJSON();
bool seek_frame(int frameno);
bool seek_time(int seconds); bool seek_time(int seconds);
bool seek_time(int seconds, int trackNo);
bool seek_bpos(int bpos); bool seek_bpos(int bpos);
void writePacket(std::string & newPacket); void writePacket(std::string & newPacket);
void writePacket(JSON::Value & newPacket); void writePacket(JSON::Value & newPacket);
void selectTracks(std::vector<std::string> & trackIDs);
bool atKeyframe(); bool atKeyframe();
void selectTracks(std::set<int> & tracks);
private: private:
void readHeader(int pos); void readHeader(int pos);
std::string strbuffer; std::string strbuffer;
@ -104,7 +127,8 @@ namespace DTSC {
unsigned long headerSize; unsigned long headerSize;
char buffer[4]; char buffer[4];
bool created; bool created;
std::vector<std::string> selectedTracks; std::set<seekPos> currentPositions;
std::set<int> selectedTracks;
}; };
//FileWriter //FileWriter