mirror of
https://github.com/plan-player-analytics/Plan.git
synced 2024-12-27 11:37:41 +01:00
Fix Refresh counters
Remove Useless Config settings Remove Unused Code Update Players page to use HighCharts Update Performance Graphs to use 2 different Axis CPU Avg shows Unavailable if Negative
This commit is contained in:
parent
f9af3eee03
commit
f8434b6c81
@ -11,7 +11,6 @@ import org.bukkit.Server;
|
||||
*/
|
||||
public class ServerVariableHolder {
|
||||
|
||||
private final int maxPlayers;
|
||||
private final String ip;
|
||||
private final boolean usingPaper;
|
||||
|
||||
@ -21,7 +20,6 @@ public class ServerVariableHolder {
|
||||
* @param server instance the plugin is running on.
|
||||
*/
|
||||
public ServerVariableHolder(Server server) {
|
||||
maxPlayers = server.getMaxPlayers();
|
||||
ip = server.getIp();
|
||||
|
||||
String serverName = server.getName();
|
||||
@ -29,15 +27,6 @@ public class ServerVariableHolder {
|
||||
|| serverName.equals("TacoSpigot"); //Fork of Paper
|
||||
}
|
||||
|
||||
/**
|
||||
* Maximum amount of players defined in server.properties.
|
||||
*
|
||||
* @return number.
|
||||
*/
|
||||
public int getMaxPlayers() {
|
||||
return maxPlayers;
|
||||
}
|
||||
|
||||
/**
|
||||
* Ip string in server.properties.
|
||||
*
|
||||
|
@ -15,7 +15,6 @@ public enum Settings {
|
||||
ANALYSIS_REFRESH_ON_ENABLE("Settings.Cache.AnalysisCache.RefreshAnalysisCacheOnEnable"),
|
||||
ANALYSIS_LOG_TO_CONSOLE("Settings.Analysis.LogProgressOnConsole"),
|
||||
ANALYSIS_LOG_FINISHED("Settings.Analysis.NotifyWhenFinished"),
|
||||
ANALYSIS_REMOVE_OUTLIERS("Settings.Analysis.RemoveOutliersFromVisualization"),
|
||||
ANALYSIS_EXPORT("Settings.Analysis.Export.Enabled"),
|
||||
SHOW_ALTERNATIVE_IP("Settings.WebServer.ShowAlternativeServerIP"),
|
||||
USE_ALTERNATIVE_UI("Settings.UseTextUI"),
|
||||
@ -26,7 +25,6 @@ public enum Settings {
|
||||
DO_NOT_LOG_UNKNOWN_COMMANDS("Customization.Data.DoNotLogUnknownCommands"),
|
||||
COMBINE_COMMAND_ALIASES_TO_MAIN_COMMAND("Customization.Data.CombineCommandAliasesToMainCommand"),
|
||||
SECURITY_IP_UUID("Settings.WebServer.Security.DisplayIPsAndUUIDs"),
|
||||
GRAPH_PLAYERS_USEMAXPLAYERS_SCALE("Customization.Graphs.PlayersOnlineGraph.UseMaxPlayersAsScale"),
|
||||
PLAYERLIST_SHOW_IMAGES("Customization.SmallHeadImagesOnAnalysisPlayerlist"),
|
||||
// Integer
|
||||
ANALYSIS_MINUTES_FOR_ACTIVE("Settings.Analysis.MinutesPlayedUntilConsidiredActive"),
|
||||
@ -76,7 +74,6 @@ public enum Settings {
|
||||
HCOLOR_TER("Customization.Colors.HTML.UI.Tertiary"),
|
||||
HCOLOR_TER_DARK("Customization.Colors.HTML.UI.TertiaryDark"),
|
||||
HCOLOR_ACT_ONL("Customization.Colors.HTML.ActivityGraph.OnlinePlayers"),
|
||||
HCOLOR_ACT_ONL_FILL("Customization.Colors.HTML.ActivityGraph.OnlinePlayersFill"),
|
||||
HCOLOR_ACTP_ACT("Customization.Colors.HTML.ActivityPie.Active"),
|
||||
HCOLOR_ACTP_BAN("Customization.Colors.HTML.ActivityPie.Banned"),
|
||||
HCOLOR_ACTP_INA("Customization.Colors.HTML.ActivityPie.Inactive"),
|
||||
|
@ -12,6 +12,7 @@ import main.java.com.djrapitops.plan.ui.html.graphs.PunchCardGraphCreator;
|
||||
import main.java.com.djrapitops.plan.ui.html.graphs.SessionLengthDistributionGraphCreator;
|
||||
import main.java.com.djrapitops.plan.utilities.FormatUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.HtmlUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.AnalysisUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.MathUtils;
|
||||
|
||||
@ -73,25 +74,17 @@ public class ActivityPart extends RawData {
|
||||
long averageLength = MathUtils.averageLong(lengths);
|
||||
addValue("sessionaverage", FormatUtils.formatTimeAmount(averageLength));
|
||||
|
||||
addValue("punchcardseries", PunchCardGraphCreator.createDataSeries(sessions));
|
||||
List<SessionData> sessionsMonth = sessions.stream()
|
||||
.filter(s -> s.getSessionStart() > MiscUtils.getTime() - TimeAmount.MONTH.ms())
|
||||
.collect(Collectors.toList());
|
||||
addValue("punchcardseries", PunchCardGraphCreator.createDataSeries(sessionsMonth));
|
||||
addValue("sessionlengthseries", SessionLengthDistributionGraphCreator.createDataSeries(lengths));
|
||||
}
|
||||
|
||||
private void playerActivityGraphs() {
|
||||
List<TPS> tpsData = tpsPart.getTpsData();
|
||||
|
||||
String dayScatter = PlayerActivityGraphCreator.buildScatterDataString(tpsData, TimeAmount.DAY.ms());
|
||||
String weekScatter = PlayerActivityGraphCreator.buildScatterDataString(tpsData, TimeAmount.WEEK.ms());
|
||||
String monthScatter = PlayerActivityGraphCreator.buildScatterDataString(tpsData, TimeAmount.MONTH.ms());
|
||||
|
||||
addValue("datascatterday", dayScatter);
|
||||
addValue("datascatterweek", weekScatter);
|
||||
addValue("datascattermonth", monthScatter);
|
||||
|
||||
addValue("playersonlineseries", PlayerActivityGraphCreator.buildSeriesDataString(tpsData));
|
||||
|
||||
addValue("%playersgraphcolor%", Settings.HCOLOR_ACT_ONL + "");
|
||||
addValue("%playersgraphfill%", Settings.HCOLOR_ACT_ONL_FILL + "");
|
||||
}
|
||||
|
||||
private void activityPiechart() {
|
||||
|
@ -19,12 +19,10 @@ import java.util.Map;
|
||||
*/
|
||||
public class GeolocationPart extends RawData {
|
||||
|
||||
private final Map<String, Integer> geoLocations;
|
||||
private final Map<String, String> geoCodes;
|
||||
private final Map<String, Integer> geoCodeCounts;
|
||||
|
||||
public GeolocationPart() {
|
||||
geoLocations = new HashMap<>();
|
||||
geoCodes = new HashMap<>();
|
||||
geoCodeCounts = new HashMap<>();
|
||||
|
||||
@ -34,7 +32,6 @@ public class GeolocationPart extends RawData {
|
||||
String country = countries[i];
|
||||
String countryCode = codes[i];
|
||||
|
||||
geoLocations.put(country, 0);
|
||||
geoCodes.put(country, countryCode);
|
||||
geoCodeCounts.put(countryCode, 0);
|
||||
}
|
||||
@ -42,21 +39,10 @@ public class GeolocationPart extends RawData {
|
||||
|
||||
@Override
|
||||
public void analyse() {
|
||||
choroplethMapValues();
|
||||
}
|
||||
|
||||
private void choroplethMapValues() {
|
||||
String[] choropleth = WorldMapCreator.choroplethMapValues(geoLocations, geoCodes);
|
||||
|
||||
addValue("geomapseries", WorldMapCreator.createDataSeries(geoCodeCounts));
|
||||
|
||||
addValue("geomapz", choropleth[0]);
|
||||
addValue("geomapcountries", choropleth[1]);
|
||||
addValue("geomapcodes", choropleth[2]);
|
||||
}
|
||||
|
||||
public void addGeoloc(String country) {
|
||||
geoLocations.computeIfPresent(country, (computedCountry, amount) -> amount + 1);
|
||||
public void addGeolocation(String country) {
|
||||
String countryCode = geoCodes.get(country);
|
||||
if (countryCode != null) {
|
||||
geoCodeCounts.computeIfPresent(countryCode, (computedCountry, amount) -> amount + 1);
|
||||
|
@ -3,7 +3,6 @@ package main.java.com.djrapitops.plan.data.analysis;
|
||||
import com.djrapitops.plugin.api.TimeAmount;
|
||||
import com.djrapitops.plugin.utilities.Verify;
|
||||
import main.java.com.djrapitops.plan.data.SessionData;
|
||||
import main.java.com.djrapitops.plan.ui.html.graphs.NewPlayersGraphCreator;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.AnalysisUtils;
|
||||
|
||||
@ -87,14 +86,6 @@ public class JoinInfoPart extends RawData {
|
||||
addValue("newperdayday", newPerDayDay);
|
||||
addValue("newperdayweek", newPerDayWeek);
|
||||
addValue("newperdaymonth", newPerDayMonth);
|
||||
|
||||
String scatterDay = NewPlayersGraphCreator.buildScatterDataString(registered, TimeAmount.DAY.ms(), now);
|
||||
String scatterWeek = NewPlayersGraphCreator.buildScatterDataString(registered, TimeAmount.WEEK.ms(), now);
|
||||
String scatterMonth = NewPlayersGraphCreator.buildScatterDataString(registered, TimeAmount.MONTH.ms(), now);
|
||||
|
||||
addValue("npdataday", scatterDay);
|
||||
addValue("npdataweek", scatterWeek);
|
||||
addValue("npdatamonth", scatterMonth);
|
||||
}
|
||||
|
||||
public void addToLoginTimes() {
|
||||
|
@ -66,8 +66,8 @@ public class TPSPart extends RawData {
|
||||
addValue("averagetpsweek", FormatUtils.cutDecimals(averageTPSWeek));
|
||||
addValue("averagetpsday", FormatUtils.cutDecimals(averageTPSDay));
|
||||
|
||||
addValue("averagecpuweek", FormatUtils.cutDecimals(averageCPUWeek));
|
||||
addValue("averagecpuday", FormatUtils.cutDecimals(averageCPUDay));
|
||||
addValue("averagecpuweek", averageCPUWeek >= 0 ? FormatUtils.cutDecimals(averageCPUWeek) + "%" : "Unavailable");
|
||||
addValue("averagecpuday", averageCPUDay >= 0 ? FormatUtils.cutDecimals(averageCPUDay) + "%" : "Unavailable");
|
||||
|
||||
addValue("averagememoryweek", FormatUtils.cutDecimals(averageUsedMemoryWeek));
|
||||
addValue("averagememoryday", FormatUtils.cutDecimals(averageUsedMemoryDay));
|
||||
|
@ -1,7 +1,6 @@
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.TPS;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.List;
|
||||
@ -22,13 +21,4 @@ public class CPUGraphCreator {
|
||||
.collect(Collectors.toList());
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
public static String buildScatterDataString(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> points = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
.map(tps -> new Point(tps.getDate(), tps.getCPUUsage()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true);
|
||||
}
|
||||
}
|
||||
|
@ -1,51 +0,0 @@
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* Class for creating scatter graph data from Registration epoch dates.
|
||||
*
|
||||
* @author Rsl1122
|
||||
* @since 3.6.0
|
||||
*/
|
||||
public class NewPlayersGraphCreator {
|
||||
|
||||
/**
|
||||
* Constructor used to hide the public constructor
|
||||
*/
|
||||
private NewPlayersGraphCreator() {
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a scatter data string from given data.
|
||||
*
|
||||
* @param registered Registration dates of players
|
||||
* @param scale Scale which the graph should reside within. (Milliseconds)
|
||||
* @param now Current epoch ms.
|
||||
* @return Scatter Graph data string for ChartJs
|
||||
*/
|
||||
public static String buildScatterDataString(List<Long> registered, long scale, long now) {
|
||||
List<Long> filtered = registered.stream()
|
||||
.filter(date -> date >= now - scale).collect(Collectors.toList());
|
||||
List<Point> points = filtered.stream()
|
||||
.distinct()
|
||||
.map(date -> new Point(date, getCount(filtered, date)))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Counts registration amounts of certain date.
|
||||
*
|
||||
* @param filtered Filtered registration list (Filtered to scale)
|
||||
* @param lookFor Look for this date
|
||||
* @return How many were on the list.
|
||||
*/
|
||||
private static long getCount(List<Long> filtered, long lookFor) {
|
||||
return filtered.stream().filter(date -> lookFor == date).count();
|
||||
}
|
||||
}
|
@ -2,12 +2,11 @@ package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.SessionData;
|
||||
import main.java.com.djrapitops.plan.data.TPS;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
@ -29,33 +28,11 @@ public class PlayerActivityGraphCreator {
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
public static String buildScatterDataString(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> points = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
.map(tps -> new Point(tps.getDate(), tps.getPlayers()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true);
|
||||
}
|
||||
|
||||
public static String buildScatterDataStringSessions(List<SessionData> sessionData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
long nowMinusScale = now - scale;
|
||||
List<SessionData> filtered = filterSessions(sessionData, nowMinusScale);
|
||||
|
||||
List<Point> points = filtered.stream()
|
||||
public static String buildSeriesDataStringSessions(Collection<SessionData> sessions) {
|
||||
List<Point> points = sessions.stream()
|
||||
.map(session -> new Point[]{new Point(session.getSessionStart(), 1), new Point(session.getSessionEnd(), 0)})
|
||||
.flatMap(Arrays::stream)
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true, false);
|
||||
}
|
||||
|
||||
private static List<SessionData> filterSessions(List<SessionData> sessions, long nowMinusScale) {
|
||||
return sessions.parallelStream()
|
||||
.filter(Objects::nonNull)
|
||||
.filter(session -> session.isValid() || session.getSessionEnd() == -1)
|
||||
.filter(session -> session.getSessionStart() >= nowMinusScale || session.getSessionEnd() >= nowMinusScale)
|
||||
.distinct()
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
}
|
||||
|
@ -5,20 +5,20 @@
|
||||
*/
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.Settings;
|
||||
import main.java.com.djrapitops.plan.data.SessionData;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.AnalysisUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.MathUtils;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
/**
|
||||
* Utility class for creating Punch Card Data Array for the javascripts.
|
||||
*
|
||||
* @author Rsl1122
|
||||
* @since 3.6.0
|
||||
*/
|
||||
public class PunchCardGraphCreator {
|
||||
|
||||
@ -29,7 +29,12 @@ public class PunchCardGraphCreator {
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Creates a Punchcard series data Array for HighCharts
|
||||
*
|
||||
* @param sessions Sessions (Unique/Player) to be placed into the punchcard.
|
||||
* @return Data array as a string.
|
||||
*/
|
||||
public static String createDataSeries(Collection<SessionData> sessions) {
|
||||
List<Long> sessionStarts = getSessionStarts(sessions);
|
||||
List<int[]> daysAndHours = AnalysisUtils.getDaysAndHours(sessionStarts);
|
||||
@ -43,7 +48,11 @@ public class PunchCardGraphCreator {
|
||||
if (value == 0) {
|
||||
continue;
|
||||
}
|
||||
arrayBuilder.append("{x:").append(j * 3600000).append(", y:").append(i).append(", z:").append(value).append(", marker: { radius:").append(value).append("}}");
|
||||
arrayBuilder.append("{x:").append(j * 3600000)
|
||||
.append(", y:").append(i)
|
||||
.append(", z:").append(value).
|
||||
append(", marker: { radius:").append(value)
|
||||
.append("}}");
|
||||
if (i != 6 || j != 23) {
|
||||
arrayBuilder.append(",");
|
||||
}
|
||||
@ -53,38 +62,6 @@ public class PunchCardGraphCreator {
|
||||
return arrayBuilder.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param data
|
||||
* @return
|
||||
*/
|
||||
public static String generateDataArray(Collection<SessionData> data) {
|
||||
List<Long> sessionStarts = getSessionStarts(data);
|
||||
List<int[]> daysAndHours = AnalysisUtils.getDaysAndHours(sessionStarts);
|
||||
int[][] dataArray = createDataArray(daysAndHours);
|
||||
int big = findBiggestValue(dataArray);
|
||||
int[][] scaled = scale(dataArray, big);
|
||||
StringBuilder arrayBuilder = buildString(scaled);
|
||||
return arrayBuilder.toString();
|
||||
}
|
||||
|
||||
private static StringBuilder buildString(int[][] scaled) {
|
||||
StringBuilder arrayBuilder = new StringBuilder("[");
|
||||
for (int i = 0; i < 7; i++) {
|
||||
for (int j = 0; j < 24; j++) {
|
||||
int value = scaled[i][j];
|
||||
if (value == 0) {
|
||||
continue;
|
||||
}
|
||||
arrayBuilder.append("{x:").append(j).append(", y:").append(i).append(", r:").append(value).append("}");
|
||||
if (i != 6 || j != 23) {
|
||||
arrayBuilder.append(",");
|
||||
}
|
||||
}
|
||||
}
|
||||
arrayBuilder.append("]");
|
||||
return arrayBuilder;
|
||||
}
|
||||
|
||||
private static int[][] createDataArray(List<int[]> daysAndHours) {
|
||||
int[][] dataArray = createEmptyArray();
|
||||
for (int[] dAndH : daysAndHours) {
|
||||
@ -92,47 +69,9 @@ public class PunchCardGraphCreator {
|
||||
int h = dAndH[1];
|
||||
dataArray[d][h] = dataArray[d][h] + 1;
|
||||
}
|
||||
|
||||
if (Settings.ANALYSIS_REMOVE_OUTLIERS.isTrue()) {
|
||||
int avg = findAverage(dataArray);
|
||||
double standardDeviation = getStandardDeviation(dataArray, avg);
|
||||
if (standardDeviation > 3.5) {
|
||||
for (int i = 0; i < 7; i++) {
|
||||
for (int j = 0; j < 24; j++) {
|
||||
int value = dataArray[i][j];
|
||||
if (value - avg > 3 * standardDeviation) {
|
||||
dataArray[i][j] = avg;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return dataArray;
|
||||
}
|
||||
|
||||
private static double getStandardDeviation(int[][] array, int avg) {
|
||||
int[][] valueMinusAvg = new int[7][24];
|
||||
for (int i = 0; i < 7; i++) {
|
||||
for (int j = 0; j < 24; j++) {
|
||||
valueMinusAvg[i][j] = (int) Math.pow(Math.abs(array[i][j] - avg), 2);
|
||||
}
|
||||
}
|
||||
|
||||
int size = array.length * array[0].length;
|
||||
double sum = sum(valueMinusAvg);
|
||||
return Math.sqrt(sum / size);
|
||||
}
|
||||
|
||||
private static int findAverage(int[][] array) {
|
||||
int total = sum(array);
|
||||
int size = array.length * array[0].length;
|
||||
return (int) MathUtils.average(total, size);
|
||||
}
|
||||
|
||||
private static int sum(int[][] array) {
|
||||
return Arrays.stream(array).mapToInt(is -> is.length).sum();
|
||||
}
|
||||
|
||||
private static List<Long> getSessionStarts(Collection<SessionData> data) {
|
||||
long now = MiscUtils.getTime();
|
||||
return data.stream()
|
||||
|
@ -1,7 +1,6 @@
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.TPS;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.List;
|
||||
@ -23,26 +22,16 @@ public class RamGraphCreator {
|
||||
throw new IllegalStateException("Utility class");
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a series data string from given data.
|
||||
*
|
||||
* @param tpsData TPS Data collected by TPSCountTimer, one data point for each minute.
|
||||
* @return Series data for HighCharts
|
||||
*/
|
||||
public static String buildSeriesDataString(List<TPS> tpsData) {
|
||||
List<Point> points = tpsData.stream()
|
||||
.map(tps -> new Point(tps.getDate(), tps.getUsedMemory()))
|
||||
.collect(Collectors.toList());
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a scatter data string from given data.
|
||||
*
|
||||
* @param tpsData TPS Data collected by TPSCountTimer, one data point for each minute.
|
||||
* @param scale Time span this graph resides within. (Milliseconds)
|
||||
* @return Scatter Graph data string for ChartJs
|
||||
*/
|
||||
public static String buildScatterDataString(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> points = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
.map(tps -> new Point(tps.getDate(), tps.getUsedMemory()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true);
|
||||
}
|
||||
}
|
||||
|
@ -5,10 +5,6 @@
|
||||
*/
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.SessionData;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.AnalysisUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.MathUtils;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@ -55,63 +51,6 @@ public class SessionLengthDistributionGraphCreator {
|
||||
return arrayBuilder.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* @param data
|
||||
* @return
|
||||
*/
|
||||
public static String[] generateDataArraySessions(Collection<SessionData> data) {
|
||||
List<Long> lengths = AnalysisUtils.transformSessionDataToLengths(data);
|
||||
return generateDataArray(lengths);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param lengths
|
||||
* @return
|
||||
*/
|
||||
public static String[] generateDataArray(Collection<Long> lengths) {
|
||||
Map<Long, Integer> values = getValues(lengths);
|
||||
StringBuilder arrayBuilder = buildString(values);
|
||||
StringBuilder labelBuilder = buildLabels(values);
|
||||
|
||||
return new String[]{arrayBuilder.toString(), labelBuilder.toString()};
|
||||
}
|
||||
|
||||
private static StringBuilder buildString(Map<Long, Integer> scaled) {
|
||||
StringBuilder arrayBuilder = new StringBuilder("[");
|
||||
|
||||
long big = MathUtils.getBiggestLong(scaled.keySet());
|
||||
for (long key = 0; key <= big; key++) {
|
||||
Integer value = scaled.get(key);
|
||||
if (value == null) {
|
||||
continue;
|
||||
}
|
||||
arrayBuilder.append(value);
|
||||
if (key != big) {
|
||||
arrayBuilder.append(", ");
|
||||
}
|
||||
}
|
||||
arrayBuilder.append("]");
|
||||
return arrayBuilder;
|
||||
}
|
||||
|
||||
private static StringBuilder buildLabels(Map<Long, Integer> scaled) {
|
||||
StringBuilder arrayBuilder = new StringBuilder("[");
|
||||
|
||||
long big = MathUtils.getBiggestLong(scaled.keySet());
|
||||
for (long key = 0; key <= big; key++) {
|
||||
Integer value = scaled.get(key);
|
||||
if (value == null) {
|
||||
continue;
|
||||
}
|
||||
arrayBuilder.append("\'").append(key - 5).append(" - ").append(key).append(" min").append("\'");
|
||||
if (key != big) {
|
||||
arrayBuilder.append(", ");
|
||||
}
|
||||
}
|
||||
arrayBuilder.append("]");
|
||||
return arrayBuilder;
|
||||
}
|
||||
|
||||
private static Map<Long, Integer> getValues(Collection<Long> lengths) {
|
||||
List<Long> unused = new ArrayList<>(lengths);
|
||||
Map<Long, Integer> values = new HashMap<>();
|
||||
|
@ -1,7 +1,6 @@
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.TPS;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.List;
|
||||
@ -29,15 +28,6 @@ public class TPSGraphCreator {
|
||||
|
||||
}
|
||||
|
||||
public static String buildScatterDataStringTPS(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> points = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
.map(tps -> new Point(tps.getDate(), tps.getTps()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(points, true);
|
||||
}
|
||||
|
||||
public static List<TPS> filterTPS(List<TPS> tpsData, long nowMinusScale) {
|
||||
return tpsData.stream()
|
||||
.filter(Objects::nonNull)
|
||||
|
@ -1,7 +1,6 @@
|
||||
package main.java.com.djrapitops.plan.ui.html.graphs;
|
||||
|
||||
import main.java.com.djrapitops.plan.data.TPS;
|
||||
import main.java.com.djrapitops.plan.utilities.MiscUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.Point;
|
||||
|
||||
import java.util.List;
|
||||
@ -16,20 +15,6 @@ import java.util.stream.Collectors;
|
||||
*/
|
||||
public class WorldLoadGraphCreator {
|
||||
|
||||
public static String buildSeriesDataStringEntities(List<TPS> tpsData) {
|
||||
List<Point> points = tpsData.stream()
|
||||
.map(tps -> new Point(tps.getDate(), tps.getEntityCount()))
|
||||
.collect(Collectors.toList());
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
public static String buildSeriesDataStringChunks(List<TPS> tpsData) {
|
||||
List<Point> points = tpsData.stream()
|
||||
.map(tps -> new Point(tps.getDate(), tps.getChunksLoaded()))
|
||||
.collect(Collectors.toList());
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor used to hide the public constructor
|
||||
*/
|
||||
@ -38,34 +23,28 @@ public class WorldLoadGraphCreator {
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates scatter graph data of entity load.
|
||||
* Creates series graph data of entity load.
|
||||
*
|
||||
* @param tpsData TPS Data collected by TPSCountTimer, one data point for each minute.
|
||||
* @param scale Time span this graph resides within. (Milliseconds)
|
||||
* @return Scatter Graph data string for ChartJs
|
||||
* @return Series data for HighCharts
|
||||
*/
|
||||
public static String buildScatterDataStringEntities(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> entityPoints = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
public static String buildSeriesDataStringEntities(List<TPS> tpsData) {
|
||||
List<Point> points = tpsData.stream()
|
||||
.map(tps -> new Point(tps.getDate(), tps.getEntityCount()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(entityPoints, true);
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates scatter graph data of chunk load.
|
||||
* Creates series data of chunk load.
|
||||
*
|
||||
* @param tpsData TPS Data collected by TPSCountTimer, one data point for each minute.
|
||||
* @param scale Time span this graph resides within. (Milliseconds)
|
||||
* @return Scatter Graph data string for ChartJs
|
||||
* @return Series data for HighCharts
|
||||
*/
|
||||
public static String buildScatterDataStringChunks(List<TPS> tpsData, long scale) {
|
||||
long now = MiscUtils.getTime();
|
||||
List<Point> chunkPoints = tpsData.stream()
|
||||
.filter(tps -> tps.getDate() >= now - scale)
|
||||
public static String buildSeriesDataStringChunks(List<TPS> tpsData) {
|
||||
List<Point> points = tpsData.stream()
|
||||
.map(tps -> new Point(tps.getDate(), tps.getChunksLoaded()))
|
||||
.collect(Collectors.toList());
|
||||
return ScatterGraphCreator.scatterGraph(chunkPoints, true);
|
||||
return SeriesCreator.seriesGraph(points, true);
|
||||
}
|
||||
}
|
||||
|
@ -38,34 +38,4 @@ public class WorldMapCreator {
|
||||
arrayBuilder.append("]");
|
||||
return arrayBuilder.toString();
|
||||
}
|
||||
|
||||
public static String[] choroplethMapValues(Map<String, Integer> geoLocations, Map<String, String> geoCodes) {
|
||||
StringBuilder locations = new StringBuilder("[");
|
||||
StringBuilder z = new StringBuilder("[");
|
||||
StringBuilder text = new StringBuilder("[");
|
||||
|
||||
int i = 0;
|
||||
int size = geoLocations.size();
|
||||
for (Map.Entry<String, Integer> entrySet : geoLocations.entrySet()) {
|
||||
String country = entrySet.getKey();
|
||||
String code = geoCodes.getOrDefault(country, "UNK");
|
||||
int amount = entrySet.getValue();
|
||||
|
||||
z.append("\"").append(amount).append("\"");
|
||||
locations.append("\"").append(country).append("\"");
|
||||
text.append("\"").append(code).append("\"");
|
||||
|
||||
if (i < size - 1) {
|
||||
locations.append(",");
|
||||
z.append(",");
|
||||
text.append(",");
|
||||
}
|
||||
}
|
||||
|
||||
locations.append("]");
|
||||
z.append("]");
|
||||
text.append("]");
|
||||
|
||||
return new String[]{z.toString(), locations.toString(), text.toString()};
|
||||
}
|
||||
}
|
||||
|
@ -1,9 +1,9 @@
|
||||
package main.java.com.djrapitops.plan.utilities;
|
||||
|
||||
import com.djrapitops.plugin.api.TimeAmount;
|
||||
import main.java.com.djrapitops.plan.Plan;
|
||||
import main.java.com.djrapitops.plan.Settings;
|
||||
import main.java.com.djrapitops.plan.data.AnalysisData;
|
||||
import main.java.com.djrapitops.plan.data.SessionData;
|
||||
import main.java.com.djrapitops.plan.data.UserData;
|
||||
import main.java.com.djrapitops.plan.data.analysis.GamemodePart;
|
||||
import main.java.com.djrapitops.plan.ui.html.Html;
|
||||
@ -14,9 +14,7 @@ import main.java.com.djrapitops.plan.ui.html.tables.KillsTableCreator;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.AnalysisUtils;
|
||||
import main.java.com.djrapitops.plan.utilities.analysis.MathUtils;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* @author Rsl1122
|
||||
@ -42,11 +40,9 @@ public class PlaceholderUtils {
|
||||
replaceMap.putAll(data.getReplaceMap());
|
||||
replaceMap.put("%plugins%", data.replacePluginsTabLayout());
|
||||
|
||||
replaceMap.put("%currenttime%", MiscUtils.getTime() + "");
|
||||
replaceMap.put("%refresh%", FormatUtils.formatTimeAmountDifference(data.getRefreshDate(), MiscUtils.getTime()));
|
||||
replaceMap.put("%refreshlong%", data.getRefreshDate() + "");
|
||||
|
||||
replaceMap.put("%graphmaxplayers%", Settings.GRAPH_PLAYERS_USEMAXPLAYERS_SCALE.isTrue() ? Plan.getInstance().getVariable().getMaxPlayers() + "" : "2");
|
||||
replaceMap.put("%servername%", Settings.SERVER_NAME.toString());
|
||||
|
||||
// Html Theme colors
|
||||
@ -108,17 +104,14 @@ public class PlaceholderUtils {
|
||||
replaceMap.put("%killstable%", KillsTableCreator.createKillsTable(data.getPlayerKills()));
|
||||
Plan plugin = Plan.getInstance();
|
||||
replaceMap.put("%version%", plugin.getDescription().getVersion());
|
||||
replaceMap.put("%planlite%", "");
|
||||
replaceMap.put("%graphmaxplayers%", "2");
|
||||
String scatterGraphData = PlayerActivityGraphCreator.buildScatterDataStringSessions(data.getSessions(), TimeAmount.WEEK.ms());
|
||||
replaceMap.put("%dataweek%", scatterGraphData);
|
||||
replaceMap.put("%playersgraphcolor%", Settings.HCOLOR_ACT_ONL.toString());
|
||||
replaceMap.put("%playersgraphfill%", Settings.HCOLOR_ACT_ONL_FILL.toString());
|
||||
replaceMap.put("%datapunchcard%", PunchCardGraphCreator.generateDataArray(data.getSessions()));
|
||||
String[] distribution = SessionLengthDistributionGraphCreator.generateDataArraySessions(data.getSessions());
|
||||
replaceMap.put("%datasessiondistribution%", distribution[0]);
|
||||
replaceMap.put("%labelssessiondistribution%", distribution[1]);
|
||||
replaceMap.put("%inaccuratedatawarning%", (now - data.getRegistered() < 180000) ? Html.WARN_INACCURATE.parse() : "");
|
||||
Set<SessionData> sessions = new HashSet<>(data.getSessions());
|
||||
replaceMap.put("%punchcardseries%", PunchCardGraphCreator.createDataSeries(sessions));
|
||||
List<Long> lengths = AnalysisUtils.transformSessionDataToLengths(sessions);
|
||||
replaceMap.put("%sessionlengthseries%", SessionLengthDistributionGraphCreator.createDataSeries(lengths));
|
||||
|
||||
replaceMap.put("%playersonlineseries%", PlayerActivityGraphCreator.buildSeriesDataStringSessions(sessions));
|
||||
|
||||
String[] colors = new String[]{Settings.HCOLOR_MAIN.toString(), Settings.HCOLOR_MAIN_DARK.toString(), Settings.HCOLOR_SEC.toString(), Settings.HCOLOR_TER.toString(), Settings.HCOLOR_TER_DARK.toString()};
|
||||
String[] defaultCols = new String[]{"348e0f", "267F00", "5cb239", "89c471", "5da341"};
|
||||
for (int i = 0; i < colors.length; i++) {
|
||||
@ -126,8 +119,9 @@ public class PlaceholderUtils {
|
||||
replaceMap.put("#" + defaultCols[i], "#" + colors[i]);
|
||||
}
|
||||
}
|
||||
replaceMap.put("%refreshlong%", String.valueOf(plugin.getInspectCache().getCacheTime(uuid)));
|
||||
replaceMap.put("%currenttime%", String.valueOf(MiscUtils.getTime()));
|
||||
long cacheTime = plugin.getInspectCache().getCacheTime(uuid);
|
||||
replaceMap.put("%refresh%", FormatUtils.formatTimeAmountDifference(cacheTime, now));
|
||||
replaceMap.put("%refreshlong%", String.valueOf(cacheTime));
|
||||
replaceMap.put("%servername%", Settings.SERVER_NAME.toString());
|
||||
String pluginsTabHtml = plugin.getHookHandler().getPluginsTabLayoutForInspect();
|
||||
Map<String, String> additionalReplaceRules = plugin.getHookHandler().getAdditionalInspectReplaceRules(uuid);
|
||||
|
@ -277,7 +277,7 @@ public class Analysis {
|
||||
joinInfo.addToLoginTimes(uData.getLoginTimes());
|
||||
joinInfo.addRegistered(uData.getRegistered());
|
||||
|
||||
geolocPart.addGeoloc(uData.getGeolocation());
|
||||
geolocPart.addGeolocation(uData.getGeolocation());
|
||||
|
||||
final UUID uuid = uData.getUuid();
|
||||
if (uData.isOp()) {
|
||||
|
@ -341,7 +341,6 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<!--<canvas id="playerChartDay" width="1000" height="350" style="width: 95%;"></canvas>-->
|
||||
<div id="playerChartDay" style="width=100%; height=350px;"></div>
|
||||
<p><i class="fa fa-user-circle" aria-hidden="true"></i> Unique Players: %uniquejoinsday% | <i
|
||||
class="fa fa-user-circle-o" aria-hidden="true"></i> Unique/Day: %avguniquejoinsday%</p>
|
||||
@ -530,14 +529,14 @@
|
||||
</div>
|
||||
<p><b>Week:</b><br>
|
||||
<i class="fa fa-tachometer" aria-hidden="true"></i> Average TPS: %averagetpsweek%<br>
|
||||
<i class="fa fa-building-o" aria-hidden="true"></i> Average CPU: %averagecpuweek%%<br>
|
||||
<i class="fa fa-building-o" aria-hidden="true"></i> Average CPU: %averagecpuweek%<br>
|
||||
<i class="fa fa-microchip" aria-hidden="true"></i> Average RAM: %averagememoryweek%Mb<br>
|
||||
<i class="fa fa-umbrella" aria-hidden="true"></i> Avg. Entities: %averageentitiesweek%<br>
|
||||
<i class="fa fa-tree" aria-hidden="true"></i> Average Chunks: %averagechunksweek%
|
||||
</p>
|
||||
<p><b>Day:</b><br>
|
||||
<i class="fa fa-tachometer" aria-hidden="true"></i> Average TPS: %averagetpsday%<br>
|
||||
<i class="fa fa-building-o" aria-hidden="true"></i> Average CPU: %averagecpuday%%<br>
|
||||
<i class="fa fa-building-o" aria-hidden="true"></i> Average CPU: %averagecpuday%<br>
|
||||
<i class="fa fa-microchip" aria-hidden="true"></i> Average RAM: %averagememoryday%Mb<br>
|
||||
<i class="fa fa-umbrella" aria-hidden="true"></i> Avg. Entities: %averageentitiesday%<br>
|
||||
<i class="fa fa-tree" aria-hidden="true"></i> Average Chunks: %averagechunksday%</p>
|
||||
@ -669,8 +668,6 @@
|
||||
<script src="https://code.highcharts.com/stock/highstock.js"></script>
|
||||
<script src="https://code.highcharts.com/maps/modules/map.js"></script>
|
||||
<script src="https://code.highcharts.com/mapdata/custom/world.js"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.5.0/Chart.bundle.js"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.5.0/Chart.js"></script>
|
||||
<script>
|
||||
// Data Variables
|
||||
var playersOnlineSeries = {
|
||||
@ -689,10 +686,11 @@
|
||||
color: '#b74343',
|
||||
tooltip: {
|
||||
valueDecimals: 2
|
||||
}
|
||||
},
|
||||
yAxis: 1
|
||||
};
|
||||
var cpuSeries = {
|
||||
name: 'CPU Usage',
|
||||
name: 'CPU Usage',
|
||||
data: %cpuseries%,
|
||||
type: 'spline',
|
||||
color: '#e0d264',
|
||||
@ -701,13 +699,14 @@
|
||||
}
|
||||
};
|
||||
var ramSeries = {
|
||||
name: 'RAM Usage',
|
||||
name: 'RAM Usage',
|
||||
data: %ramseries%,
|
||||
type: 'spline',
|
||||
color: '#7dcc24',
|
||||
tooltip: {
|
||||
valueDecimals: 0
|
||||
}
|
||||
},
|
||||
yAxis: 1
|
||||
};
|
||||
var entitySeries = {
|
||||
name: 'Loaded Entities',
|
||||
@ -716,7 +715,8 @@
|
||||
color: '#ac69ef',
|
||||
tooltip: {
|
||||
valueDecimals: 0
|
||||
}
|
||||
},
|
||||
yAxis: 1
|
||||
};
|
||||
var chunkSeries = {
|
||||
name: 'Loaded Chunks',
|
||||
@ -869,7 +869,30 @@
|
||||
type: 'all',
|
||||
text: 'All'
|
||||
}]
|
||||
},
|
||||
},
|
||||
yAxis: [{
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'Players'
|
||||
},
|
||||
top: '55%',
|
||||
height: '40%',
|
||||
offset: 0,
|
||||
lineWidth: 2
|
||||
}, {
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'TPS'
|
||||
},
|
||||
height: '55%',
|
||||
lineWidth: 2
|
||||
}],
|
||||
title: {text: 'Ticks Per Second'},
|
||||
series: [tpsSeries, playersOnlineSeries]
|
||||
});
|
||||
@ -900,7 +923,30 @@
|
||||
type: 'all',
|
||||
text: 'All'
|
||||
}]
|
||||
},
|
||||
},
|
||||
yAxis: [{
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'CPU / %'
|
||||
},
|
||||
height: '55%',
|
||||
lineWidth: 2
|
||||
}, {
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'RAM / MB'
|
||||
},
|
||||
top: '55%',
|
||||
height: '40%',
|
||||
offset: 0,
|
||||
lineWidth: 2
|
||||
}],
|
||||
title: {text: 'Resource Usage'},
|
||||
series: [cpuSeries, ramSeries]
|
||||
});
|
||||
@ -931,7 +977,30 @@
|
||||
type: 'all',
|
||||
text: 'All'
|
||||
}]
|
||||
},
|
||||
},
|
||||
yAxis: [{
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'Chunks'
|
||||
},
|
||||
height: '50%',
|
||||
lineWidth: 2
|
||||
}, {
|
||||
labels: {
|
||||
align: 'right',
|
||||
x: -3
|
||||
},
|
||||
title: {
|
||||
text: 'Entities'
|
||||
},
|
||||
top: '50%',
|
||||
height: '40%',
|
||||
offset: 0,
|
||||
lineWidth: 2
|
||||
}],
|
||||
title: {text: 'World Load'},
|
||||
series: [entitySeries, chunkSeries]
|
||||
});
|
||||
@ -1074,9 +1143,6 @@
|
||||
</script>
|
||||
<script>
|
||||
// Navigation & Refresh time clock
|
||||
var serverTime = new Date(%currenttime%);
|
||||
var now = new Date();
|
||||
var timediff = serverTime.getTime() - now.getTime();
|
||||
function openNav() {
|
||||
document.getElementById("sidenav").style.width = "100%";
|
||||
document.getElementById("limiter").style.display = "none";
|
||||
@ -1141,7 +1207,7 @@
|
||||
}
|
||||
function countUpTimer() {
|
||||
var now = new Date();
|
||||
var begin = new Date( %refreshlong% - timediff);
|
||||
var begin = new Date(%refreshlong%);
|
||||
var out = "";
|
||||
var seconds = now.getTime() - begin.getTime();
|
||||
seconds = Math.floor(seconds / 1000);
|
||||
|
@ -11,7 +11,6 @@ Settings:
|
||||
LogProgressOnConsole: false
|
||||
NotifyWhenFinished: true
|
||||
MinutesPlayedUntilConsidiredActive: 10
|
||||
RemoveOutliersFromVisualization: true
|
||||
Export:
|
||||
Enabled: false
|
||||
DestinationFolder: 'Analysis Results'
|
||||
@ -49,9 +48,6 @@ Customization:
|
||||
Data:
|
||||
DoNotLogUnknownCommands: false
|
||||
CombineCommandAliasesToMainCommand: false
|
||||
Graphs:
|
||||
PlayersOnlineGraph:
|
||||
UseMaxPlayersAsScale: true
|
||||
Formats:
|
||||
TimeAmount:
|
||||
Year: '1 year, '
|
||||
@ -76,7 +72,6 @@ Customization:
|
||||
TertiaryDark: 5da341
|
||||
ActivityGraph:
|
||||
OnlinePlayers: '1E90FF'
|
||||
OnlinePlayersFill: '75BBFF'
|
||||
NewPlayers: '228B22'
|
||||
GamemodePie:
|
||||
Survival: '438c99'
|
||||
|
@ -379,80 +379,7 @@
|
||||
<i class="fa fa-globe" aria-hidden="true"></i> Has Connected from ips: %ips%</p>
|
||||
</div>
|
||||
<div class="about box column">
|
||||
<div class="headerbox">
|
||||
<div class="header-icon" style="width: 50%">
|
||||
<div class="header-label"><i class="fa fa-pie-chart" aria-hidden="true"></i><span
|
||||
class="header-text"> Gamemode Usage</span></div>
|
||||
</div>
|
||||
<div class="infobox">
|
||||
<div class="info-icon">
|
||||
<i class="fa fa-clock-o" aria-hidden="true"></i>
|
||||
</div>
|
||||
<div class="info-text" style="width: 70%;">
|
||||
<div class="info-number">
|
||||
%gmtotal%
|
||||
</div>
|
||||
<div class="info-label">
|
||||
Total
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="box-area">
|
||||
<div class="infobox" style="float: left; background-color: #%gm0col%; width: 45%;">
|
||||
<div class="info-icon">
|
||||
<i class="fa fa-fire" aria-hidden="true"></i>
|
||||
</div>
|
||||
<div class="info-text">
|
||||
<div class="info-number">
|
||||
%gm0%
|
||||
</div>
|
||||
<div class="info-label">
|
||||
Survival
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="infobox" style="float: left; background-color: #%gm1col%; width: 45%;">
|
||||
<div class="info-icon">
|
||||
<i class="fa fa-cube" aria-hidden="true"></i>
|
||||
</div>
|
||||
<div class="info-text">
|
||||
<div class="info-number">
|
||||
%gm1%
|
||||
</div>
|
||||
<div class="info-label">
|
||||
Creative
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="infobox" style="float: left; background-color: #%gm2col%; width: 45%;">
|
||||
<div class="info-icon">
|
||||
<i class="fa fa-chevron-right" aria-hidden="true"></i>
|
||||
</div>
|
||||
<div class="info-text">
|
||||
<div class="info-number">
|
||||
%gm2%
|
||||
</div>
|
||||
<div class="info-label">
|
||||
Adventure
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="infobox" style="float: left; background-color: #%gm3col%; width: 45%;">
|
||||
<div class="info-icon">
|
||||
<i class="fa fa-binoculars" aria-hidden="true"></i>
|
||||
</div>
|
||||
<div class="info-text">
|
||||
<div class="info-number">
|
||||
%gm3%
|
||||
</div>
|
||||
<div class="info-label">
|
||||
Spectator
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<canvas id="gmPie" width="1000" height="600" style="width: 95%;"></canvas>
|
||||
<div id="gmPie" style="width: 100%; height: 400px;"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row">
|
||||
@ -476,7 +403,7 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<canvas id="playerChartWeek" width="1000" height="350" style="width: 95%;"></canvas>
|
||||
<div id="playerChart" style="width=100%; height=350px;"></div>
|
||||
</div>
|
||||
<div class="about box column">
|
||||
<div class="headerbox">
|
||||
@ -524,7 +451,7 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<canvas id="punchcard" width="1000" height="600" style="width: 95%;"></canvas>
|
||||
<div id="punchcard" style="width: 100%; height:400px;"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row">
|
||||
@ -548,7 +475,7 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<canvas id="sessiondistribution" width="1000" height="600" style="width: 95%;"></canvas>
|
||||
<div id="sessionDistribution" style="width: 100%; height:400px;"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@ -557,10 +484,168 @@
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<script src="https://www.kryogenix.org/code/browser/sorttable/sorttable.js"></script>
|
||||
<script src="https://code.highcharts.com/stock/highstock.js"></script>
|
||||
<script>
|
||||
var playersOnlineSeries = {
|
||||
name: 'Online',
|
||||
data: %playersonlineseries%,
|
||||
type: 'spline',
|
||||
color: '#%playersgraphcolor%',
|
||||
tooltip: {
|
||||
valueDecimals: 0
|
||||
}
|
||||
};
|
||||
var gmData = %gmdata%;
|
||||
var gmSeries = {
|
||||
name: 'GM Usage',
|
||||
colorByPoint: true,
|
||||
data: [{
|
||||
name: 'Survival',
|
||||
y: gmData[0],
|
||||
sliced: true,
|
||||
selected: true
|
||||
}, {
|
||||
name: 'Creative',
|
||||
y: gmData[1]
|
||||
}, {
|
||||
name: 'Adventure',
|
||||
y: gmData[2]
|
||||
}, {
|
||||
name: 'Spectator',
|
||||
y: gmData[3]
|
||||
}]
|
||||
};
|
||||
var sessionLengthSeries = {
|
||||
name: 'Sessions',
|
||||
color: '#89c471',
|
||||
data: %sessionlengthseries%
|
||||
};
|
||||
var punchcardSeries = {
|
||||
name: 'Relative Activity',
|
||||
color: '#222',
|
||||
data: %punchcardseries%
|
||||
};
|
||||
</script>
|
||||
<script>
|
||||
function playersChart() {
|
||||
var myChart = Highcharts.stockChart('playerChart', {
|
||||
rangeSelector: {
|
||||
selected: 2,
|
||||
buttons: [{
|
||||
type: 'hour',
|
||||
count: 12,
|
||||
text: '12h'
|
||||
},{
|
||||
type: 'hour',
|
||||
count: 24,
|
||||
text: '24h'
|
||||
},{
|
||||
type: 'day',
|
||||
count: 7,
|
||||
text: '7d'
|
||||
},{
|
||||
type: 'month',
|
||||
count: 1,
|
||||
text: '30d'
|
||||
},{
|
||||
type: 'all',
|
||||
text: 'All'
|
||||
}]
|
||||
},
|
||||
title: {text: 'Online Activity'},
|
||||
series: [playersOnlineSeries]
|
||||
});
|
||||
}
|
||||
</script>
|
||||
<script>
|
||||
function gmPie() {
|
||||
Highcharts.chart('gmPie', {
|
||||
chart: {
|
||||
plotBackgroundColor: null, plotBorderWidth: null, plotShadow: false,
|
||||
type: 'pie'
|
||||
},
|
||||
title: {text: 'Gamemode Usage'},
|
||||
subtitle: {text: '%gmtotal%'},
|
||||
tooltip: {
|
||||
pointFormat: '{series.name}: <b>{point.percentage:.2f}%</b>'
|
||||
},
|
||||
plotOptions: {
|
||||
pie: {
|
||||
allowPointSelect: true,
|
||||
cursor: 'pointer',
|
||||
dataLabels: {
|
||||
enabled: false
|
||||
},
|
||||
colors: [%gmcolors%],
|
||||
showInLegend: true
|
||||
}
|
||||
},
|
||||
series: [gmSeries]
|
||||
});
|
||||
};
|
||||
</script>
|
||||
<script>
|
||||
function punchCard() {
|
||||
Highcharts.chart('punchcard' , {
|
||||
chart: {
|
||||
defaultSeriesType: 'scatter'
|
||||
},
|
||||
title: {
|
||||
text: 'Player Join PunchCard'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'datetime',
|
||||
dateTimeLabelFormats: {
|
||||
hour: '%I %P'
|
||||
},
|
||||
tickInterval: 3600000
|
||||
},
|
||||
yAxis: {
|
||||
categories: ['Monday','Tuesday','Wednesday','Thursday','Friday','Saturday','Sunday'],
|
||||
},
|
||||
tooltip: {
|
||||
pointFormat: 'Activity: {point.z}'
|
||||
},
|
||||
series: [punchcardSeries]
|
||||
});
|
||||
}
|
||||
</script>
|
||||
<script>
|
||||
function sessionDistributionChart() {
|
||||
Highcharts.chart('sessionDistribution', {
|
||||
chart: {
|
||||
type: 'column'
|
||||
},
|
||||
title: {
|
||||
text: 'Session Length Distribution'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'category',
|
||||
labels: {
|
||||
rotation: -45
|
||||
}
|
||||
},
|
||||
yAxis: {
|
||||
min: 0,
|
||||
title: {
|
||||
text: 'Sessions'
|
||||
}
|
||||
},
|
||||
legend: {
|
||||
enabled: false
|
||||
},
|
||||
plotOptions: {
|
||||
series: {
|
||||
groupPadding: 0
|
||||
},
|
||||
pointPadding: 0
|
||||
},
|
||||
series: [sessionLengthSeries]
|
||||
});
|
||||
};
|
||||
</script>
|
||||
<script>
|
||||
var serverTime = new Date(%currenttime%);
|
||||
var now = new Date();
|
||||
var timediff = serverTime.getTime()-now.getTime();
|
||||
function openNav() {
|
||||
document.getElementById("sidenav").style.width = "100%";
|
||||
document.getElementById("limiter").style.display = "none";
|
||||
@ -588,6 +673,12 @@
|
||||
}
|
||||
x.style.opacity = "1";
|
||||
openFunc(slideIndex)();
|
||||
|
||||
playersChart();
|
||||
sessionDistributionChart();
|
||||
gmPie();
|
||||
punchCard();
|
||||
|
||||
countUpTimer();
|
||||
|
||||
function openFunc(i) {
|
||||
@ -618,7 +709,7 @@
|
||||
|
||||
function countUpTimer() {
|
||||
var now = new Date();
|
||||
var begin = new Date(%refreshlong%-timediff);
|
||||
var begin = new Date(%refreshlong%);
|
||||
var out = "";
|
||||
|
||||
var seconds = now.getTime() - begin.getTime();
|
||||
@ -649,256 +740,6 @@
|
||||
document.getElementById('divTime').innerHTML = out;
|
||||
setTimeout('countUpTimer()', 1000);
|
||||
}
|
||||
|
||||
</script>
|
||||
<script src="https://www.kryogenix.org/code/browser/sorttable/sorttable.js"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.5.0/Chart.bundle.js"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.5.0/Chart.js"></script>
|
||||
<script>
|
||||
function hour(i) {
|
||||
switch (i) {
|
||||
case 25:
|
||||
case -1:
|
||||
case -2:
|
||||
case -3:
|
||||
case -4:
|
||||
case -5:
|
||||
return '';
|
||||
default:
|
||||
return i+':00';
|
||||
}
|
||||
}
|
||||
function day(i) {
|
||||
switch (i) {
|
||||
case 0:
|
||||
return 'Monday';
|
||||
case 1:
|
||||
return 'Tuesday';
|
||||
case 2:
|
||||
return 'Wednesday';
|
||||
case 3:
|
||||
return 'Thursday';
|
||||
case 4:
|
||||
return 'Friday';
|
||||
case 5:
|
||||
return 'Saturday';
|
||||
case 6:
|
||||
return 'Sunday';
|
||||
default:
|
||||
break;
|
||||
return '';
|
||||
}
|
||||
}
|
||||
// Script for All charts using Chart.js
|
||||
var ctxgmpie = document.getElementById("gmPie");
|
||||
var dataGmPie = {
|
||||
labels: %gmlabels% ,
|
||||
datasets: [{
|
||||
data: %gmdata% ,
|
||||
backgroundColor: [ %gmcolors% ],
|
||||
hoverBackgroundColor: [ %gmcolors% ]
|
||||
}]
|
||||
}
|
||||
var GMPie = new Chart(ctxgmpie, {
|
||||
type: 'doughnut',
|
||||
data: dataGmPie,
|
||||
options: {
|
||||
legend: {
|
||||
position: 'right',
|
||||
labels: {
|
||||
padding: 7
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
var ctxweek = document.getElementById("playerChartWeek");
|
||||
var dataweek = {
|
||||
datasets: [{
|
||||
label: "Online",
|
||||
fill: true,
|
||||
lineTension: 0.1,
|
||||
backgroundColor: "#%playersgraphfill%",
|
||||
borderColor: "#%playersgraphcolor%",
|
||||
borderCapStyle: 'butt',
|
||||
borderDash: [],
|
||||
borderDashOffset: 0.0,
|
||||
borderJoinStyle: 'miter',
|
||||
pointBorderColor: "#%playersgraphcolor%",
|
||||
pointBackgroundColor: "#fff",
|
||||
pointBorderWidth: 1,
|
||||
pointHoverRadius: 5,
|
||||
pointHoverBackgroundColor: "#%playersgraphcolor%",
|
||||
pointHoverBorderColor: "#8fabc6",
|
||||
pointHoverBorderWidth: 2,
|
||||
pointRadius: 1,
|
||||
pointHitRadius: 10,
|
||||
spanGaps: false,
|
||||
data: %dataweek% ,
|
||||
}]};
|
||||
var playersChartWeek = new Chart(ctxweek, {
|
||||
type: 'scatter',
|
||||
data: dataweek,
|
||||
options: {
|
||||
tooltips: {
|
||||
callbacks: {
|
||||
label: function(tooltipItems, data) {
|
||||
var newDate = new Date();
|
||||
newDate.setTime(tooltipItems.xLabel);
|
||||
dateString = newDate.toUTCString();
|
||||
return dateString +': '+ tooltipItems.yLabel+ ' Players';
|
||||
}
|
||||
}
|
||||
},
|
||||
scales: {
|
||||
yAxes: [{
|
||||
display: true,
|
||||
ticks: {
|
||||
callback: function(value, index, values) {
|
||||
switch (value) {
|
||||
case 0:
|
||||
return '0';
|
||||
case 1:
|
||||
return '1';
|
||||
default:
|
||||
return '';
|
||||
};
|
||||
},
|
||||
suggestedMax: %graphmaxplayers%,
|
||||
suggestedMin: 0
|
||||
}
|
||||
}],
|
||||
xAxes: [{
|
||||
type: 'linear',
|
||||
display: false
|
||||
}]
|
||||
}
|
||||
}
|
||||
});
|
||||
var ctxpunch = document.getElementById("punchcard");
|
||||
var datapunch = {
|
||||
datasets: [
|
||||
{
|
||||
label: 'Player Join Punchcard',
|
||||
data: %datapunchcard%,
|
||||
backgroundColor: "#222",
|
||||
hoverBackgroundColor: "#333",
|
||||
}]
|
||||
};
|
||||
var punchcardChart = new Chart(ctxpunch, {
|
||||
type: 'bubble',
|
||||
data: datapunch,
|
||||
options: {
|
||||
tooltips: {
|
||||
callbacks: {
|
||||
label: function(tooltipItems, data) {
|
||||
function day(i) {
|
||||
switch (i) {
|
||||
case 0:
|
||||
return 'Monday';
|
||||
case 1:
|
||||
return 'Tuesday';
|
||||
case 2:
|
||||
return 'Wednesday';
|
||||
case 3:
|
||||
return 'Thursday';
|
||||
case 4:
|
||||
return 'Friday';
|
||||
case 5:
|
||||
return 'Saturday';
|
||||
case 6:
|
||||
return 'Sunday';
|
||||
default:
|
||||
return '';
|
||||
}
|
||||
}
|
||||
function hour(i) {
|
||||
switch (i) {
|
||||
case 25:
|
||||
case -1:
|
||||
case -2:
|
||||
case -3:
|
||||
case -4:
|
||||
case -5:
|
||||
return '';
|
||||
default:
|
||||
return i+':00';
|
||||
}
|
||||
}
|
||||
return day(tooltipItems.yLabel)+': '+hour(tooltipItems.xLabel);
|
||||
}
|
||||
}
|
||||
},
|
||||
scales: {
|
||||
xAxes: [{
|
||||
ticks: {
|
||||
callback: function(value, index, values) {
|
||||
return hour(value);
|
||||
},
|
||||
suggestedMax: 25,
|
||||
suggestedMin: -1
|
||||
}
|
||||
}],
|
||||
yAxes: [{
|
||||
ticks: {
|
||||
callback: function(value, index, values) {
|
||||
return day(value);
|
||||
},
|
||||
suggestedMax: 7,
|
||||
suggestedMin: -1
|
||||
}
|
||||
}]
|
||||
}
|
||||
}
|
||||
});
|
||||
var ctxDistribution = document.getElementById("sessiondistribution");
|
||||
var dataDistr = {
|
||||
labels: %labelssessiondistribution%,
|
||||
datasets: [
|
||||
{
|
||||
label: 'Session Length Distribution',
|
||||
data: %datasessiondistribution%,
|
||||
backgroundColor: "#89c471",
|
||||
fill: true,
|
||||
borderColor: "#348e0f",
|
||||
borderCapStyle: 'butt',
|
||||
borderDash: [],
|
||||
borderDashOffset: 0.0,
|
||||
borderJoinStyle: 'miter',
|
||||
pointBorderColor: "#348e0f",
|
||||
pointBackgroundColor: "#fff",
|
||||
pointBorderWidth: 1,
|
||||
pointHoverRadius: 5,
|
||||
pointHoverBackgroundColor: "#348e0f",
|
||||
pointHoverBorderColor: "#348e0f",
|
||||
pointHoverBorderWidth: 2,
|
||||
pointRadius: 1,
|
||||
pointHitRadius: 10,
|
||||
spanGaps: false,
|
||||
}]
|
||||
};
|
||||
var sessionDistributions = new Chart(ctxDistribution, {
|
||||
type: 'bar',
|
||||
data: dataDistr,
|
||||
options: {
|
||||
tooltips: {
|
||||
callbacks: {
|
||||
label: function(tooltipItems, data) {
|
||||
return tooltipItems.xLabel+'utes: '+tooltipItems.yLabel+' sessions';
|
||||
}
|
||||
}
|
||||
},
|
||||
scales: {
|
||||
yAxes: [{
|
||||
ticks: {
|
||||
callback: function(value, index, values) {
|
||||
return value+'';
|
||||
}
|
||||
}
|
||||
}]
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
</script>
|
||||
</div>
|
||||
</body>
|
||||
|
@ -14,7 +14,6 @@ import org.powermock.core.classloader.annotations.PrepareForTest;
|
||||
import org.powermock.modules.junit4.PowerMockRunner;
|
||||
import test.java.utils.TestInit;
|
||||
|
||||
import java.io.FileNotFoundException;
|
||||
import java.util.HashMap;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
@ -76,29 +75,6 @@ public class HtmlUtilsTest {
|
||||
assertEquals(result, exp);
|
||||
}
|
||||
|
||||
/**
|
||||
* @throws FileNotFoundException
|
||||
*/
|
||||
@Test
|
||||
public void testGetServerAnalysisUrl() throws Exception {
|
||||
TestInit.init();
|
||||
String result = HtmlUtils.getServerAnalysisUrlWithProtocol();
|
||||
String exp = "http://0.0.0.0:8804/server";
|
||||
assertEquals(exp, result);
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
@Test
|
||||
public void testGetInspectUrl() throws Exception {
|
||||
TestInit.init();
|
||||
String playerName = "Test";
|
||||
String expResult = "http://0.0.0.0:8804/player/Test";
|
||||
String result = HtmlUtils.getInspectUrlWithProtocol(playerName);
|
||||
assertEquals(expResult, result);
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
|
Loading…
Reference in New Issue
Block a user