summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFreeyorp <TheFreeYorp@NOSPAM.G.m.a.i.l.replace>2013-03-30 15:10:10 +1300
committerFreeyorp <TheFreeYorp@NOSPAM.G.m.a.i.l.replace>2013-03-30 15:10:10 +1300
commit821ebabae17b6339ec79b102215b584d23be77ab (patch)
tree0342b6d9387e8c6813258fa6087c71412144993e
parentce52475d9b640fa848333ec01340d6d2244bac7b (diff)
downloadmanavis-821ebabae17b6339ec79b102215b584d23be77ab.tar.gz
manavis-821ebabae17b6339ec79b102215b584d23be77ab.tar.bz2
manavis-821ebabae17b6339ec79b102215b584d23be77ab.tar.xz
manavis-821ebabae17b6339ec79b102215b584d23be77ab.zip
Rearrange layout, prototype stat charting
This is a work in progress, and will likely end up making use of custom charts.
-rw-r--r--css/style.css7
-rw-r--r--index.html64
-rw-r--r--js/mv.js84
3 files changed, 128 insertions, 27 deletions
diff --git a/css/style.css b/css/style.css
index 70482a7..0216c8e 100644
--- a/css/style.css
+++ b/css/style.css
@@ -78,3 +78,10 @@ body {
.help {
cursor: help;
}
+
+.blob {
+ background-color: #445566;
+ height: 100px;
+ width: 100px;
+ float: left;
+}
diff --git a/index.html b/index.html
index a30cc0a..2138f92 100644
--- a/index.html
+++ b/index.html
@@ -6,8 +6,59 @@
<div id="body">
<div id="side">
- <div id="date-chart" class="chart-root">
- <h3>Experience gain instances by Date <a class="reset" style="display: none;" href="javascript:mv.dateChart.filterAll();dc.redrawAll();">clear</a></h3>
+ <!-- Sketch things out. While this is technically functional and useful for prototyping, the sheer number of dimensions required will slow things to a standstill. -->
+ <div class="chart-root">
+ <h3>Experience gain instances by Stat Allocation</h3>
+ <table>
+ <tr>
+ <th></th>
+ <th>AGI</th>
+ <th>VIT</th>
+ <th>INT</th>
+ <th>DEX</th>
+ <th>LUK</th>
+ <tr>
+ <tr>
+ <th>STR</th>
+ <td><div id="agi-str" class="blob"></div></td>
+ <td><div id="vit-str" class="blob"></div></td>
+ <td><div id="int-str" class="blob"></div></td>
+ <td><div id="dex-str" class="blob"></div></td>
+ <td><div id="luk-str" class="blob"></div></td>
+ </tr>
+ <tr>
+ <th>AGI</th>
+ <td></td>
+ <td><div id="vit-agi" class="blob"></div></td>
+ <td><div id="int-agi" class="blob"></div></td>
+ <td><div id="dex-agi" class="blob"></div></td>
+ <td><div id="luk-agi" class="blob"></div></td>
+ </tr>
+ <tr>
+ <th>VIT</th>
+ <td></td>
+ <td></td>
+ <td><div id="int-vit" class="blob"></div></td>
+ <td><div id="dex-vit" class="blob"></div></td>
+ <td><div id="luk-vit" class="blob"></div></td>
+ </tr>
+ <tr>
+ <th>INT</th>
+ <td></td>
+ <td></td>
+ <td></td>
+ <td><div id="dex-int" class="blob"></div></td>
+ <td><div id="luk-int" class="blob"></div></td>
+ </tr>
+ <tr>
+ <th>DEX</th>
+ <td></td>
+ <td></td>
+ <td></td>
+ <td></td>
+ <td><div id="luk-dex" class="blob"></div></td>
+ </tr>
+ </table>
</div>
<div id="player-chart" class="chart-root">
<h3>Experience gain instances by Character ID <span class="help" title="Older to newer characters appear left to right, respectively.">[?]</span> <a class="reset" style="display: none;" href="javascript:mv.pcChart.filterAll();dc.redrawAll();">clear</a></h3>
@@ -15,9 +66,6 @@
<div id="blvl-chart" class="chart-root">
<h3>Experience gain instances by Character Base Level <a class="reset" style="display: none;" href="javascript:mv.blvlChart.filterAll();dc.redrawAll();">clear</a></h3>
</div>
- <div id="def-chart" class="chart-root">
- <h3>Definedness of records <span class="help" title="If logs are missing between server boot and the logs provided, not all information will be available for all records. Definedness of records falls into three categories. Records with undefined data; records with well defined data, but mixed in with records having undefined data, limiting validity of inferences; and records after any uncertain times, which are fully well defined. It is highly recommended that you filter results to only include records which are in fully well defined times; however, this may not always be possible.">[?]</span> <a class="reset" style="display: none;" href="javascript:mv.defChart.filterAll();dc.redrawAll();">clear</a></h3>
- </div>
</div>
<div id="main">
<!-- <div id="status">
@@ -37,9 +85,15 @@
</div>
</div>
</div>
+ <div id="date-chart" class="chart-root">
+ <h3>Experience gain instances by Date <a class="reset" style="display: none;" href="javascript:mv.dateChart.filterAll();dc.redrawAll();">clear</a></h3>
+ </div>
<div id="map-chart" class="chart-root">
<h3>Experience gain by Map <span class="help" title="Bubble size indicates instances of experience gain for that map. X axis position indicates the sum of level experience gain for that map. Y axis position indicates the sum of job experience gain for that map.">[?]</span> <a class="reset" style="display: none;" href="#">reset</a></h3>
</div>
+ <div id="def-chart" class="chart-root">
+ <h3>Definedness of records <span class="help" title="If logs are missing between server boot and the logs provided, not all information will be available for all records. Definedness of records falls into three categories. Records with undefined data; records with well defined data, but mixed in with records having undefined data, limiting validity of inferences; and records after any uncertain times, which are fully well defined. It is highly recommended that you filter results to only include records which are in fully well defined times; however, this may not always be possible.">[?]</span> <a class="reset" style="display: none;" href="javascript:mv.defChart.filterAll();dc.redrawAll();">clear</a></h3>
+ </div>
</div>
</div>
diff --git a/js/mv.js b/js/mv.js
index 82a7d5f..27d5fcc 100644
--- a/js/mv.js
+++ b/js/mv.js
@@ -85,6 +85,17 @@ var mv = {};
default: console.log(d, d.data); throw "Unknown definedness case (" + d.data.key + "); this shouldn't happen";
}
}
+ function Stat(str, agi, vit, int, dex, luk) {
+ this.str = str;
+ this.agi = agi;
+ this.vit = vit;
+ this.int = int;
+ this.dex = dex;
+ this.luk = luk;
+ this.blvl = stat.minLevelForStats(str, agi, vit, int, dex, luk);
+ }
+ Stat.prototype.valueOf = function() { return this.str * 1e15 + this.agi * 1e12 + this.vit * 1e9 + this.int * 1e6 + this.dex * 1e3 + this.luk; /*this.str + ":" + this.agi + ":" + this.vit + ":" + this.dex + ":" + this.int + ":" + this.luk*/; };
+ var nullstat = new Stat(0,0,0,0,0,0);
function parseRecords(data) {
var spl = data.split(/\r?\n/);
spl.forEach(function(e) {
@@ -102,7 +113,7 @@ var mv = {};
e: parseInt(d[6]),
j: parseInt(d[7]),
type: d[8],
- pcstat: pcstat[d[2]]
+ pcstat: pcstat[d[2]] ? pcstat[d[2]] : nullstat
});
if (pcstat[d[2]] == undefined && (!fullyDefinedCutoff || ts > fullyDefinedCutoff)) {
fullyDefinedCutoff = ts;
@@ -111,26 +122,18 @@ var mv = {};
}
d = e.match(/^(?:\d+\.\d+) PC(\d+) (?:\d+):(?:\d+),(?:\d+) STAT (\d+) (\d+) (\d+) (\d+) (\d+) (\d+) /);
if (d) {
- var s = {
- str: parseInt(d[2]),
- agi: parseInt(d[3]),
- vit: parseInt(d[4]),
- int: parseInt(d[5]),
- dex: parseInt(d[6]),
- luk: parseInt(d[7])
- };
- s.blvl = stat.minLevelForStats(s.str, s.agi, s.vit, s.int, s.dex, s.luk);
- pcstat[d[1]] = s;
+ pcstat[d[1]] = new Stat(parseInt(d[2]), parseInt(d[3]), parseInt(d[4]), parseInt(d[5]), parseInt(d[6]), parseInt(d[7]));
return;
}
});
- console.log(records.length);
}
+ var attrs = ["str", "agi", "vit", "int", "dex", "luk"];
var cfdata, all,
dateDim, dateGroup,
pcDim, pcGroup,
mapDim, mapGroup,
blvlDim, blvlGroup,
+ attrDims, attrGroups,
/*
* How well defined a record is.
* 0 -> Record contains undefined data
@@ -140,22 +143,36 @@ var mv = {};
defDim, defGroup;
/* The record files are set, do everything */
function makeHeap() {
- function a(p, d) { return { e: p.e + d.e, j: p.j + d.j, r: p.r + 1 }; }
- function s(p, d) { return { e: p.e - d.e, j: p.j - d.j, r: p.r - 1 }; }
- function z(p, d) { return { e: 0, j: 0, r: 0 }; }
cfdata = crossfilter(records);
- all = cfdata.groupAll().reduce(a, s, z);
+ mv.all = all = cfdata.groupAll().reduceCount();
dateDim = cfdata.dimension(function(d) { return d3.time.hour.round(d.date); });
dateGroup = dateDim.group().reduceCount();
pcDim = cfdata.dimension(function(d) { return d.pc; });
pcGroup = pcDim.group().reduceCount();
mapDim = cfdata.dimension(function(d) { return d.map; });
- mapGroup = mapDim.group().reduce(a, s, z);
- blvlDim = cfdata.dimension(function(d) { return d.pcstat ? d.pcstat.blvl : 0; });
+ mapGroup = mapDim.group().reduce(
+ function(p, d) { return { e: p.e + d.e, j: p.j + d.j, r: p.r + 1 }; },
+ function(p, d) { return { e: p.e - d.e, j: p.j - d.j, r: p.r - 1 }; },
+ function(p, d) { return { e: 0, j: 0, r: 0 }; }
+ );
+ blvlDim = cfdata.dimension(function(d) { return d.pcstat != nullstat ? d.pcstat.blvl : 0; });
blvlGroup = blvlDim.group().reduceCount();
- defDim = cfdata.dimension(function(d) { if (d.pcstat == undefined) { return 0; } if (d.date <= fullyDefinedCutoff) { return 1; } return 2; });
+ mv.attrDims = attrDims = {};
+ mv.attrGroups = attrGroups = {};
+ for (var y = 0; y != attrs.length - 1; ++y) {
+ attrDims[attrs[y]] = {};
+ attrGroups[attrs[y]] = {};
+ for (var x = y + 1; x != attrs.length; ++x) {
+ attrDims[attrs[y]][attrs[x]] = cfdata.dimension(function(h, l) { return function(d) { return Math.floor(d.pcstat[h] / 7) * 7 * 1e3 + Math.floor(d.pcstat[l] / 7) * 7; } }(attrs[y], attrs[x]));
+ attrGroups[attrs[y]][attrs[x]] = attrDims[attrs[y]][attrs[x]].group().reduceCount();
+ }
+ }
+// for (var i = 0; i != attrs.length; ++i) {
+// attrDims[attrs[i]] = cfdata.dimension(function(d) { return d.pcstat ? d.pcstat[attrs[i]] });
+// attrGroups[attrs[i]] = attrDims[attrs[i]].group().reduceCount();
+// }
+ defDim = cfdata.dimension(function(d) { if (d.pcstat == nullstat) { return 0; } if (d.date <= fullyDefinedCutoff) { return 1; } return 2; });
defGroup = defDim.group().reduceCount();
- defDim.filterExact(2);
/*
* The viewport is the bubble frame.
* - K: Map
@@ -192,7 +209,6 @@ var mv = {};
.title(function(d) { return d.key + ": " + d.value; })
.brushOn(true)
;
- console.log([pcDim.bottom(1)[0], pcDim.top(1)[0]])
mv.pcChart = dc.barChart("#player-chart")
.width(630)
.height(130)
@@ -235,7 +251,6 @@ var mv = {};
case 2: return "#6baed6";
default: throw "Definition chart: Color access key out of range!";
}})
- .filter(2)
;
mv.mapChart = dc.bubbleChart("#map-chart")
.width(700)
@@ -260,6 +275,31 @@ var mv = {};
.title(function(d) { return "Map " + d.key; })
.renderTitle(true)
;
+ mv.defChart.filter(2);
+ var c = function(v) { return "rgb(" + 25 * v + "," + 15 * v + "," + 3 * v + ")"; };
+ c.range = function() { return { length: 11 }; };
+ mv.attrCharts = {};
+ for (var y = 0; y != attrs.length - 1; ++y) {
+ mv.attrCharts[attrs[y]] = {};
+ for (var x = y + 1; x != attrs.length; ++x) {
+ mv.attrCharts[attrs[y]][attrs[x]] = dc.bubbleChart("#" + attrs[x] + "-" + attrs[y])
+ .width(100)
+ .height(100)
+ .margins({left: 0, right: 0, top: 0, bottom: 0})
+ .dimension(attrDims[attrs[y]][attrs[x]])
+ .group(attrGroups[attrs[y]][attrs[x]])
+ .colors(c)
+ .colorAccessor(function(d, i){ return d.value; })
+ .keyAccessor(function(k) { return function(d) { return d.key % 1e3; }; }(attrs[x]))
+ .valueAccessor(function(k) { return function(d) { return Math.floor(d.key / 1e3); }; }(attrs[y]))
+ .radiusValueAccessor(function(d) { return 3; })
+ .x(d3.scale.linear().domain([1, 99]))
+ .y(d3.scale.linear().domain([1, 99]))
+ .r(d3.scale.identity())
+ .renderLabel(false)
+ ;
+ }
+ }
dc.renderAll();
}
})();