Files
gtav-src/tools_ng/web/cert/js/session_timeline.js
T
2025-09-29 00:52:08 +02:00

515 lines
15 KiB
JavaScript
Executable File

var sessions = null;
// How to convert this to local?
var dateSessionFormat = d3.time.format("%H:%M:%S %d/%m/%Y");
var defaultTimelineHeight = $("#content").height() - 2.5 * $("#header").height();
//Object used for local storage of the user selections
var pageData = {
platform: "PS3",
gameType: $("select#session-game-type-select option:eq(0)").val(),
gamer: "",
//start: dateInputFormat(new Date()),
//end: dateInputFormat(new Date()),
}
//set true for disabled filter
var headerAndFilters = {
headerType: "header-sc", // social club filtering header
disabledFields: // disables header fields
[
false, // platforms
false, // locations
false, // age
false, // gamers
false, // game-types
false, // dates+builds
],
};
//Use this to map rest event names to more human readable ones and to respective css classes
var eventsMap = {
TelemetryEventDto: {name: "Telemetry Event", css: "telemetry-event"} ,
PositionalEventDto: {name: "Positional Event", css: "positional-event"},
WeaponEventDto: {name: "Weapon Event", css: "weapon-event"},
DeathEventDto: {name: "Death Event", css: "death-event"},
VehicleEventDto: {name: "Vehicle Event", css: "vehicle-event"},
WantedLevelEventDto: {name: "Wanted Level Event", css: "wanted-level-event"},
EmergencyServicesEventDto: {name: "Emergency Services Event", css: "emergency-services-event"},
CutsceneEventDto: {name: "Cutscene Event", css: "cutscene-event"},
MissionEventDto: {name: "Mission Event", css: "mission-event"},
RadioStationEventDto: {name: "Radio Station Event", css: "radio-station-event"},
}
function initSessionTimelinePage() {
// function from generic.js, variable from config file
initHeaderAndFilters(headerAndFilters);
var localData = retrieveLocalObject(config.currentFilename);
pageData = (localData) ? localData : pageData;
//block();
/*
// Gametypes List
$.ajax({
url: config.restHost + config.gametypesAll,
type: "GET",
data: {},
dataType: "xml",
success: function(xml, textStatus, jqXHR) {
var gametypes = convertGametypesXml(xml);
$.each(gametypes, function(i, gametype) {
$("select#session-game-type-select").append(
$("<option />")
.text(gametype.Value)
.val(gametype.Value)
.attr("selected", function() {
return (pageData && pageData.gameType == gametype.Value) ? "selected" : false;
})
);
});
},
error: function (xhr, ajaxOptions, thrownError) {
console.error(this.url + "\n" + ajaxOptions + " " + xhr.status + " " + thrownError);
}
});
*/
var gameTypes = getGameTypes();
$.each(gameTypes, function(i, gametype) {
$("select#session-game-type-select").append(
$("<option />")
.text(gametype.Name)
.val(gametype.Name)
.attr("selected", function() {
return (pageData && pageData.gameType == gametype.Name) ? "selected" : false;
})
);
});
// Platforms List
/*
$.ajax({
url: config.restHost + config.platformsAll,
type: "GET",
data: {},
dataType: "xml",
success: function(xml, textStatus, jqXHR) {
var platforms = convertPlatformsXml(xml);
$.each(platforms, function(i, platform) {
$("select#session-platform").append(
$("<option />")
.text(platform.Value)
.val(platform.Value)
.attr("selected", function() {
return (pageData && pageData.platform == platform.Value) ? "selected" : false;
})
);
});
updateGamersList();
},
error: function (xhr, ajaxOptions, thrownError) {
console.error(this.url + "\n" + ajaxOptions + " " + xhr.status + " " + thrownError);
}
});
*/
var platforms = getPlatforms();
$.each(platforms, function(i, platform) {
$("select#session-platform").append(
$("<option />")
.text(platform.Name)
.val(platform.Name)
.attr("selected", function() {
return (pageData && pageData.platform == platform.Name) ? "selected" : false;
})
);
});
updateGamersList();
/*
if (pageData && pageData.start)
$("input#start").val(pageData.start);
if (pageData && pageData.end)
$("input#end").val(pageData.end);
*/
//unBlock();
// Bind events to selectors
$("select#session-platform").change(function() {
pageData.platform = $(this).val();
storeLocalObject(config.currentFilename, pageData);
updateGamersList();
resetSessionList();
resetTimeline();
});
$("select#platform-gamer").change(function() {
pageData.gamer = $(this).val();
storeLocalObject(config.currentFilename, pageData);
$("#go").trigger("click");
});
/*
$("input#start").datepicker({
dateFormat: "dd/mm/yy",
});
$("input#end").datepicker({
dateFormat: "dd/mm/yy",
});
*/
$("#go").click(function() {
// store the dates
/*
pageData.start = $("input#start").val();
pageData.end = $("input#end").val();
storeLocalObject(config.currentFilename, pageData);
*/
// get the session list
updateSessions();
});
// Trigger click() on go button when pressing enter
$("#sub-header input").keypress(function(e) {
if (e.which == 13) {
$("#go").trigger("click");
}
});
$("select#session-game-type-select").change(function() {
pageData.gameType = $(this).val();
storeLocalObject(config.currentFilename, pageData);
updateSessionsList();
});
$("select#session-list-select").change(function() {
retrieveSessionSummary($("select#session-list-select :selected"));
});
$("#timeline").masonry({
itemSelector : ".item",
// isAnimated: true
});
// Post header filter addition
$("#filter").click(function() {
$("#go").trigger("click");
resetTimeline();
});
initTimeline();
}
function initTimeline() {
$("#timeline").height(defaultTimelineHeight);
}
function updateTimelineTime(startDate, endDate) {
$("#timeline-start-time").html(startDate);
$("#timeline-end-time").html(endDate);
}
function resetTimeline() {
$("#timeline div.item").remove();
initTimeline();
updateTimelineTime("", "");
}
function updateGamersList() {
block();
// Gamers List
$.ajax({
url: config.restHost + config.gamersPath + $("select#session-platform :selected").val(),
type: "GET",
data: {},
dataType: "xml",
success: function(xml, textStatus, jqXHR) {
var gamers = convertGamersXml(xml);
$("select#platform-gamer").empty();
$.each(gamers, function(i, gamer) {
$("select#platform-gamer").append(
$("<option />")
.text(gamer.GamerTag)
.val(gamer.GamerTag)
.attr("selected", function() {
return (pageData && pageData.gamer == gamer.GamerTag) ? "selected" : false;
})
);
});
unBlock();
// try to fetch the sessions list (by firing the button click event) if everything is set
$("#go").trigger("click");
},
error: function (xhr, ajaxOptions, thrownError) {
unBlock();
console.error(this.url + "\n" + ajaxOptions + " " + xhr.status + " " + thrownError);
}
});
}
function updateSessions() {
var platform = $("select#session-platform :selected").val();
var gamer = $("select#platform-gamer :selected").val();
// Convert each inserted date to ISO string that the endpoint understands
var start = new Date(config.dateInputFormat.parse($("input#date-from").val())).toISOString();
//console.log(new Date(dateInputFormat.parse($("input#start").val())).toString());
var end = new Date(config.dateInputFormat.parse($("input#date-to").val())).toISOString();
//console.log(new Date(dateInputFormat.parse($("input#end").val())).toString());
if (platform && gamer && start && end) {
block();
$.ajax({
url: config.restHost + config.gamersPath + platform + "/" + gamer + config.sessionsSubPath,
type: "GET",
data: {
start: start,
end: end,
},
dataType: "xml",
success: function(xml, textStatus, jqXHR) {
sessions = convertSessionsXml(xml);
updateSessionsList();
},
error: function (xhr, ajaxOptions, thrownError) {
console.error(this.url + "\n" + ajaxOptions + " " + xhr.status + " " + thrownError);
},
complete: function() {
unBlock();
resetTimeline();
}
});
}
}
function updateSessionsList() {
var gameType = $("select#session-game-type-select :selected").val();
var sessionsList = [];
if (!sessions)
return;
if (gameType == $("select#session-game-type-select option:eq(0)").val()) {
sessionsList = sessions.SingleplayerSessions;
}
else if (gameType == $("select#session-game-type-select option:eq(1)").val()) {
sessionsList = sessions.MultiplayerSession;
}
resetSessionList();
$.each(sessionsList, function(i, session) {
$("select#session-list-select").append(
$('<option />')
.text(++i + ". " + dateSessionFormat(new Date(session.Start))
+ " - " + dateSessionFormat(new Date(session.End)))
.val(session.Id)
.data({"start" : dateSessionFormat(new Date(session.Start)),
"end" : dateSessionFormat(new Date(session.End))
})
);
});
}
function resetSessionList() {
$("select#session-list-select").empty();
}
function retrieveSessionSummary(sessionElement) {
resetTimeline();
updateTimelineTime("<br />" + sessionElement.data("start"),
"<br />" + sessionElement.data("end"));
block();
$.ajax({
url: config.restHost + config.sessionsSummaryPath,
type: "GET",
data: {
gameType: $("select#session-game-type-select :selected").val(),
gamerId: sessions.GamerId,
sessionId: sessionElement.val()
},
dataType: "xml",
success: function(xml, textStatus, jqXHR) {
var sessionEvents = convertEventsXml(xml);
drawTimeline(sessionEvents);
},
error: function (xhr, ajaxOptions, thrownError) {
console.error(this.url + "\n" + ajaxOptions + " " + xhr.status + " " + thrownError);
},
complete: unBlock
});
}
function drawTimeline(sessionEvents) {
$.each(sessionEvents, function(i, event) {
var datetime = dateSessionFormat(new Date(event.Timestamp));
var header = "<div class='item-header " + eventsMap[event.Name].css + "'>" + eventsMap[event.Name].name
+ "<br />" + datetime + "</div>";
var html = header + "<div><span class='item-label'>Type : </span>" + event.Metric + "</div>";
if (event.WeaponName)
html += ("<div><span class='item-label'>Weapon Name : </span>" + event.WeaponName + "</div>");
if (event.VehicleName)
html += ("<div><span class='item-label'>Vehicle Name : </span>" + event.VehicleName + "</div>");
//html += ("Vehicle Name : " + event.VehicleName + "<br/>");
if (event.Location.x && event.Location.y)
html += ("<div><span class='item-label'>Location : </span>(" + event.Location.x + ", " + event.Location.y + ")</div>");
//html += ("Location : (" + event.Location.x + ", " + event.Location.y + ")<br/>");
if (event.KillerName)
//html += ("Killer Name : " + event.KillerName + "<br/>");
html += ("<div><span class='item-label'>Killer Name : </span>" + event.KillerName + "</div>");
if (event.VictimName)
//html += ("Victim Name : " + event.VictimName + "<br/>");
html += ("<div><span class='item-label'>Victim Name : </span>" + event.VictimName + "</div>");
if (event.WantedLevel)
//html += ("Wanted Level : " + event.WantedLevel + "<br/>");
html += ("<div><span class='item-label'>Wanted Level : </span>" + event.WantedLevel + "</div>");
if (event.CutsceneName)
//html += ("Cutscene Name : " + event.CutsceneName + "<br/>");
html += ("<div><span class='item-label'>Cutscene Name : </span>" + event.CutsceneName + "</div>");
if (event.MissionName)
//html += ("Mission Name : " + event.MissionName + "<br/>");
html += ("<div><span class='item-label'>Mission Name : </span>" + event.MissionName + "</div>");
if (event.RadioStationName)
html += ("<div><span class='item-label'>Radio Station Name : </span>" + event.RadioStationName + "</div>");
$("#timeline").append(
$("<div />")
.addClass("item")
.html(html)
);
});
// Reload the masonry positions / animation
if (sessionEvents.length > 0)
$("#timeline").masonry("reload");
$("#timeline").find(".item").each(function(i, item) {
if($(item).css("left") == "0px") {
//if((i%2) == 0) {
html = "<span class='right-arrow'></span>";
$(item).prepend(html);
$(item).find(".item-header").addClass("bg-right");
}
else {
html = "<span class='left-arrow'></span>";
$(item).prepend(html);
$(item).css("margin-top", "2.2em");
$(item).find(".item-header").addClass("bg-left");
// IE hack
if ($.browser.msie)
$(item).find(".left-arrow").css("margin-left", "-24px");
}
});
}
// All these convertXml() functions will be removed once the data are returned in json
function convertGamersXml(xml) {
var elementsArray = [];
$(xml).find("Gamer").each(function(){
var gamer = {
Id: $(this).find("Id").text(),
CreatedOn: $(this).find("CreatedOn").text(),
GamerTag: $(this).find("GamerTag").text(),
Platform: $(this).find("Platform").attr("Value"),
};
elementsArray.push(gamer);
});
return elementsArray;
}
function convertSessionsXml(xml) {
var gamerId = $(xml).find("GamerId").text();
var singleplayerSessions = [];
$(xml).find("SingleplayerSession").each(function() {
var singleplayerSession = {
Id: $(this).find("Id").text(),
Start: $(this).find("Start").text(),
End: $(this).find("End").text()
};
singleplayerSessions.push(singleplayerSession);
});
var multiplayerSessions = [];
$(xml).find("MultiplayerSession").each(function() {
var multiplayerSession = {
Id: $(this).find("Id").text(),
Start: $(this).find("Start").text(),
End: $(this).find("End").text()
};
multiplayerSessions.push(multiplayerSession);
});
return {
GamerId: gamerId,
SingleplayerSessions: singleplayerSessions,
MultiplayerSession: multiplayerSessions
};
}
function convertEventsXml(xml) {
var elementsArray = [];
$(xml).find("Items").children().each(function() {
var event = {
Name: $(this).prop("tagName"),
Timestamp: $(this).find("Timestamp").text(),
Metric: $(this).find("Metric").find("Value").text(),
WeaponName: $(this).find("WeaponName").text(),
VehicleName: $(this).find("VehicleName").text(),
Location: {
x: parseFloat($(this).find("Location").attr("x")),
y: parseFloat($(this).find("Location").attr("y"))
},
KillerName: $(this).find("KillerName").text(),
VictimName: $(this).find("VictimName").text(),
WantedLevel: parseInt($(this).find("WantedLevel").text()),
CutsceneName: $(this).find("CutsceneName").text(),
MissionName: $(this).find("MissionName").text(),
RadioStationName: $(this).find("RadioStationName").text(),
};
//console.log(event);
elementsArray.push(event);
});
return elementsArray;
}