Nikatlas %!s(int64=6) %!d(string=hai) anos
pai
achega
95d4d431c7

+ 1 - 0
package.json

@@ -5,6 +5,7 @@
   "dependencies": {
     "@uirouter/react": "^0.5.4",
     "bootstrap": "^4.0.0-beta.3",
+    "chart.js": "^2.7.2",
     "dat.gui": "^0.7.1",
     "material-ui": "^0.20.0",
     "pixi-layers": "^0.1.9",

+ 209 - 209
src/Game/game/machine/GameMachine.js

@@ -1,223 +1,223 @@
 var Card = require('./Card.js');
 
 class GameMachine {
-	constructor() {
-		this.state = {
-			board: new Board(),
-			players: [],
-			hash: "0123456789"
-		};
-
-	}
-
-	setState(state) {
-		this.state = { ...this.state, ...state};
-	}
-
-	setBoard(board) {
-		this.state = { ...this.state, board};
-	}
-
-	setPlayers(players) {
-		this.state = { ...this.state, players};
-	}
-
-	runMove(move) {
-		move.performMove(this.state.board);
-	}
+    constructor() {
+        this.state = {
+            board: new Board(),
+            players: [],
+            hash: "0123456789"
+        };
+
+    }
+
+    setState(state) {
+        this.state = { ...this.state, ...state};
+    }
+
+    setBoard(board) {
+        this.state = { ...this.state, board};
+    }
+
+    setPlayers(players) {
+        this.state = { ...this.state, players};
+    }
+
+    runMove(move) {
+        move.performMove(this.state.board);
+    }
 }
 
 class Board {
-	constructor() {
-		this.data = [];
-		this.owners = [];
-
-		// These 2 to be updated after every move
-		this.triggerPaths = []; // like attackVectors
-		this.plusPaths = []; // like attackVectors
-		for (var i=0; i < 9; i += 1) {
-			this.triggerPaths[i] = [];
-			this.plusPaths[i] = {
-				winner: -1,
-				sums: []
-			}
-		}
-	}
-
-	debug() {
-		console.log('BOARD');
-		console.log('---------------------------');
-		console.log('Cards :');
-		let s = '';
-		for(var i=0,j=0;i<this.data.length;i+=1) {
-			s += this.owners[i] + ':' + this.data[i] + '\t';
-			j += 1;
-			if(j%3===0)s += '\n';
-		}
-		console.log(s);
-		console.log('---------------------------');
-		console.log('Triggers');
-		console.log('---------------------------');
-		s = '';
-		for(var i=0,j=0;i<this.triggerPaths.length;i+=1) {
-			s += '[' + this.triggerPaths[i] + ']' + '\t\t';
-			j += 1;
-			if(j%3===0)s += '\n';
-		}
-		console.log(s);
-		console.log('---------------------------');
-		console.log('Pluspaths');
-		console.log('---------------------------');
-		s = '';
-		for(var i=0,j=0;i<this.plusPaths.length;i+=1) {
-			s += '[' + (this.plusPaths[i].winner) + ']' + '\t\t';
-			j += 1;
-			if(j%3===0)s += '\n';
-		}
-		console.log(s);
-		console.log('---------------------------');
-
-	}
-
-	putCard(card, position, player) { // position = 0-9
-		this.data[ position ] = card;
-		this.owners[position] = player;
-
-		this._calculatePlusAndTriggers(position);
-		this._analyze(position);
-	}
-
-	_calculatePlusAndTriggers(position) {
-		const attacker 		= this.data[position];
-		for (let j = 0; j < 4; j += 1) {
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
-			
-			const dx = this._getDisplacement(j);
-			const attackedCard  = this.data[position + dx];
-			const defendJ = ( j + 2 ) % 4;
-
-			if (attackedCard) {
-				const sum = attacker.attack[j] + attackedCard.attack[defendJ];
-				this.plusPaths[	 	 position  ].sums[j] = sum;
-				this.plusPaths[   position + dx].sums[defendJ] = sum;
-				this.triggerPaths[	 position  ][j] =   attacker.attack[j] - attackedCard.attack[defendJ];
-				this.triggerPaths[position + dx][defendJ] =   -this	.triggerPaths[position][j]; // opposite to the above
-			}
-		}
-	}
-
-	_getDisplacement(j) {
-		switch(j) {
-			case 0: return 1;//return {x: 1, y:0};
-			case 1: return -3;//return {x: 0, y:1};
-			case 2: return -1;//return {x: -1, y:0};
-			case 3: return 3;//return {x: 0, y:-1};
-			default: throw Error("Cannot _getDisplacement of this value: " + j);
-		}
-	}
-
-	_flipCard(position, combo, owner) {
-		// change owner!
-
-		this.owners[position] = owner;
-		if(combo) this._analyze(position, combo);
-	}
-
-	_analyze(position, combo) {
-		// check rules!
-		if(			this._checkSameRule(position) && !combo ) {
-			// Apply Same Rule
-			this._applySameRule(position);
-		} else if ( this._checkPlusRule(position) && !combo ) {
-			// Apply Plus Rule
-			this._applyPlusRule(position);
-		} else {
-			this._applyAttackRule(position);
-		}
-	}
-
-	_applyAttackRule(position) { //seems ok
-		if ( !this.triggerPaths[position] ) return;
-		for (let j = 0; j < 4; j += 1) {
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
-			const dx = this._getDisplacement(j);
-			if ( this.triggerPaths[position][j] > 0 ) {
-				this._flipCard(position + dx, false, this.owners[position]);
-			}
-		}
-	}
-
-	_applySameRule(position) {
-		for (let j = 0; j < 4; j += 1) {
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
-			const dx = this._getDisplacement(j);
-			if ( this.triggerPaths[position][j] === 0 ) {
-				this._flipCard(position + dx, true, this.owners[position]);
-			}
-		}	
-	}
-
-	_applyPlusRule(position) {
-		for (let j = 0; j < 4; j += 1) { // this for loop can be fixed seems obsolete & slow
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
-			const dx = this._getDisplacement(j);
-			if ( this.plusPaths[position].sums[j] === this.plusPaths[position].winner ) {
-				this._flipCard(position + dx, true, this.owners[position]);
-			}
-		}
-	}
-
-	_checkSameRule(position) {
-		const card = this.data[position];
-		let  sames = 0;
-		for (let j = 0; j < 4; j += 1) {
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;			
-			if (this.triggerPaths[position] && 
-				this.triggerPaths[position][j] === 0) {
-				sames += 1;
-			}
-		}	
-		return sames > 1;
-	}
-
-	_checkPlusRule(position) { // refactor plz // need fix (problem double plus a.k.a. four side attack)
-		const card = this.data[position];
-		let pluses = {};
-		let sum = -1;
-		for (let j = 0; j < 4; j += 1) {
-			if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
-			if(sum = this.plusPaths[position].sums[j])
-				pluses[sum] = (pluses[sum] || 0) + 1;
-		}
-		for (var i in pluses) {
-			if (pluses[i] > 1) {
-				this.plusPaths[position].winner = parseInt(i);
-				console.log(i);
-				return true;
-			}
-		}
-		this.plusPaths[position].winner = -1;
-		return false;
-	}
-
-	isEmpty(position) {
-		return !!this.data[position];
-	}
+    constructor() {
+        this.data = [];
+        this.owners = [];
+
+        // These 2 to be updated after every move
+        this.triggerPaths = []; // like attackVectors
+        this.plusPaths = []; // like attackVectors
+        for (var i=0; i < 9; i += 1) {
+            this.triggerPaths[i] = [];
+            this.plusPaths[i] = {
+                winner: -1,
+                sums: []
+            }
+        }
+    }
+
+    debug() {
+        console.log('BOARD');
+        console.log('---------------------------');
+        console.log('Cards :');
+        let s = '';
+        for(var i=0,j=0;i<this.data.length;i+=1) {
+            s += this.owners[i] + ':' + this.data[i] + '\t';
+            j += 1;
+            if(j%3===0)s += '\n';
+        }
+        console.log(s);
+        console.log('---------------------------');
+        console.log('Triggers');
+        console.log('---------------------------');
+        s = '';
+        for(var i=0,j=0;i<this.triggerPaths.length;i+=1) {
+            s += '[' + this.triggerPaths[i] + ']' + '\t\t';
+            j += 1;
+            if(j%3===0)s += '\n';
+        }
+        console.log(s);
+        console.log('---------------------------');
+        console.log('Pluspaths');
+        console.log('---------------------------');
+        s = '';
+        for(var i=0,j=0;i<this.plusPaths.length;i+=1) {
+            s += '[' + (this.plusPaths[i].winner) + ']' + '\t\t';
+            j += 1;
+            if(j%3===0)s += '\n';
+        }
+        console.log(s);
+        console.log('---------------------------');
+
+    }
+
+    putCard(card, position, player) { // position = 0-9
+        this.data[ position ] = card;
+        this.owners[position] = player;
+
+        this._calculatePlusAndTriggers(position);
+        this._analyze(position);
+    }
+
+    _calculatePlusAndTriggers(position) {
+        const attacker      = this.data[position];
+        for (let j = 0; j < 4; j += 1) {
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
+            
+            const dx = this._getDisplacement(j);
+            const attackedCard  = this.data[position + dx];
+            const defendJ = ( j + 2 ) % 4;
+
+            if (attackedCard) {
+                const sum = attacker.attack[j] + attackedCard.attack[defendJ];
+                this.plusPaths[      position  ].sums[j] = sum;
+                this.plusPaths[   position + dx].sums[defendJ] = sum;
+                this.triggerPaths[   position  ][j] =   attacker.attack[j] - attackedCard.attack[defendJ];
+                this.triggerPaths[position + dx][defendJ] =   -this .triggerPaths[position][j]; // opposite to the above
+            }
+        }
+    }
+
+    _getDisplacement(j) {
+        switch(j) {
+            case 0: return 1;//return {x: 1, y:0};
+            case 1: return -3;//return {x: 0, y:1};
+            case 2: return -1;//return {x: -1, y:0};
+            case 3: return 3;//return {x: 0, y:-1};
+            default: throw Error("Cannot _getDisplacement of this value: " + j);
+        }
+    }
+
+    _flipCard(position, combo, owner) {
+        // change owner!
+
+        this.owners[position] = owner;
+        if(combo) this._analyze(position, combo);
+    }
+
+    _analyze(position, combo) {
+        // check rules!
+        if(         this._checkSameRule(position) && !combo ) {
+            // Apply Same Rule
+            this._applySameRule(position);
+        } else if ( this._checkPlusRule(position) && !combo ) {
+            // Apply Plus Rule
+            this._applyPlusRule(position);
+        } else {
+            this._applyAttackRule(position);
+        }
+    }
+
+    _applyAttackRule(position) { //seems ok
+        if ( !this.triggerPaths[position] ) return;
+        for (let j = 0; j < 4; j += 1) {
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
+            const dx = this._getDisplacement(j);
+            if ( this.triggerPaths[position][j] > 0 ) {
+                this._flipCard(position + dx, false, this.owners[position]);
+            }
+        }
+    }
+
+    _applySameRule(position) {
+        for (let j = 0; j < 4; j += 1) {
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
+            const dx = this._getDisplacement(j);
+            if ( this.triggerPaths[position][j] === 0 ) {
+                this._flipCard(position + dx, true, this.owners[position]);
+            }
+        }   
+    }
+
+    _applyPlusRule(position) {
+        for (let j = 0; j < 4; j += 1) { // this for loop can be fixed seems obsolete & slow
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
+            const dx = this._getDisplacement(j);
+            if ( this.plusPaths[position].sums[j] === this.plusPaths[position].winner ) {
+                this._flipCard(position + dx, true, this.owners[position]);
+            }
+        }
+    }
+
+    _checkSameRule(position) {
+        const card = this.data[position];
+        let  sames = 0;
+        for (let j = 0; j < 4; j += 1) {
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;            
+            if (this.triggerPaths[position] && 
+                this.triggerPaths[position][j] === 0) {
+                sames += 1;
+            }
+        }   
+        return sames > 1;
+    }
+
+    _checkPlusRule(position) { // refactor plz // need fix (problem double plus a.k.a. four side attack)
+        const card = this.data[position];
+        let pluses = {};
+        let sum = -1;
+        for (let j = 0; j < 4; j += 1) {
+            if ( Board.ATTACK_VECTORS[position][j] === 0 ) continue;
+            if(sum = this.plusPaths[position].sums[j])
+                pluses[sum] = (pluses[sum] || 0) + 1;
+        }
+        for (var i in pluses) {
+            if (pluses[i] > 1) {
+                this.plusPaths[position].winner = parseInt(i);
+                console.log(i);
+                return true;
+            }
+        }
+        this.plusPaths[position].winner = -1;
+        return false;
+    }
+
+    isEmpty(position) {
+        return !!this.data[position];
+    }
 }
 // START From top left goin row row  
 Board.ATTACK_VECTORS = [
 //  [R, U, L, D] // right up left down
-	[1, 0, 0, 1],
-	[1, 0, 1, 1],
-	[0, 0, 1, 1],
-	[1, 1, 0, 1],
-	[1, 1, 1, 1],
-	[0, 1, 1, 1],
-	[1, 1, 0, 0],
-	[1, 1, 1, 0],
-	[0, 1, 1, 0]
+    [1, 0, 0, 1],
+    [1, 0, 1, 1],
+    [0, 0, 1, 1],
+    [1, 1, 0, 1],
+    [1, 1, 1, 1],
+    [0, 1, 1, 1],
+    [1, 1, 0, 0],
+    [1, 1, 1, 0],
+    [0, 1, 1, 0]
 ];
 
 module.exports = {
-	GameMachine
+    GameMachine
 };

+ 19 - 19
src/Game/views/buildings/Board.js

@@ -3,7 +3,7 @@ import config from '../../config';
 
 import GuiableContainer from '../../../helpers/Guiable';
 import Deck from '../../assets/deck';
-//import CardHolder from '../base/CardHolder';
+import CardHolder from '../base/CardHolder';
 import CollectionHolder from '../base/CollectionHolder';
 import Injector from '../../services/Injector';
 
@@ -52,24 +52,24 @@ class BoardHandler extends GuiableContainer{
 
 
         this.holders = [];
-        // this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': -230, team: 0, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(0, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': -230, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(1, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': -230, team: 0, id: 1}).scaleTo(BoardScale).onDrop((c) => this.placeCard(2, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': 0, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(3, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': 0, team: 0, id: 2}).scaleTo(BoardScale).onDrop((c) => this.placeCard(4, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': 0, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(5, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': 230, team: 1, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(6, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(7, c)));
-        // this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(8, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': -230, team: 0, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(0, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': -230, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(1, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': -230, team: 0, id: 1}).scaleTo(BoardScale).onDrop((c) => this.placeCard(2, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': 0, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(3, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': 0, team: 0, id: 2}).scaleTo(BoardScale).onDrop((c) => this.placeCard(4, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': 0, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(5, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': 230, team: 1, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(6, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(7, c)));
-        this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(8, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': -230, team: 0, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(0, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': -230, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(1, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': -230, team: 0, id: 1}).scaleTo(BoardScale).onDrop((c) => this.placeCard(2, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': 0, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(3, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': 0, team: 0, id: 2}).scaleTo(BoardScale).onDrop((c) => this.placeCard(4, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': 0, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(5, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -220, 'y': 230, team: 1, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(6, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': -50, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(7, c)));
+        this.holders.push(new CardHolder({GameLayer, 'x': 120, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(8, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': -230, team: 0, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(0, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': -230, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(1, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': -230, team: 0, id: 1}).scaleTo(BoardScale).onDrop((c) => this.placeCard(2, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': 0, team: 1, id: 5}).scaleTo(BoardScale).onDrop((c) => this.placeCard(3, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': 0, team: 0, id: 2}).scaleTo(BoardScale).onDrop((c) => this.placeCard(4, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': 0, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(5, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -220, 'y': 230, team: 1, id: 4}).scaleTo(BoardScale).onDrop((c) => this.placeCard(6, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': -50, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(7, c)));
+        // this.holders.push(new CollectionHolder({GameLayer, 'x': 120, 'y': 230, team: 1, id: 3}).scaleTo(BoardScale).onDrop((c) => this.placeCard(8, c)));
         this.holders.forEach((item) => item.parentLayer = Injector.getByName('TopLayer'));
         this.holders.forEach((item) => item.lockable());
         this.holders.forEach((item) => this.addChild(item));

+ 15 - 0
src/components/Stats.css

@@ -0,0 +1,15 @@
+.chartBox {
+	width: 600px;
+	height: 250px;
+	display: inline-block;
+}
+.chartBox-sm {
+	width: 300px;
+	height: 200px;
+	display: inline-block;
+}
+.chartBox-lg {
+	width: 1000px;
+	height: 400px;
+	display: inline-block;
+}

+ 273 - 0
src/components/Stats.js

@@ -0,0 +1,273 @@
+import React, { Component } from 'react';
+import './Stats.css';
+import Chart from 'chart.js';
+
+import Zigg from '../helpers/generator'
+
+var seed = 1;
+
+let gen = new Zigg();
+function random() {
+    // var x = Math.sin(seed++) * 10000;
+    // return (x - Math.floor(x))* 123456;
+    let n =  gen.nextGaussian() * 2 + 4.5;
+    return n;
+}
+function r9() {
+    return (parseInt( random() ) % 9) + 1;
+}
+let bgColors = [	
+	'rgba(255, 99, 132, 0.2)',
+    'rgba(54, 162, 235, 0.2)',
+    'rgba(255, 206, 86, 0.2)',
+    'rgba(75, 192, 192, 0.2)',
+    'rgba(153, 102, 255, 0.2)',
+];
+
+let borderColors = [	
+	'rgba(255,99,132,1)',
+    'rgba(54, 162, 235, 1)',
+    'rgba(255, 206, 86, 1)',
+    'rgba(75, 192, 192, 1)',
+    'rgba(153, 102, 255, 1)',
+];
+
+function createChart(chartID, data, title = "Simple Attack", maxScale = 30) {
+	let labels = Array.apply(null, Array(data.length)).map((a,i) => i+1);
+	let numbers = Array.apply(null, Array(data.length)).map((a,i) => parseInt(random() * 1032132 % 5));
+	let borders = numbers.map((a) => borderColors[a]); 
+	let bgs = numbers.map((a) => bgColors[a]);
+
+	var ctx = document.getElementById(chartID).getContext('2d');
+		var WA = new Chart(ctx, {
+		    type: 'bar',
+		    data: {
+		        labels: labels,
+		        datasets: [{
+		            label: title,
+		            data: data,
+		            backgroundColor: bgs,
+		            borderColor: borders,
+		            borderWidth: 1
+		        }]
+		    },
+		    options: {
+		        scales: {
+		            yAxes: [{
+		                ticks: {
+		                    beginAtZero:true,
+		                    max: maxScale
+		                }
+		            }]
+		        }
+		    }
+		});
+}
+
+
+
+class Stats extends Component {
+	constructor(props) {
+		super(props);
+
+		let {
+			deck
+		} = props;
+
+		deck = this.createRandomDeck();
+		this.numbers = this.calculateNumbers(deck);
+		this.sums    = this.calculateSummables(this.numbers);
+		this.wapropabilities = this.findWinning(deck);
+		this.losepropabilities = this.findLosing(deck);
+		this.samepropabilities = this.findSame(deck);
+		this.solosamepropabilities = this.findSoloSame(this.samepropabilities);
+	}
+	
+	createRandomDeck() {
+		let a = [];
+		for(var j=0;j<100;j++){
+			let b = [];
+			for(var i=0;i<4;i++){
+				b[i] = r9();
+			}
+			a.push(b);
+		}
+		return a;
+	}
+
+	componentDidMount() {
+        createChart("chart11", this.numbers[0], "Right Numbers Distribution");
+        createChart("chart12", this.numbers[1], "Up Numbers Distribution");
+        createChart("chart13", this.numbers[2], "Left Numbers Distribution");
+        createChart("chart14", this.numbers[3], "Down Numbers Distribution");
+        createChart("chart21", this.sums[0], "Right Summable Distribution", 100);
+        createChart("chart22", this.sums[1], "Up Summable Distribution", 100);
+        createChart("chart23", this.sums[2], "Left Summable Distribution", 100);
+        createChart("chart24", this.sums[3], "Down Summable Distribution", 100);
+        createChart("chart31", this.wapropabilities[0], "Right Winning Chance", 100);
+        createChart("chart32", this.wapropabilities[1], "Up Winning Chance", 100);
+        createChart("chart33", this.wapropabilities[2], "Left Winning Chance", 100);
+        createChart("chart34", this.wapropabilities[3], "Down Winning Chance", 100);
+        createChart("chart41", this.samepropabilities[0], "Right Same Chance", 100);
+        createChart("chart42", this.samepropabilities[1], "Up Same Chance", 100);
+        createChart("chart43", this.samepropabilities[2], "Left Same Chance", 100);
+        createChart("chart44", this.samepropabilities[3], "Down Same Chance", 100);
+        createChart("chart51", this.solosamepropabilities, "Same Chance Of card", 100);
+	}
+	componentWillUnmount() {
+       
+	}
+
+	goTo = (stateName) => {
+		this.props.resolves.$transition$.router.stateService.go(stateName);
+	}
+
+	findSame(deck) {
+		let nums = this.calculateNumbers(deck);
+		let sums = this.calculateSummables(nums);
+
+		let cards = deck.map((card) => {
+			return [
+				nums[2][card[0]-1] || 0,
+				nums[3][card[1]-1] || 0,
+				nums[0][card[2]-1] || 0,
+				nums[1][card[3]-1] || 0
+			];
+		});
+
+		// 100 - to find the NOT SAME Chance on side 
+		let result = cards[0].map((col, i) => cards.map(row => row[i]));
+		return result; 
+	}
+
+	findSoloSame(cards) {
+		let a = [];
+		for(var i=0;i<cards[0].length;i++){
+			a[i] = ((100-cards[0][i])/100) * ((100-cards[1][i])/100) * ((100-cards[2][i])/100) * ((100-cards[3][i])/100);
+			a[i] = (1-a[i]) * 100;
+		}
+		return a;
+	}
+
+	findLosing(deck) {
+		let wins = this.findWinning(deck);
+		let loses = wins.map((sidewins) => sidewins.map((n) => 100-n));
+		return loses;
+	}
+
+	findWinning(deck) {
+		let nums = this.calculateNumbers(deck);
+		let sums = this.calculateSummables(nums);
+
+		let cards = deck.map((card) => {
+			return [
+				sums[2][card[0]-2],
+				sums[3][card[1]-2],
+				sums[0][card[2]-2],
+				sums[1][card[3]-2]
+			];
+		});
+
+		let result = cards[0].map((col, i) => cards.map(row => row[i]));
+		return result;
+	}
+
+	// Athroistiki katanomi arithmwn
+	calculateSummables(nums) {
+		let sums = nums.map((arr, index) => {
+			let sum = 0;
+			return arr.map((item) => sum = sum + item);
+		});		
+		return sums;
+	}
+
+	// Katanomi arithmwn
+	calculateNumbers(deck) {
+		let nums = [
+			Array.apply(null, Array(9)).map(Number.prototype.valueOf,0),
+			Array.apply(null, Array(9)).map(Number.prototype.valueOf,0),
+			Array.apply(null, Array(9)).map(Number.prototype.valueOf,0),
+			Array.apply(null, Array(9)).map(Number.prototype.valueOf,0)
+		];
+
+		deck.map((card) => 
+			card.map((number,side) => {
+				nums[side][number-1] += 1;
+			})
+		);
+		return nums;
+	}
+
+	render() {
+	    return (
+	    <div>
+		    <div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart11" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart12" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart13" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart14" width="300" height="200"></canvas>
+		    	</div>
+		    </div>
+		    <div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart21" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart22" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart23" width="300" height="200"></canvas>
+		    	</div>
+		    	<div className="chartBox-sm">
+		    		<canvas id="chart24" width="300" height="200"></canvas>
+		    	</div>
+		    </div>
+		    <div>
+		    	<div className="chartBox">
+		    		<canvas id="chart31" width="250" height="100"></canvas>
+		    	</div>
+		    	<div className="chartBox">
+		    		<canvas id="chart32" width="250" height="100"></canvas>
+		    	</div>
+		    </div>
+		    <div>
+		    	<div className="chartBox">
+		    		<canvas id="chart33" width="250" height="100"></canvas>
+		    	</div>
+		    	<div className="chartBox">
+		    		<canvas id="chart34" width="250" height="100"></canvas>
+		    	</div>
+		    </div><div>
+		    	<div className="chartBox">
+		    		<canvas id="chart41" width="250" height="100"></canvas>
+		    	</div>
+		    	<div className="chartBox">
+		    		<canvas id="chart42" width="250" height="100"></canvas>
+		    	</div>
+		    </div>
+		    <div>
+		    	<div className="chartBox">
+		    		<canvas id="chart43" width="250" height="100"></canvas>
+		    	</div>
+		    	<div className="chartBox">
+		    		<canvas id="chart44" width="250" height="100"></canvas>
+		    	</div>
+		    </div>
+		    <div>
+		    	<div className="chartBox-lg">
+		    		<canvas id="chart51" width="200" height="100"></canvas>
+		    	</div>
+		    </div>
+	    </div>
+	    );
+	}
+}
+
+export default Stats;

+ 92 - 0
src/helpers/generator.js

@@ -0,0 +1,92 @@
+function Ziggurat(){
+
+  var jsr = 123456789;
+
+  var wn = Array(128);
+  var fn = Array(128);
+  var kn = Array(128);
+
+  function RNOR(){
+    var hz = SHR3();
+    var iz = hz & 127;
+    return (Math.abs(hz) < kn[iz]) ? hz * wn[iz] : nfix(hz, iz);
+  }
+
+  this.nextGaussian = function(){
+    return RNOR();
+  }
+
+  function nfix(hz, iz){
+    var r = 3.442619855899;
+    var r1 = 1.0 / r;
+    var x;
+    var y;
+    while(true){
+      x = hz * wn[iz];
+      if( iz == 0 ){
+        x = (-Math.log(UNI()) * r1); 
+        y = -Math.log(UNI());
+        while( y + y < x * x){
+          x = (-Math.log(UNI()) * r1); 
+          y = -Math.log(UNI());
+        }
+        return ( hz > 0 ) ? r+x : -r-x;
+      }
+
+      if( fn[iz] + UNI() * (fn[iz-1] - fn[iz]) < Math.exp(-0.5 * x * x) ){
+         return x;
+      }
+      hz = SHR3();
+      iz = hz & 127;
+ 
+      if( Math.abs(hz) < kn[iz]){
+        return (hz * wn[iz]);
+      }
+    }
+  }
+
+  function SHR3(){
+    var jz = jsr;
+    var jzr = jsr;
+    jzr ^= (jzr << 13);
+    jzr ^= (jzr >>> 17);
+    jzr ^= (jzr << 5);
+    jsr = jzr;
+    return (jz+jzr) | 0;
+  }
+
+  function UNI(){
+    return 0.5 * (1 + SHR3() / -Math.pow(2,31));
+  }
+
+  function zigset(){
+    // seed generator based on current time
+    //jsr ^= new Date().getTime();
+
+    var m1 = 2147483648.0;
+    var dn = 3.442619855899;
+    var tn = dn;
+    var vn = 9.91256303526217e-3;
+    
+    var q = vn / Math.exp(-0.5 * dn * dn);
+    kn[0] = Math.floor((dn/q)*m1);
+    kn[1] = 0;
+
+    wn[0] = q / m1;
+    wn[127] = dn / m1;
+
+    fn[0] = 1.0;
+    fn[127] = Math.exp(-0.5 * dn * dn);
+
+    for(var i = 126; i >= 1; i--){
+      dn = Math.sqrt(-2.0 * Math.log( vn / dn + Math.exp( -0.5 * dn * dn)));
+      kn[i+1] = Math.floor((dn/tn)*m1);
+      tn = dn;
+      fn[i] = Math.exp(-0.5 * dn * dn);
+      wn[i] = dn / m1;
+    }
+  }
+  zigset();
+}
+
+export default Ziggurat;

+ 6 - 0
src/states.js

@@ -1,6 +1,7 @@
 import Game from './components/Game';
 import Home from './components/Home';
 import Playground from './components/Playground';
+import Stats from './components/Stats';
 
 export default [
 {
@@ -17,5 +18,10 @@ export default [
   name : 'playground',
   url  : '/playground',
   component: Playground
+},
+{
+  name : 'stats',
+  url  : '/stats',
+  component: Stats
 }
 ];