173 lines
4.8 KiB
JavaScript
173 lines
4.8 KiB
JavaScript
import React from 'react'
|
|
import axios from 'axios'
|
|
import { Control, Form } from 'react-redux-form';
|
|
import fuzzy from 'fuzzy';
|
|
|
|
function MoviePosters(props) {
|
|
let movies = props.movies.slice();
|
|
|
|
// Filter the movies
|
|
if (props.filter !== "") {
|
|
const filtered = fuzzy.filter(props.filter, movies, {
|
|
extract: (el) => el.title
|
|
});
|
|
movies = filtered.map((el) => el.original);
|
|
}
|
|
|
|
// Limit the number of results
|
|
if (movies.length > props.perPage) {
|
|
movies = movies.slice(0, props.perPage);
|
|
}
|
|
|
|
return (
|
|
<div className="col-xs-5 col-md-8">
|
|
<MovieListFilter />
|
|
<div className="row">
|
|
{movies.map(function(movie, index) {
|
|
const selected = (movie.imdb_id === props.selectedMovieId) ? true : false;
|
|
return (
|
|
<MoviePoster
|
|
data={movie}
|
|
key={movie.imdb_id}
|
|
selected={selected}
|
|
onClick={() => props.onClick(movie.imdb_id)}
|
|
/>
|
|
)}
|
|
)}
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
class MovieListFilter extends React.Component {
|
|
render() {
|
|
return (
|
|
<div className="col-xs-12 col-md-12 movie-list-filter">
|
|
<div className="row">
|
|
<Form model="movieStore" className="input-group" >
|
|
<Control.text
|
|
model="movieStore.filter"
|
|
className="form-control input-sm"
|
|
placeholder="Filter movies..."
|
|
updateOn="change"
|
|
/>
|
|
<span className="input-group-btn">
|
|
<button className="btn btn-default btn-sm" type="button">Filter</button>
|
|
</span>
|
|
</Form>
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|
|
}
|
|
|
|
function MoviePoster(props) {
|
|
const selected = props.selected ? ' thumbnail-selected' : '';
|
|
const imgClass = 'thumbnail' + selected;
|
|
return (
|
|
<div className="col-xs-12 col-sm-6 col-md-3 col-lg-2">
|
|
<a className={imgClass}>
|
|
<img
|
|
src={props.data.poster_url}
|
|
onClick={props.onClick}
|
|
/>
|
|
</a>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
function MovieDetails(props) {
|
|
return (
|
|
<div className="col-xs-7 col-md-4">
|
|
<div className="movie-detail affix">
|
|
<h1 className="hidden-xs">{props.movie.title}</h1>
|
|
<h3 className="visible-xs">{props.movie.title}</h3>
|
|
<p>
|
|
<i className="fa fa-clock-o"></i>
|
|
{props.movie.runtime} min
|
|
</p>
|
|
<p>
|
|
<i className="fa fa-star-o"></i>
|
|
{props.movie.rating} <small>({props.movie.votes} counts)</small>
|
|
</p>
|
|
<p className="movie-plot">{props.movie.plot}</p>
|
|
</div>
|
|
<MovieButtons {...props} />
|
|
</div>
|
|
);
|
|
}
|
|
|
|
class MovieButtons extends React.Component {
|
|
constructor(props) {
|
|
super(props);
|
|
this.handleClick = this.handleClick.bind(this);
|
|
}
|
|
handleClick(e) {
|
|
e.preventDefault();
|
|
if (this.props.fetching) {
|
|
return
|
|
}
|
|
this.props.getMovieDetails(this.props.movie.imdb_id);
|
|
}
|
|
render() {
|
|
const imdb_link = `http://www.imdb.com/title/${this.props.movie.imdb_id}`;
|
|
return (
|
|
<div className="movie-details-buttons btn-toolbar">
|
|
<a type="button" className="btn btn-default btn-sm" onClick={this.handleClick}>
|
|
{this.props.fetching ||
|
|
<span>
|
|
<i className="fa fa-refresh"></i> Refresh
|
|
</span>
|
|
}
|
|
{this.props.fetching &&
|
|
<span>
|
|
<i className="fa fa-spin fa-refresh"></i> Refreshing
|
|
</span>
|
|
}
|
|
</a>
|
|
{this.props.movie.polochon_url !== "" &&
|
|
<a type="button" className="btn btn-primary btn-sm" href={this.props.movie.polochon_url}>
|
|
<i className="fa fa-download"></i> Download
|
|
</a>
|
|
}
|
|
<a type="button" className="btn btn-warning btn-sm" href={imdb_link}>
|
|
<i className="fa fa-external-link"></i> IMDB
|
|
</a>
|
|
</div>
|
|
);
|
|
}
|
|
}
|
|
|
|
export default class MovieList extends React.Component {
|
|
componentWillMount() {
|
|
this.props.fetchMovies(this.props.moviesUrl);
|
|
}
|
|
render() {
|
|
const movies = this.props.movieStore.movies;
|
|
const selectedMovieId = this.props.movieStore.selectedImdbId;
|
|
let index = movies.map((el) => el.imdb_id).indexOf(selectedMovieId);
|
|
if (index === -1) {
|
|
index = 0;
|
|
}
|
|
const selectedMovie = movies[index];
|
|
return (
|
|
<div className="row" id="container">
|
|
<MoviePosters
|
|
movies={movies}
|
|
selectedMovieId={selectedMovieId}
|
|
filter={this.props.movieStore.filter}
|
|
perPage={this.props.movieStore.perPage}
|
|
onClick={this.props.selectMovie}
|
|
/>
|
|
{selectedMovie &&
|
|
<MovieDetails
|
|
movie={selectedMovie}
|
|
fetching={this.props.movieStore.fetchingDetails}
|
|
getMovieDetails={this.props.getMovieDetails}
|
|
/>
|
|
}
|
|
</div>
|
|
);
|
|
}
|
|
}
|