' +
'
' +
'
'+
'
' +
'
' +
'
Keys
' +
' - TAB - When split switches selected blob
' +
' - A - Toggle Acid mode
' +
' - C - Toggle display of visual cues
' +
' - G - Toggle new grazer (better overall)
' +
' - H - Toggle old grazer (slightly better early on)' +
'
- E - Fire at virus near cursor
' +
' - R - Fire at virus near selected blob (virus is highlighted in red)
' +
' - M - Enables/Disables mouse input
' +
' - Z - Zoom in/zoom out
' +
' - 1...7 - Selecte n-th blob sorted by size
' +
' - Click - Lock currently selected blob (if blob locking enabled)
' +
' - S - Unlock all blobs (if blob locking enabled)
' +
'
' +
'
' +
'
' +
'
');
jQuery(".agario-profile-panel").appendTo("#XPArea");
jQuery("#statsTab").click(function(){OnShowOverlay(false);});
function LS_getValue(aKey, aDefault) {
var val = localStorage.getItem(__STORAGE_PREFIX + aKey);
if (null === val && 'undefined' != typeof aDefault) return aDefault;
return val;
}
function LS_setValue(aKey, aVal) {
localStorage.setItem(__STORAGE_PREFIX + aKey, aVal);
}
function GetRgba(hex_color, opacity)
{
var patt = /^#([\da-fA-F]{2})([\da-fA-F]{2})([\da-fA-F]{2})$/;
var matches = patt.exec(hex_color);
return "rgba("+parseInt(matches[1], 16)+","+parseInt(matches[2], 16)+","+parseInt(matches[3], 16)+","+opacity+")";
}
function secondsToHms(d)
{
d = Number(d);
var h = Math.floor(d / 3600);
var m = Math.floor(d % 3600 / 60);
var s = Math.floor(d % 3600 % 60);
return ((h > 0 ? h + ":" + (m < 10 ? "0" : "") : "") + m + ":" + (s < 10 ? "0" : "") + s);
}
var chart = null;
var chart_data = [];
var num_cells_data = [];
var chart_counter = 0;
var stat_canvas = null;
var stats = null;
var my_cells = null;
var my_color = "#ff8888";
var pie = null;
var stats_chart;
var display_chart = LS_getValue('display_chart', 'false') === 'true';
var display_stats = LS_getValue('display_stats', 'false') === 'true';
function AppendCheckbox(e, id, label, checked, on_change)
{
e.append('
');
jQuery('#'+id).attr('checked', checked);
jQuery('#'+id).change(function(){
on_change(!!this.checked);
});
on_change(checked);
}
function AppendCheckboxP(e, id, label, checked, on_change)
{
e.append('
'+label+'
');
jQuery('#'+id).attr('checked', checked);
jQuery('#'+id).change(function(){
on_change(!!this.checked);
});
on_change(checked);
}
function OnChangeDisplayChart(display)
{
LS_setValue('display_chart', display ? 'true' : 'false');
display_chart = display;
display ? jQuery('#chart-container').show() : jQuery('#chart-container').hide();
}
function OnChangeDisplayStats(display)
{
LS_setValue('display_stats', display ? 'true' : 'false');
display_stats = display;
RenderStats(false);
}
function ResetChart()
{
chart = null;
chart_data.length = 0;
num_cells_data.length = 0;
chart_counter = 0;
jQuery('#chart-container').empty();
}
function UpdateChartData(mass)
{
chart_counter++;
if (chart_counter%chart_update_interval > 0)
return false;
num_cells_data.push({
x: chart_counter,
y: my_cells.length
});
chart_data.push({
x: chart_counter,
y: mass/100
});
return true;
}
function CreateChart(e, color, interactive)
{
return new CanvasJS.Chart(e,{
interactivityEnabled: false,
title: null,
axisX:{
valueFormatString: " ",
lineThickness: 0,
tickLength: 0
},
axisY:{
lineThickness: 0,
tickLength: 0,
gridThickness: 2,
gridColor: "white",
labelFontColor: "white"
},
backgroundColor: "rgba(0,0,0,0.2)",
data: [{
type: "area",
color: color,
dataPoints: chart_data
}]
});
}
function UpdateChart(mass, color)
{
my_color = color;
if (chart === null)
chart = CreateChart("chart-container", color, false);
if (UpdateChartData(mass) && display_chart)
chart.render();
jQuery('.canvasjs-chart-credit').hide();
}
function ResetStats()
{
stats = {
pellets: {num:0, mass:0},
w: {num:0, mass:0},
cells: {num:0, mass:0},
viruses: {num:0, mass:0},
birthday: Date.now(),
time_of_death: null,
high_score: 0,
top_slot: Number.POSITIVE_INFINITY,
gains: {},
losses: {},
};
}
function OnGainMass(me, other)
{
var mass = other.size * other.size;
if (other.isVirus){
stats.viruses.num++;
stats.viruses.mass += mass; //TODO: shouldn't add if game mode is teams
sfx_event("virushit");
}
else if (Math.floor(mass) <= 400 && !other.name){
stats.pellets.num++;
stats.pellets.mass += mass;
sfx_event("pellet");
}
// heuristic to determine if mass is 'w', not perfect
else if (!other.name && mass <= 1444 && (mass >= 1369 || (other.x == other.ox && other.y == other.oy))){
//console.log('w', mass, other.name, other);
if (other.color != me.color){ //don't count own ejections, again not perfect
stats.w.num++;
stats.w.mass += mass;
}
sfx_event("eat");
}
else {
//console.log('cell', mass, other.name, other);
var key = other.name + ':' + other.color;
stats.cells.num++;
stats.cells.mass += mass;
if (stats.gains[key] == undefined)
stats.gains[key] = {num: 0, mass: 0};
stats.gains[key].num++;
stats.gains[key].mass += mass;
sfx_event("eat");
}
}
function OnLoseMass(me, other)
{
var mass = me.size * me.size;
var key = other.name + ':' + other.color;
if (stats.losses[key] == undefined)
stats.losses[key] = {num: 0, mass: 0};
stats.losses[key].num++;
stats.losses[key].mass += mass;
sfx_event("eat");
}
function DrawPie(pellet, w, cells, viruses)
{
var total = pellet + w + cells + viruses;
pie = new CanvasJS.Chart("pieArea", {
title: null,
animationEnabled: false,
legend:{
verticalAlign: "center",
horizontalAlign: "left",
fontSize: 20,
fontFamily: "Helvetica"
},
theme: "theme2",
data: [{
type: "pie",
startAngle:-20,
showInLegend: true,
toolTipContent:"{legendText} {y}%",
dataPoints: [
{ y: 100*pellet/total, legendText:"pellets"},
{ y: 100*cells/total, legendText:"cells"},
{ y: 100*w/total, legendText:"w"},
{ y: 100*viruses/total, legendText:"viruses"},
]
}]
});
pie.render();
}
function GetTopN(n, p){
var r = [];
var a = Object.keys(stats[p]).sort(function(a, b) {return -(stats[p][a].mass - stats[p][b].mass)});
for (var i = 0; i < n && i < a.length; ++i){
var key = a[i];
var mass = stats[p][key].mass;
var name = key.slice(0,key.length-8);
if (!name) name = "An unnamed cell";
var color = key.slice(key.length-7);
r.push({name:name, color:color, mass:Math.floor(mass/100)});
}
return r;
}
function AppendTopN(n, p, list) {
var a = GetTopN(n,p);
for (var i = 0; i < a.length; ++i){
var text = a[i].name + ' (' + (p == 'gains' ? '+' : '-') + a[i].mass + ' mass)';
list.append('
' + text + '');
};
return a.length > 0;
}
function ShowZCStats(){
if(cobbler.showZcStats){
jQuery("#ZCOverlay").fadeIn();
jQuery('#statsTab').tab('show');
}
}
function DrawStats(game_over) {
if (!stats) return;
jQuery('#statArea').empty();
jQuery('#pieArea').empty();
jQuery('#gainArea').empty();
jQuery('#lossArea').empty();
jQuery('#chartArea').empty();
//jQuery('#statsTab').tab('show');
if (game_over){
stats.time_of_death = Date.now();
sfx_play(1);
ShowZCStats();
if(window.cobbler.autoRespawn && window.cobbler.grazingMode){setTimeout(function(){jQuery(".btn-play-guest").click();},3000);}
}
var time = stats.time_of_death ? stats.time_of_death : Date.now();
var seconds = (time - stats.birthday)/1000;
var list = jQuery('
');
list.append('- Game time: ' + secondsToHms(seconds) + '
');
list.append('- High score: ' + ~~(stats.high_score/100) + '
');
if (stats.top_slot == Number.POSITIVE_INFINITY){
list.append('- You didn\'t make the leaderboard
');
}
else {
list.append('- Leaderboard max: ' + stats.top_slot + '
');
}
list.append('- ' + stats.pellets.num + " pellets eaten (" + ~~(stats.pellets.mass/100) + ' mass)
');
list.append('- ' + stats.cells.num + " cells eaten (" + ~~(stats.cells.mass/100) + ' mass)
');
list.append('- ' + stats.w.num + " masses eaten (" + ~~(stats.w.mass/100) + ' mass)
');
list.append('- ' + stats.viruses.num + " viruses eaten (" + ~~(stats.viruses.mass/100) + ' mass)
');
jQuery('#statArea').append('Game Summary
');
jQuery('#statArea').append(list);
DrawPie(stats.pellets.mass, stats.w.mass, stats.cells.mass, stats.viruses.mass);
jQuery('#gainArea').append('Top Gains
');
list = jQuery('');
if (AppendTopN(5, 'gains', list))
jQuery('#gainArea').append(list);
else
jQuery('#gainArea').append('- You have not eaten anybody
');
jQuery('#lossArea').append('Top Losses
');
list = jQuery('');
if (AppendTopN(5, 'losses', list))
jQuery('#lossArea').append(list);
else
jQuery('#lossArea').append('');
if (stats.time_of_death !== null){
jQuery('#chartArea').height(200);
jQuery('#chartArea')[0].height=200;
stat_chart = CreateChart('chartArea', my_color, true);
var scale = Math.max.apply(Math,chart_data.map(function(o){return o.y;}))/16;
var scaled_data = num_cells_data.map(function(a){return {x:a.x, y:a.y*scale};});
stat_chart.options.data.push({type: "line", dataPoints: scaled_data, toolTipContent:" "});
stat_chart.render();
}
else {
jQuery('#chartArea').height(200);
jQuery('#chartArea')[0].height=200;
}
}
var styles = {
heading: {font:"30px Ubuntu", spacing: 41, alpha: 1},
subheading: {font:"25px Ubuntu", spacing: 31, alpha: 1},
normal: {font:"17px Ubuntu", spacing: 21, alpha: 0.6}
};
var g_stat_spacing = 0;
var g_display_width = 220;
var g_layout_width = g_display_width;
function AppendText(text, context, style) {
context.globalAlpha = styles[style].alpha;
context.font = styles[style].font;
g_stat_spacing += styles[style].spacing;
var width = context.measureText(text).width;
g_layout_width = Math.max(g_layout_width, width);
context.fillText(text, g_layout_width/2 - width/2, g_stat_spacing);
}
function RenderStats(reset) {
if (reset) g_layout_width = g_display_width;
if (!display_stats || !stats) return;
g_stat_spacing = 0;
var gains = GetTopN(3, 'gains');
var losses = GetTopN(3, 'losses');
var height = 30 + styles['heading'].spacing + styles['subheading'].spacing * 2 + styles['normal'].spacing * (4 + gains.length + losses.length);
stat_canvas = document.createElement("canvas");
var scale = Math.min(g_display_width, .3 * window.innerWidth) / g_layout_width;
stat_canvas.width = g_layout_width * scale;
stat_canvas.height = height * scale;
var context = stat_canvas.getContext("2d");
context.scale(scale, scale);
context.globalAlpha = .4;
context.fillStyle = "#000000";
context.fillRect(0, 0, g_layout_width, height);
context.fillStyle = "#FFFFFF";
AppendText("Stats", context, 'heading');
var text = stats.pellets.num + " pellets eaten (" + ~~(stats.pellets.mass/100) + ")";
AppendText(text, context,'normal');
text = stats.w.num + " mass eaten (" + ~~(stats.w.mass/100) + ")";
AppendText(text, context,'normal');
text = stats.cells.num + " cells eaten (" + ~~(stats.cells.mass/100) + ")";
AppendText(text, context,'normal');
text = stats.viruses.num + " viruses eaten (" + ~~(stats.viruses.mass/100) + ")";
AppendText(text, context,'normal');
AppendText("Top Gains",context,'subheading');
for (var j = 0; j < gains.length; ++j){
text = (j+1) + ". " + gains[j].name + " (" + gains[j].mass + ")";
context.fillStyle = gains[j].color;
AppendText(text, context,'normal');
}
context.fillStyle = "#FFFFFF";
AppendText("Top Losses",context,'subheading');
for (var j = 0; j < losses.length; ++j){
text = (j+1) + ". " + losses[j].name + " (" + losses[j].mass + ")";
context.fillStyle = losses[j].color;
AppendText(text, context,'normal');
}
}
jQuery(unsafeWindow).resize(function() {
RenderStats(false);
});
unsafeWindow.OnGameStart = function(cells) {
my_cells = cells;
ResetChart();
ResetStats();
RenderStats(true);
sfx_play(0);
};
unsafeWindow.OnShowOverlay = function(game_in_progress) {
DrawStats(!game_in_progress);
};
unsafeWindow.OnUpdateMass = function(mass) {
stats.high_score = Math.max(stats.high_score, mass);
UpdateChart(mass, GetRgba(my_cells[0].color,0.4));
};
unsafeWindow.OnCellEaten = function(predator, prey) {
if (!my_cells) return;
if (my_cells.indexOf(predator) != -1){
OnGainMass(predator, prey);
RenderStats(false);
}
if (my_cells.indexOf(prey) != -1){
OnLoseMass(prey, predator);
RenderStats(false);
}
};
unsafeWindow.OnLeaderboard = function(position) {
stats.top_slot = Math.min(stats.top_slot, position);
};
unsafeWindow.OnDraw = function(context) {
display_stats && stat_canvas && context.drawImage(stat_canvas, 10, 10);
};
// ====================== SFX System ==============================================================
//sfx play on event (only one of each sfx can play - for sfx that won't overlap with itself)
var ssfxlist = [
'spawn',
'gameover'
];
var ssfxs = [];
for (i=0;iOptions");
AppendCheckbox(col1, 'showZcStats-checkbox', ' Show ' + zc_short_name + ' Stats On Death', window.cobbler.showZcStats, function(val){window.cobbler.showZcStats = val;});
col1.append("Modes
");
AppendCheckbox(col1, 'isacid-checkbox', ' Enable Acid Mode', window.cobbler.isAcid, function(val){window.cobbler.isAcid = val;});
col1.append("Visual
");
AppendCheckbox(col1, 'trailingtail-checkbox', ' Draw Trailing Tail', window.cobbler.drawTail, function(val){window.cobbler.drawTail = val;});
AppendCheckbox(col1, 'splitguide-checkbox', ' Draw Split Guide', window.cobbler.splitGuide, function(val){window.cobbler.splitGuide = val;});
AppendCheckbox(col1, 'absorptionguide-checkbox', ' Draw Absorption Guide', window.cobbler.absorptionGuide, function(val){window.cobbler.absorptionGuide = val;});
AppendCheckbox(col1, 'namesunder-checkbox', ' Names under blobs', window.cobbler.namesUnderBlobs, function(val){window.cobbler.namesUnderBlobs = val;});
AppendCheckbox(col1, 'gridlines-checkbox', ' Show Gridlines', window.cobbler.gridLines, function(val){window.cobbler.gridLines = val;});
AppendCheckbox(col1, 'mousecoordlines-checkbox', ' Show Mouse Lines', window.cobbler.mouseCoordLines, function(val){window.cobbler.mouseCoordLines = val;});
col1.append("Stats
");
AppendCheckbox(col1, 'chart-checkbox', ' Show in-game chart', display_chart, OnChangeDisplayChart);
AppendCheckbox(col1, 'stats-checkbox', ' Show in-game stats', display_stats, OnChangeDisplayStats);
col1.append("Features
");
AppendCheckbox(col1, 'feature-click-fire', ' Click to fire @ virus', window.cobbler.rightClickFires, function(val) {window.cobbler.rightClickFires = val;});
AppendCheckbox(col1, 'feature-blob-lock', ' Click to lock blob', window.cobbler.enableBlobLock, function(val) {window.cobbler.enableBlobLock = val;});
AppendCheckbox(col1, 'feature-blob-lock-next', ' Switch blob on lock', window.cobbler.nextOnBlobLock, function(val) {window.cobbler.nextOnBlobLock = val;});
var col2 = $("#col2");
col2.append('Debug Level
' +
'' +
'' +
'' +
'
');
$('input[name="DebugLevel"]:radio[value='+window.cobbler.debugLevel +']').parent().addClass("active");
$('input[name="DebugLevel"]').change( function() {window.cobbler.debugLevel = $(this).val();});
col2.append('Virus Popper
Milliseconds between shots
ms
145ms = 7 shots per second. Lower values are faster but less stable.
');
$('#mspershot-textbox').on('input propertychange paste', function() {
var newval = parseInt(this.value);
if(!_.isNaN(newval) && newval > 0 && newval <= 2000) {
$("#mspershot-group").removeClass('has-error');
cobbler.msDelayBetweenShots = newval;
}
else{
$("#mspershot-group").addClass('has-error');
}
});
col2.append('Grazer
');
var grazerChecks = $("#grazer-checks");
AppendCheckbox(grazerChecks, 'autorespawn-checkbox', ' Grazer Auto-Respawns', window.cobbler.autoRespawn, function(val){window.cobbler.autoRespawn = val;});
AppendCheckbox(grazerChecks, 'option5', ' Visualize Grazer', window.cobbler.visualizeGrazing, function(val){window.cobbler.visualizeGrazing = val;});
col2.append('Hybrid Grazer
' +
'' +
'
' +
'Starts with old grazer and at specified mass switches to new grazer
');
$('#hybrid-checkbox').change(function(){
if(!!this.checked){
$('#hybrid-textbox').removeAttr("disabled");
} else {
$('#hybrid-textbox').attr({disabled:"disabled"})
}
cobbler.grazerHybridSwitch = !!this.checked;
});
if(cobbler.grazerHybridSwitch){$('#hybrid-checkbox').prop('checked', true);}else{ $('#hybrid-textbox').attr({disabled:"disabled"})}
$('#hybrid-textbox').on('input propertychange paste', function() {
var newval = parseInt(this.value);
if(!_.isNaN(newval)) {
$("#hybrid-group").removeClass('has-error');
cobbler.grazerHybridSwitchMass = newval;
}
else{
$("#hybrid-group").addClass('has-error');
}
});
var col3 = $("#col3");
col3.append("Sound
");
col3.append('Sound Effects
');
// Ugly ass hack to fix effects of official code loading before mod
//$("#canvas").remove();
//$("body").prepend('');