Benoit Sida 3 år sedan
förälder
incheckning
278d5e1176

+ 1
- 0
.meteor/packages Visa fil

@@ -23,3 +23,4 @@ meyerweb-reset
23 23
 fourseven:scss
24 24
 maxharris9:classnames
25 25
 momentjs:moment
26
+fortawesome:fontawesome

+ 1
- 0
.meteor/versions Visa fil

@@ -24,6 +24,7 @@ ecmascript-runtime@0.3.15
24 24
 ejson@1.0.13
25 25
 es5-shim@4.6.15
26 26
 fastclick@1.0.13
27
+fortawesome:fontawesome@4.7.0
27 28
 fourseven:scss@4.5.0
28 29
 geojson-utils@1.0.10
29 30
 hot-code-push@1.0.4

+ 22
- 6
imports/ui/App.jsx Visa fil

@@ -1,21 +1,37 @@
1 1
 import React, { Component } from 'react';
2 2
 import './styles/App';
3 3
 import Board from './Board';
4
+import Info from './Info';
4 5
 
5 6
 export default class App extends Component {
7
+	constructor(props) {
8
+		super(props);
9
+		this.state = {
10
+			infoVisible: false
11
+		};
12
+	}
13
+
14
+	toggleInfo() {
15
+		this.setState({ infoVisible: !this.state.infoVisible });
16
+	}
17
+
6 18
 	render() {
7 19
 		return (
8 20
 			<div id="app-container">
9
-				<header>ESPTrainer</header>
21
+				<header>
22
+					<h1>ESPTrainer</h1>
23
+					<div className="flex-space" />
24
+					<div><i className="info fa fa-lg fa-info-circle" onClick={this.toggleInfo.bind(this)}/></div>
25
+				</header>
10 26
 				<main id="content">
11
-					{/*<div className="left" />*/}
12 27
 					<div className="center">
13
-						<Board />
14
-						{/*<Actions></Actions>*/}
28
+						{ this.state.infoVisible ? <Info /> : <Board /> }
15 29
 					</div>
16
-					{/*<div className="right" />*/}
17 30
 				</main>
18
-				<footer>Copyright © 2017 Coldiary</footer>
31
+				<footer>
32
+					<div>Copyright © 2017 Coldiary</div>
33
+					<div className="credits">Based on Russell Targ's ESPTrainer on iOS</div>
34
+				</footer>
19 35
 			</div>
20 36
 		);
21 37
 	}

+ 0
- 1
imports/ui/Board.jsx Visa fil

@@ -16,7 +16,6 @@ class Board extends Component {
16 16
 		this.actions = [
17 17
 			{ label: 'Reset', action: this.reset.bind(this), active: () => true },
18 18
 			{ label: 'Pass', action: this.pass.bind(this), active: () => !this.state.end },
19
-			{ label: 'AddScore', action: () => this.registerScore(Math.floor(Math.random() * 100) % 24), active: () => true }
20 19
 		];
21 20
 		this.choices = [0, 1, 2, 3].map(i => this.choice.bind(this, i));
22 21
 	}

+ 1
- 0
imports/ui/BoardLayout.jsx Visa fil

@@ -10,6 +10,7 @@ import './styles/Board';
10 10
 
11 11
 const BoardLayout = ({ active, win, actions, trials, score, scores, image, choices, highlighted }) =>
12 12
 	<div className="board">
13
+		<div className="title">Tap the correct square to see a picture</div>
13 14
 		<Score score={score} />
14 15
 		<div className="squares">
15 16
 			<div className="row">

+ 18
- 0
imports/ui/Info.jsx Visa fil

@@ -0,0 +1,18 @@
1
+import React, { Component, PropTypes } from 'react';
2
+import './styles/Info';
3
+
4
+export default class Info extends Component {
5
+	render() {
6
+		return <div className="Info">
7
+			<em>This program is a clone of the Russell Targ's App on the iOS platform. All credits goes to him.</em>
8
+			<div>Extract from the app:</div>
9
+			<blockquote>
10
+				<div>The player is presented with four colored squares. For each trial, one has been selected at random by the ESP Trainer. Your task is to choose the correct square.</div>
11
+				<div>If you succeed, you will [...] see a large color picture. Otherwise, the system lights up the correct square, and you proceed with the next trial.</div>
12
+				<div>The score indicator at the top counts the number of correct choices. [...] After 24 trials you may begin a new game.</div>
13
+			</blockquote>
14
+			<div>You can find the app at the link below :</div>
15
+			<a href="https://itunes.apple.com/fr/app/esp-trainer/id336882103?mt=8" className="apple-link" />
16
+		</div>;
17
+	}
18
+}

+ 1
- 0
imports/ui/Score.jsx Visa fil

@@ -3,6 +3,7 @@ import './styles/Score';
3 3
 
4 4
 const Score = ({ score }) =>
5 5
 	<div className="score">
6
+		<h3>Correct</h3>
6 7
 		<div className="scale">
7 8
 			{ [...Array(25).keys()].map(x => <div key={x} className="grade" />) }
8 9
 		</div>

+ 24
- 30
imports/ui/ScoreChart.jsx Visa fil

@@ -1,36 +1,30 @@
1 1
 import React, { Component, PropTypes} from 'react';
2 2
 import Chart from 'chart.js';
3 3
 
4
-Chart.defaults.global.legend.labels.fontColor = '#fff';
5
-const dateFormat = 'DD/MM/YYYY H:ss';
6
-const ScoreScales = {
7
-	yAxes: [{
8
-		ticks: {
9
-			fontColor: "#fff",
10
-			stepSize: 6,
11
-			max: 24,
12
-		}
13
-	}],
14
-	xAxes: [{
15
-		type: 'time',
16
-		time: {
17
-			fontColor: "#fff",
18
-			fontSize: 10,
19
-			parser: moment.unix,
20
-			tooltipFormat: dateFormat,
21
-			//unit: 'day'
22
-		},
23
-		ticks: {
24
-			fontColor: "#fff"
25
-		}
26
-	}]
27
-};
4
+
5
+
28 6
 
29 7
 
30 8
 export default class ScoreChart extends Component {
31 9
 	constructor(props) {
32 10
 		super(props);
11
+		Chart.defaults.global.legend.labels.fontColor = '#fff';
33 12
 		this.chart = null;
13
+		this.scoreScales = {
14
+			yAxes: [{
15
+				ticks: {
16
+					fontColor: "#fff",
17
+					stepSize: 6,
18
+					max: 24,
19
+				}
20
+			}],
21
+			xAxes: [{
22
+				ticks: {
23
+					fontColor: "#fff",
24
+					fontSize: 10,
25
+				}
26
+			}]
27
+		};
34 28
 	}
35 29
 
36 30
 	shouldComponentUpdate(nextProps) {
@@ -40,7 +34,7 @@ export default class ScoreChart extends Component {
40 34
 	componentDidMount() {
41 35
 		let labels = Object.keys(this.props.data);
42 36
 		const data = labels.map(key => this.props.data[key]);
43
-		// labels = labels.map(d => moment.unix(d).format(dateFormat).split(' '));
37
+		labels = labels.map(ts => moment.unix(ts).format('DD/MM/YYYY H:ss'));
44 38
 		this.chart = new Chart(this.canvas, {
45 39
 			type: 'line',
46 40
 			data: {
@@ -48,26 +42,26 @@ export default class ScoreChart extends Component {
48 42
 				datasets: [{
49 43
 					label: 'Progression',
50 44
 					data: data,
51
-					backgroundColor: 'rgba(255, 99, 132, 0.2)',
52
-					borderColor: 'rgba(255,99,132,1)',
45
+					backgroundColor: 'rgba(33, 150, 243, 0.2)',
46
+					borderColor: 'rgba(33, 150, 243, 1)',
53 47
 					borderWidth: 1
54 48
 				}]
55 49
 			},
56
-			options: { scales: ScoreScales }
50
+			options: { scales: this.scoreScales }
57 51
 		});
58 52
 	}
59 53
 
60 54
 	componentDidUpdate() {
61 55
 		let labels = Object.keys(this.props.data);
62 56
 		const data = labels.map(key => this.props.data[key]);
63
-		// labels = labels.map(d => moment.unix(d).format(dateFormat).split(' '));
57
+		labels = labels.map(ts => moment.unix(ts).format('DD/MM/YYYY H:ss'));
64 58
 		this.chart.data.labels = labels;
65 59
 		this.chart.data.datasets[0].data = data;
66 60
 		this.chart.update();
67 61
 	}
68 62
 
69 63
 	render() {
70
-		return <canvas ref={(node) => this.canvas = node} width={400}/>;
64
+		return <canvas ref={(node) => this.canvas = node} />;
71 65
 	}
72 66
 }
73 67
 

+ 1
- 1
imports/ui/styles/Actions.scss Visa fil

@@ -4,7 +4,7 @@
4 4
   display: flex;
5 5
   justify-content: center;
6 6
   flex-wrap: wrap;
7
-  margin-top: 20px;
7
+  margin: 20px 0;
8 8
 
9 9
   button {
10 10
     background: white;

+ 22
- 2
imports/ui/styles/App.scss Visa fil

@@ -12,15 +12,30 @@ main {
12 12
     display: flex;
13 13
     flex-direction: row;
14 14
     justify-content: center;
15
-    align-items: stretch;
15
+    align-items: flex-start;
16 16
 }
17 17
 
18 18
 header {
19
+    display: flex;
20
+    flex-direction: row;
19 21
     height: 64px;
20 22
     background: #23273c;
21 23
     color: white;
22 24
     line-height: 64px;
23
-    padding-left: 10px;
25
+    padding: 0 10px;
26
+
27
+    h1 {
28
+        letter-spacing: 0.1em;
29
+        font-size: 1.5em;
30
+    }
31
+
32
+    .flex-space {
33
+        flex: 1;
34
+    }
35
+    
36
+    .info {
37
+        cursor: pointer;
38
+    }
24 39
 }
25 40
 
26 41
 .left, .right {
@@ -59,4 +74,9 @@ footer {
59 74
     text-align: center;
60 75
     color: white;
61 76
     padding: 10px;
77
+
78
+    .credits {
79
+        margin-top: 10px;
80
+        font-size: 0.8em;
81
+    }
62 82
 }

+ 7
- 0
imports/ui/styles/Board.scss Visa fil

@@ -4,6 +4,13 @@
4 4
     align-items: stretch;
5 5
     max-width: 800px;
6 6
 
7
+    .title {
8
+        color: #fff;
9
+        text-align: center;
10
+        margin-bottom: 30px;
11
+        letter-spacing: 0.1em;
12
+    }
13
+
7 14
     .squares {
8 15
         position: relative;
9 16
         display: flex;

+ 50
- 0
imports/ui/styles/Info.scss Visa fil

@@ -0,0 +1,50 @@
1
+@import "compat";
2
+
3
+.Info {
4
+  max-width: 440px;
5
+  display: flex;
6
+  flex-direction: column;
7
+  align-items: center;
8
+  color: #fff;
9
+  padding: 20px 50px;
10
+  @include box-sizing(border-box);
11
+  text-align: center;
12
+
13
+  blockquote  {
14
+    border-left: 3px solid grey;
15
+    padding-left: 10px;
16
+    text-align: justify;
17
+    margin: 20px 0;
18
+
19
+    &:before {
20
+      content: '“';
21
+      float: left;
22
+      font-size: 2em;
23
+      margin-right: 20px;
24
+    }
25
+
26
+    &:after {
27
+      content: '”';
28
+      float: right;
29
+      font-size: 2em;
30
+      margin-top: -25px;
31
+    }
32
+
33
+  }
34
+
35
+  * {
36
+    margin-bottom: 10px;
37
+  }
38
+
39
+  .apple-link {
40
+    display: inline-block;
41
+    overflow: hidden;
42
+    margin-top: 20px;
43
+    background: url(//linkmaker.itunes.apple.com/assets/shared/badges/fr-fr/appstore-lrg.svg) no-repeat;
44
+    width: 135px;
45
+    height: 40px;
46
+    background-size: contain;
47
+    cursor: pointer;
48
+  }
49
+  
50
+}

+ 11
- 3
imports/ui/styles/Score.scss Visa fil

@@ -5,6 +5,13 @@
5 5
   flex-direction: column;
6 6
   margin-bottom: 50px;
7 7
 
8
+  h3 {
9
+    color: #fff;
10
+    margin-bottom: 10px;
11
+    text-transform: uppercase;
12
+    letter-spacing: 0.1em;
13
+  }
14
+
8 15
   .current-score {
9 16
     background: #fff;
10 17
     height: 3px;
@@ -36,9 +43,10 @@
36 43
       @mixin grade-label($number) {
37 44
         content: quote(inspect($number));
38 45
         position: absolute;
39
-        top: -20px;
40
-        @if($number > 10) { left: -8px; }
41
-        @else { left: -4px; }
46
+        font-size: 0.7em;
47
+        top: -15px;
48
+        @if($number > 10) { left: -5px; }
49
+        @else { left: -2px; }
42 50
         color: white;
43 51
       }
44 52
 

+ 5
- 1
imports/ui/styles/Square.scss Visa fil

@@ -1,5 +1,6 @@
1 1
 @import "gradient";
2 2
 @import "shadow";
3
+@import "compat";
3 4
 
4 5
 $square-blue: blue;
5 6
 $square-green: green;
@@ -25,7 +26,10 @@ $square-yellow: darken(yellow, 20);
25 26
         @if($inverted) { @include gradient(lighten($color, 20), $color, $direction); }
26 27
         @else { @include gradient($color, lighten($color, 20), $direction); }
27 28
 
28
-        &.highlighted { @include radial-gradient($color); }
29
+        &.highlighted {
30
+            @include radial-gradient($color);
31
+            @include scale(1.1);
32
+        }
29 33
 
30 34
         &.disabled {
31 35
             $color: desaturate($color, 50);

+ 13
- 0
imports/ui/styles/_compat.scss Visa fil

@@ -0,0 +1,13 @@
1
+@mixin scale($amount) {
2
+  -webkit-transform: scale($amount);
3
+  -moz-transform: scale($amount);
4
+  -ms-transform: scale($amount);
5
+  -o-transform: scale($amount);
6
+  transform: scale($amount);
7
+}
8
+
9
+@mixin box-sizing($value) {
10
+  -webkit-box-sizing: $value;
11
+  -moz-box-sizing: $value;
12
+  box-sizing: $value;
13
+}