void Catalog::onRequestHanderl() { auto netReplay = qobject_cast<QNetworkReply*>(sender()); if(netReplay->error() == QNetworkReply::NoError) { const Replay rep(netReplay->readAll()); if(rep.isSuccess()) { parseData(rep.objectData()); } } netReplay->deleteLater(); }
void PlayFilesModel::onRequestHanderl() { auto netReplay = qobject_cast<QNetworkReply*>(sender()); if(netReplay->error() == QNetworkReply::NoError) { const Replay replay(netReplay->readAll()); if(replay.isSuccess()) { parseData(replay.arrayData()); } } netReplay->deleteLater(); }
void OsuManiaRenderer::RenderReplay(Window& _win) { Replay* replay = play->replay; osu::TIMING frame = replay->getFrameAt(*viewTime); int hitYpos = this->height; const int KEYS = play->beatmap->getMods().getCS(); for (int key = 0; key < KEYS; key++) { if ((int)frame.pos.X & (1 << key)) { int hitXpos = key * (this->width / KEYS) + (this->absXpos - this->width / 2); int width = ((this->width) / KEYS) - (2 * KEYS); _win.driver->draw2DRectangle(SColor(255, 100, 100, 100), rect<s32>(absXpos + hitXpos, absYpos + hitYpos, absXpos + hitXpos + width, absYpos + hitYpos + 15)); } } }
void ReplayLoadingThread::run() { QDirIterator dirIterator(_folder, QDirIterator::Subdirectories); int counter = 0; while(dirIterator.hasNext()) { QString fileName = dirIterator.next(); if(counter >= _startFrom && counter < _startFrom + REPLAYS_PER_THREAD) { if(fileName.right(REPLAY_FILE_EXT.length()) == REPLAY_FILE_EXT) { Replay *replay = new Replay(fileName, _vehicleNames); if(replay->load()) { _replays->append(replay); } else { delete replay; } } } else if(counter > _startFrom + REPLAYS_PER_THREAD) { break; } counter++; } }
/** * Callbackfunktion zum Eintragen einer Replay-Zeile in der Tabelle. * * @param[in] filename Der Dateiname * @param[in] param Ein benutzerdefinierter Parameter * * @todo Noch korrekt dokumentieren (was wird da so übersprungen usw) * @todo Fehlerabfrage der freads!!! * * @author OLiver */ void iwPlayReplay::FillReplayTable(const std::string& filename, void* param) { Replay replay; // Datei laden if(!replay.LoadHeader(filename, false)) return; // Zeitstamp benutzen char datestring[64]; TIME.FormatTime(datestring, "%d.%m.%Y - %H:%i", &replay.save_time); // Spielernamen auslesen std::string tmp_players; unsigned char j = 0; for(unsigned char i = 0; i < replay.player_count; ++i) { // Was für ein State, wenn es nen KI Spieler oder ein normaler ist, muss das Zeug ausgelesen werden if(replay.players[i].ps == PS_OCCUPIED || replay.players[i].ps == PS_KI) { // und in unsere "Namensliste" hinzufügen (beim ersten Spieler muss kein Komma hin) if(j > 0) tmp_players += ", "; tmp_players += replay.players[i].name; ++j; } } // Dateiname noch rausextrahieren aus dem Pfad size_t pos = filename.find_last_of('/'); if(pos == std::string::npos) return; std::string extracted_filename = filename.substr(pos + 1); char gfl[50]; snprintf(gfl, 50, "%u", replay.last_gf); // Und das Zeug zur Tabelle hinzufügen static_cast<ctrlTable*>(param)->AddRow(0, extracted_filename.c_str(), datestring, tmp_players.c_str(), gfl, filename.c_str()); }
void iwPlayReplay::Msg_MsgBoxResult(const unsigned msgbox_id, const MsgboxResult mbr) { // Sollen alle Replays gelöscht werden? if(msgbox_id == 1 && mbr == MSR_YES) { std::vector<std::string> replays = GetReplays(); for(std::vector<std::string>::iterator it = replays.begin(); it != replays.end(); ++it) { boost::system::error_code ec; bfs::remove(*it, ec); } // Tabelle leeren GetCtrl<ctrlTable>(0)->DeleteAllItems(); } else if(msgbox_id == 3 && mbr == MSR_YES) { std::vector<std::string> replays = GetReplays(); for(std::vector<std::string>::iterator it = replays.begin(); it != replays.end(); ++it) { Replay replay; if(!replay.LoadHeader(*it)) { replay.StopRecording(); boost::system::error_code ec; bfs::remove(*it, ec); } } PopulateTable(); } else if(msgbox_id == 2 && mbr == MSR_YES) { ctrlTable* table = GetCtrl<ctrlTable>(0); if(table->GetSelection() < table->GetRowCount()) { boost::system::error_code ec; bfs::remove(table->GetItemText(table->GetSelection(), 4), ec); PopulateTable(); } } }
// list change void CGui::listRplChng(List* li, size_t pos) { String name = getRplName(); if (name.empty()) return; string file = GetRplListDir() + "/" + name + ".rpl"; valRplName->setCaption(name); edRplName->setCaption(name); // load replay header, upd info text Replay rpl; char stm[128]; if (rpl.LoadFile(file,true)) { String ss = String(TR("#{Track}: ")) + gcom->GetSceneryColor(rpl.header.track) + rpl.header.track + (rpl.header.track_user ? " *"+TR("#{TweakUser}")+"*" : ""); valRplName->setCaption(ss); ss = String(TR("#{Car}: ")) + rpl.header.car + " "+ (rpl.header.numPlayers == 1 ? "" : (TR("#{Players}: ") + toStr(rpl.header.numPlayers))) + " " + (rpl.header.networked == 0 ? "" : "M") + //TR("#{Multiplayer}") "\n#C0D8F0" + TR("#{RplTime}: ") + CHud::StrTime(rpl.GetTimeLength()) + "\n#90A0B0" + TR("#{Simulation}: ") + rpl.header.sim_mode; if (rpl.header.networked == 1) // list nicks ss += String("\n#90C0E0")+rpl.header.nicks[0]+" "+rpl.header.nicks[1]+" "+rpl.header.nicks[2]+" "+rpl.header.nicks[3]; //else // other cars, car colors .. //ss += String("\n#90C0E0")+rpl.header.cars[0]+" "+rpl.header.cars[1]+" "+rpl.header.cars[2]; valRplInfo->setCaption(ss); // file stats int size = fs::file_size(file); std::time_t ti = fs::last_write_time(file); if (!std::strftime(stm, 126, "%d.%b'%y %a %H:%M", std::localtime(&ti))) stm[0]=0; ss =/*"Time: "+*/String(stm)+"\n#A0A0A0"+ String(TR("#{RplFileSize}: ")) + fToStr( float(size)/1000000.f, 2,5) + TR(" #{UnitMB}") + "\n#808080" + TR("#{RplVersion}: ") + toStr(rpl.header.ver) + " " + toStr(rpl.header.frameSize) + "B"; if (valRplInfo2) valRplInfo2->setCaption(ss); } //edRplDesc }
void StartPlaying(const std::string& name) { Replay *replay = Replay::GetInstance(); replay->Init(false); if (replay->LoadReplay(name.c_str())) { Double speed = GameTime::GetInstance()->GetSpeed(); if (replay->StartPlaying()) { Game::GetInstance()->Start(); replay->StopPlaying(); GameTime::GetInstance()->SetSpeed(speed); } } replay->DeInit(); }
// Cmd line format : /rep="replay file" [/sec] [/sep=,] [/txt="text file"] // // /sec : use seconds instead of ticks // /sep=X : specifies X as the column separator (don't use ',') // /rep="replay file" : replay to analyse (use full path unless bwchart.exe is located in same directory) // /txt="text file" : output text file // // default separator is TAB // default text file is rep file with .txt extension instead of .rep extension // default time measurement is ticks // // Always put replay file name and output text file name between double quotes (eg:"c:\dir\gg.rep"). // // Return code: 0 if ok, 1 for invalid parameter, -1 for output file cant be created, -2 for replay cant be loaded // int CBwchartApp::_CommandLineMode() { char *argv[4]; int argc=0; int err = 0; // extract arguments char *p = m_lpCmdLine; bool inString =false; while(*p!=0) { argv[argc] = p; while(true) { p++; if(*p=='\"') inString=!inString; else if(*p==' ' && !inString) {*p=0; p++; argc++; break;} } while(*p==' ') p++; } // analyse arguments CString repfile; CString txtfile; bool useSeconds = false; char cSep = '\t'; for(int i=0; i<argc; i++) { // extract option and value char *option = strtok(argv[i],"="); char *val = strtok(0,"="); // lowercase option _strlwr(option); if(strcmp(option,"/sec")==0) useSeconds = true; else if(strcmp(option,"/sep")==0) { if(val==0) err = 1; cSep = val[0]; } else if(strcmp(option,"/rep")==0) { if(val==0) err = 1; repfile = val; repfile.Replace('\"',' '); repfile.TrimLeft(); repfile.TrimRight(); } else if(strcmp(option,"/txt")==0) { if(val==0) err = 1; txtfile = val; txtfile.Replace('\"',' '); txtfile.TrimLeft(); txtfile.TrimRight(); } } // if text file is missing if(err == 0 && txtfile.IsEmpty()) { // use replay file name with txt extension txtfile = repfile; txtfile.Replace(".rep",".txt"); txtfile.Replace(".REP",".txt"); } // if we have a replay to export if(!repfile.IsEmpty()) { Replay replay; if(replay.Load(repfile,true,0,true)!=0) err = -2; else err = replay.ExportToText(txtfile,useSeconds,cSep); } return err; }
bool DebugInfo::SendReplay() { LOG.lprintf("Sending replay...\n"); // Replay mode is on, no recording of replays active if (!GAMECLIENT.IsReplayModeOn()) { Replay rpl = GAMECLIENT.GetReplay(); if(!rpl.IsValid()) return true; BinaryFile* f = rpl.GetFile(); if(!f) // no replay to send return true; f->Flush(); unsigned replay_len = f->Tell(); LOG.lprintf("- Replay length: %u\n", replay_len); boost::interprocess::unique_ptr<char, Deleter<char[]> > replay(new char[replay_len]); f->Seek(0, SEEK_SET); f->ReadRawData(replay.get(), replay_len); unsigned int compressed_len = replay_len * 2 + 600; boost::interprocess::unique_ptr<char, Deleter<char[]> > compressed(new char[compressed_len]); // send size of replay via socket if (!SendString("Replay")) { return false; } LOG.lprintf("- Compressing...\n"); if (BZ2_bzBuffToBuffCompress(compressed.get(), (unsigned int*) &compressed_len, replay.get(), replay_len, 9, 0, 250) == BZ_OK) { LOG.lprintf("- Sending...\n"); if (SendString(compressed.get(), compressed_len)) { LOG.lprintf("-> success\n"); return true; } LOG.lprintf("-> Sending replay failed :(\n"); } else { LOG.lprintf("-> BZ2 compression failed.\n"); } SendUnsigned(0); return false; } else { LOG.lprintf("-> Already in replay mode, do not send replay\n"); } return true; }
int main() { size_t first_pid = 0; FdReader reader(0); Replay replay; #if defined(_WIN32) && !defined(MOZ_JEMALLOC3) malloc_init_hard(); #endif /* Read log from stdin and dispatch function calls to the Replay instance. * The log format is essentially: * <pid> <function>([<args>])[=<result>] * <args> is a comma separated list of arguments. * * The logs are expected to be preprocessed so that allocations are * attributed a tracking slot. The input is trusted not to have crazy * values for these slot numbers. * * <result>, as well as some of the args to some of the function calls are * such slot numbers. */ while (true) { Buffer line = reader.ReadLine(); if (!line) { break; } size_t pid = parseNumber(line.SplitChar(' ')); if (!first_pid) { first_pid = pid; } /* The log may contain data for several processes, only entries for the * very first that appears are treated. */ if (first_pid != pid) { continue; } Buffer func = line.SplitChar('('); Buffer args = line.SplitChar(')'); /* jemalloc_stats and free are functions with no result. */ if (func == Buffer("jemalloc_stats")) { replay.jemalloc_stats(args); continue; } else if (func == Buffer("free")) { replay.free(args); continue; } /* Parse result value and get the corresponding slot. */ Buffer dummy = line.SplitChar('='); Buffer dummy2 = line.SplitChar('#'); if (dummy || dummy2) { die("Malformed input"); } size_t slot_id = parseNumber(line); MemSlot& slot = replay[slot_id]; if (func == Buffer("malloc")) { replay.malloc(slot, args); } else if (func == Buffer("posix_memalign")) { replay.posix_memalign(slot, args); } else if (func == Buffer("aligned_alloc")) { replay.aligned_alloc(slot, args); } else if (func == Buffer("calloc")) { replay.calloc(slot, args); } else if (func == Buffer("realloc")) { replay.realloc(slot, args); } else if (func == Buffer("memalign")) { replay.memalign(slot, args); } else if (func == Buffer("valloc")) { replay.valloc(slot, args); } else { die("Malformed input"); } } return 0; }
void iwPlayReplay::PopulateTable() { ctrlTable* table = GetCtrl<ctrlTable>(0); unsigned short sortCol = table->GetSortColumn(); if(sortCol == 0xFFFF) sortCol = 0; bool sortDir = table->GetSortDirection(); table->DeleteAllItems(); unsigned numInvalid = 0; std::vector<std::string> replays = GetReplays(); for(std::vector<std::string>::iterator it = replays.begin(); it != replays.end(); ++it) { Replay replay; // Datei laden if(!replay.LoadHeader(*it)) { numInvalid++; continue; } // Zeitstamp benutzen std::string dateStr = TIME.FormatTime("%d.%m.%Y - %H:%i", &replay.save_time); // Spielernamen auslesen std::string tmp_players; for(unsigned char i = 0; i < replay.GetPlayerCount(); ++i) { // Was für ein State, wenn es nen KI Spieler oder ein normaler ist, muss das Zeug ausgelesen werden const BasePlayerInfo& curPlayer = replay.GetPlayer(i); if(curPlayer.isUsed()) { // und in unsere "Namensliste" hinzufügen (beim ersten Spieler muss kein Komma hin) if(!tmp_players.empty()) tmp_players += ", "; tmp_players += curPlayer.name; } } // Dateiname noch rausextrahieren aus dem Pfad bfs::path path = *it; if(!path.has_filename()) continue; std::string fileName = path.filename().string(); std::string lastGF = helpers::toString(replay.lastGF_); // Und das Zeug zur Tabelle hinzufügen table->AddRow(0, fileName.c_str(), dateStr.c_str(), tmp_players.c_str(), lastGF.c_str(), it->c_str()); } // Erst einmal nach Dateiname sortieren table->SortRows(sortCol, &sortDir); ctrlTextButton* btDelInvalid = GetCtrl<ctrlTextButton>(5); if(numInvalid == 0) btDelInvalid->SetVisible(false); else { btDelInvalid->SetVisible(true); char text[255]; snprintf(text, 255, _("Delete Invalid (%u)"), numInvalid); btDelInvalid->SetText(text); } }
///............................................................................................................................ /// _Tool_ convert ghosts to track's ghosts (less size and frame data) // put original ghosts into data/ghosts/original/*_ES.rpl // (ES, normal sim, 1st lap, no boost, use rewind with _Tool_ go back time) // time should be like in tracks.ini or less (last T= ) ///............................................................................................................................ void CGui::ToolGhostsConv() { LogO("ALL ghosts Convert ---------"); Replay ghost; TrackGhost trg; bool reverse = false; string sRev = reverse ? "_r" : ""; //for both dir sRev.. // foreach track for (int i=0; i < data->tracks->trks.size(); ++i) { string track = data->tracks->trks[i].name; if (track.substr(0,4) == "Test" && track.substr(0,5) != "TestC") continue; // load ghost.Clear(); trg.Clear(); string file = PATHMANAGER::TrkGhosts()+"/original/"+ track + sRev + "_ES.rpl"; if (!PATHMANAGER::FileExists(file)) {} //LogO("NOT found: "+file); else { LogO("--------- "+track+" ---------"); ghost.LoadFile(file); // convert MATHVECTOR<float,3> oldPos; float oldTime = 0.f; int num = ghost.GetNumFrames(), jmp = 0; for (int i=0; i < num; ++i) { const ReplayFrame& fr = ghost.GetFrame0(i); TrackFrame tf; tf.time = fr.time; tf.pos = fr.pos; tf.rot = fr.rot; //tf.rot[0] = fr.rot[0] * 32767.f; //.. tf.brake = fr.braking > 0 ? 1 : 0; tf.steer = fr.steer * 127.f; //LogO(toStr(fr.braking)+ " st " +fToStr(fr.steer,2,5)); #define Nth 3 if (i % Nth == Nth-1) /// write every n-th frame only trg.AddFrame(tf); // check for sudden pos jumps (rewind used but not with _Tool_ go back time !) if (i > 10 && i < num-1) // ignore jumps at start or end { float dist = (fr.pos - oldPos).MagnitudeSquared(); if (dist > 16.f) //1.f small { LogO("!Jump at "+CHud::StrTime2(fr.time)+" d "+fToStr(sqrt(dist),0)+"m"); ++jmp; } } // check vel at start if (i==50) { float dist = (fr.pos - oldPos).Magnitude(); float vel = 3.6f * dist / (fr.time - oldTime); bool bad = vel > 30; if (bad) LogO("!Vel at "+CHud::StrTime(fr.time)+" kmh "+fToStr(vel,0) + (bad ? " BAD":"")); } oldPos = fr.pos; oldTime = fr.time; } if (jmp > 0) LogO("!Jumps: "+toStr(jmp)); // save string fsave = PATHMANAGER::TrkGhosts()+"/"+ track + sRev + ".gho"; trg.header.ver = 1; trg.SaveFile(fsave); } } // check missing for (int i=0; i < data->tracks->trks.size(); ++i) { string track = data->tracks->trks[i].name; if (track.substr(0,4) == "Test" && track.substr(0,5) != "TestC") continue; string fsave = PATHMANAGER::TrkGhosts()+"/"+ track + sRev + ".gho"; if (!PATHMANAGER::FileExists(fsave)) LogO("MISSING for track: "+track); } }