Skip to content

Instantly share code, notes, and snippets.

@porfidev
Created November 10, 2017 19:09
Show Gist options
  • Save porfidev/fc12bbe422290307fe1f47ba8d748479 to your computer and use it in GitHub Desktop.
Save porfidev/fc12bbe422290307fe1f47ba8d748479 to your computer and use it in GitHub Desktop.
Juego de prueba para el curso de react.js (se necesita transpilar)
/** UTILITARIO **/
const possibleCombinationSum = function(arr, n) {
if (arr.indexOf(n) >= 0) { return true; }
if (arr[0] > n) { return false; }
if (arr[arr.length - 1] > n) {
arr.pop();
return possibleCombinationSum(arr, n);
}
var listSize = arr.length, combinationsCount = (1 << listSize)
for (var i = 1; i < combinationsCount ; i++ ) {
var combinationSum = 0;
for (var j=0 ; j < listSize ; j++) {
if (i & (1 << j)) { combinationSum += arr[j]; }
}
if (n === combinationSum) { return true; }
}
return false;
};
/** Estrellas a mostrar **/
const Stars = (props) => {
//const numberOfStars = 1 + Math.floor(Math.random()*9);
// let stars = [];
// for(let i = 0; i < numberOfStars; i++){
// stars.push(<i key={i} className="fa fa-star"></i>);
// }
return (
<div className="col-5">
{_.range(props.numberOfStars).map(i =>
<i key={i} className="fa fa-star"></i>
)}
</div>
)
}
const Button = (props) => {
let button;
switch(props.doAnswerIsCorrect){
case true:
button = <button className="btn btn-success" onClick={props.answerIsAccepted}><i className='fa fa-check'></i> </button>;
break;
case false:
button = <button className="btn btn-danger"><i className='fa fa-times'></i> </button>;
break;
default:
button = <button className="btn btn-primary"
onClick={props.doVerifyAnswer}
disabled={ props.selectedNumbers.length === 0 }> = </button>;
break;
}
return (
<div className="col-2">
{button}
<br /> <br />
<button className="btn btn-warning btn-sm center"
onClick={props.doRedraw}
disabled={props.redrawsAvailable === 0} >
<i className="fa fa-refresh"></i> {props.redrawsAvailable}
</button>
</div>
)
}
/** Respuestas elegidas **/
const Answer = (props) => {
return (
<div className="col-5">
{props.selectedNumbers.map((number,i) =>
<span key={i} onClick={() => props.unselectNumber(number) }>{number}</span>
)}
</div>
)
}
/** Numeros disponibles **/
const Numbers = (props) => {
const numberClassName = (number) => {
if(props.selectedNumbers.indexOf(number) >= 0){
return 'selected';
}
if(props.setOfUsedNumbers.indexOf(number) >= 0){
return 'used';
}
}
console.log("props", props);
return (
<div className="card text-center">
<div>
{Numbers.list.map((number, i) =>
<span key={i} className={numberClassName(number)}
onClick={() => props.onSelectNumber(number)}>{number}</span>
)}
</div>
</div>
)
}
Numbers.list = _.range(1,10);
const Done = (props) => {
return (
<div className="text-center">
<h2>{props.doneStatus}</h2>
<br />
<button onClick={props.onPlayAgain}>Jugar de Nuevo</button>
</div>
);
}
/** Componente de Juego **/
class Game extends React.Component {
static initialState = () => ({
selectedNumbers: [],
randomNumberOfStars: 1 + Math.floor(Math.random()*9),
answerIsCorrect: null,
usedNumbers: [],
redraws: 5,
doneStatus: null
});
state = Game.initialState();
resetGame = () => this.setState(Game.initialState());
selectNumber = (numberClicked) => {
console.log('numero elegido', numberClicked);
if(this.state.selectedNumbers.indexOf(numberClicked) >= 0){ return; };
this.setState(prevState => ({answerIsCorrect: null, selectedNumbers: prevState.selectedNumbers.concat(numberClicked)
})
);
};
deselectNumber = (numberClicked) => {
console.log('numero aq uitar', numberClicked);
this.setState(prevState => { return {answerIsCorrect: null, selectedNumbers: prevState.selectedNumbers.filter(number => number !== numberClicked)}
});
};
verifyAnswer = () => {
this.setState(prevState => ({
answerIsCorrect: prevState.randomNumberOfStars === prevState.selectedNumbers.reduce((acc, n) => acc + n, 0)
}))
};
acceptAnswer = () => {
this.setState(prevState => ({
selectedNumbers: [],
randomNumberOfStars: 1 + Math.floor(Math.random()*9),
answerIsCorrect: null,
usedNumbers: prevState.usedNumbers.concat(prevState.selectedNumbers)
}), this.updateDoneStatus);
};
redraw = () => {
if(this.state.redraws <= 0) { return; }
this.setState(prevState => ({
selectedNumbers: [],
randomNumberOfStars: 1 + Math.floor(Math.random()*9),
answerIsCorrect: null,
redraws: prevState.redraws - 1
}), this.updateDoneStatus);
};
possibleSolution = ({randomNumberOfStars, usedNumbers}) => {
const possibleNumbers = _.range(1,10).filter(number =>
usedNumbers.indexOf(number) === -1
);
return possibleCombinationSum(possibleNumbers, randomNumberOfStars);
};
updateDoneStatus = () => {
this.setState(prevState => {
if(prevState.usedNumbers.length === 9) {
return { doneStatus: 'Has ganado. Tio!'}
}
if(prevState.redraws <= 0 && !this.possibleSolution(prevState)){
return { doneStatus: 'Game Over!!!'}
}
});
};
render() {
const { selectedNumbers,
randomNumberOfStars,
answerIsCorrect,
usedNumbers,
redraws,
doneStatus } = this.state;
return (
<div className="container">
<h3>Play Nine</h3>
<hr />
<div className="row">
<Stars numberOfStars={randomNumberOfStars} />
<Button selectedNumbers={selectedNumbers}
doVerifyAnswer={this.verifyAnswer}
doAnswerIsCorrect={answerIsCorrect}
answerIsAccepted={this.acceptAnswer}
doRedraw={this.redraw}
redrawsAvailable={redraws}/>
<Answer selectedNumbers={selectedNumbers}
unselectNumber={this.deselectNumber} />
</div>
<br />
{doneStatus ?
<Done doneStatus={doneStatus} onPlayAgain={this.resetGame}/> :
<Numbers selectedNumbers={selectedNumbers}
onSelectNumber={this.selectNumber}
setOfUsedNumbers={usedNumbers} />
}
</div>
)
}
}
/** Componente Principal **/
class App extends React.Component {
render() {
return (
<div>
<Game />
</div>
)
}
}
ReactDOM.render(<App />, mountNode);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment