├── README.md
├── index.html
├── index.css
└── index.js
/README.md:
--------------------------------------------------------------------------------
1 | # netflix-clone-live
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | Netflix clone
8 |
9 |
10 |
11 |
12 |
13 |
33 |
34 |
35 |
36 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
--------------------------------------------------------------------------------
/index.css:
--------------------------------------------------------------------------------
1 | /* Normalise css */
2 | html,body{
3 | background-color: #141414;
4 | padding:0;
5 | margin: 0;
6 | font-family: Helvetica,Arial ,sans-serif;
7 | }
8 | .container{
9 | width: 100%;
10 | max-width: 1250px;
11 | margin: 0 auto;
12 | }
13 | *{
14 | box-sizing: border-box;
15 | }
16 | *::-webkit-scrollbar{
17 | display: none;
18 | }
19 |
20 | /* Header Css */
21 | header{
22 | background-color: transparent;
23 | position: fixed;
24 | z-index: 100;
25 | left:0;
26 | top: 0;
27 | width: 100%;
28 | transition: all ease 600ms;
29 | }
30 | header.black-bg{
31 | background-color: rgb(20, 20, 20);
32 | }
33 | .header-cont{
34 | display: flex;
35 | flex-direction: row;
36 | justify-content: space-between;
37 | }
38 |
39 | .left-cont, .right-cont{
40 | display: flex;
41 | flex-direction: row;
42 | align-items: center;
43 | }
44 | .header-brand{
45 | max-width: 110px;
46 | }
47 | .main-nav{
48 | list-style: none;
49 | display: inline-flex;
50 | flex-direction: row;
51 | }
52 | .nav-item{
53 | margin-right: 20px;
54 | color: #e5e5e5;
55 | opacity: .83;
56 | }
57 | .nav-item.active{
58 | color: white;
59 | opacity: 1;
60 | font-weight: 500;
61 | }
62 | .right-cont svg, .right-cont img{
63 | margin-right: 22px;
64 | cursor: pointer;
65 | }
66 | .right-cont svg{
67 | color: white;
68 | }
69 | .right-cont img{
70 | max-width:40px;
71 | }
72 |
73 |
74 |
75 | /* Movies Section CSS */
76 | .movies-section{
77 | margin: 41px 0;
78 | }
79 | .movie-section-heading{
80 | font-size: 20px;
81 | font-weight: 700;
82 | line-height: 1.2;
83 | color: white;
84 | cursor: pointer;
85 | margin-bottom: 10px;
86 | }
87 | .explore-nudge{
88 | color: #54b9c5;
89 | font-size: 12px;
90 | display: none;
91 | }
92 | .movie-section-heading:hover .explore-nudge{
93 | display: inline-block;
94 | }
95 | .movies-row{
96 | display: flex;
97 | flex-direction: row;
98 | align-items: center;
99 | flex-wrap: nowrap;
100 | overflow-x:auto;
101 | overflow-y: hidden;
102 | }
103 | .movie-item{
104 | width: 245px;
105 | object-fit: contain;
106 | margin-right: 6px;
107 | border-radius: 4px;
108 | position: relative;
109 | }
110 | .move-item-img{
111 | width: inherit;
112 | }
113 | .movie-item .iframe-wrap{
114 | position: absolute;
115 | top: 0;
116 | left: 0;
117 | width: 100%;
118 | height: 100%;
119 | z-index: 10;
120 | display: none;
121 | border: none;
122 | outline: none;
123 | }
124 | .movie-item:hover .iframe-wrap{
125 | display: block;
126 | }
127 | .movie-item:hover{
128 | transform: scale(1.3);
129 | transition: transform linear 300ms;
130 | }
131 |
132 |
133 | /* Banner Section */
134 | .banner-section{
135 | background-repeat: no-repeat;
136 | background-size: cover;
137 | min-height: 98vh;
138 | padding-top: 80px;
139 | position: relative;
140 | }
141 | .banner-content{
142 | display: flex;
143 | flex-direction: column;
144 | padding-top: 70px;
145 | }
146 | .banner__title{
147 | color: white;
148 | font-size: 84px;
149 | line-height: 1.1;
150 | margin: 0;
151 | margin-bottom: 16px;
152 | max-width: 40%;
153 | }
154 | .banner__info{
155 | margin-bottom: 14px;
156 | font-size: 22px;
157 | font-weight: 700;
158 | line-height: 1.5;
159 | color: white;
160 | }
161 | .banner__overview{
162 | font-size: 16.4px;
163 | color: white;
164 | line-height: 1.3;
165 | max-width: 40%;
166 | }
167 | .action-buttons-cont{
168 | display: flex;
169 | flex-direction: row;
170 | align-items: center;
171 | }
172 | .action-button{
173 | border:none;
174 | background-color: white;
175 | padding: 8px 23px;
176 | margin-right: 11px;
177 | border-radius: 4px;
178 | display: flex;
179 | align-items: center;
180 | flex-direction: row;
181 | font-size: 16px;
182 | font-weight: 700;
183 | cursor:pointer;
184 | }
185 | .action-button:last-child{
186 | background-color: rgba(109, 109, 110, 0.7);
187 | color:white;
188 | }
189 | .banner_fadeBottom{
190 | height: 120px;
191 | background:linear-gradient(180deg,
192 | transparent,
193 | rgba(37,37,37,.61),
194 | #141414
195 | );
196 | position: absolute;
197 | left:0;
198 | bottom: 0;
199 | width: 100%;
200 | }
201 |
202 |
203 |
204 | /* RESPONSIVE CSS */
205 | @media (max-width:767px) {
206 | .main-nav{
207 | display: none;
208 | }
209 | .banner__overview, .banner__title{
210 | max-width: 100%;
211 | }
212 | }
--------------------------------------------------------------------------------
/index.js:
--------------------------------------------------------------------------------
1 | // Consts
2 | const apikey = "7543524441a260664a97044b8e2dc621";
3 | const apiEndpoint = "https://api.themoviedb.org/3"
4 | const imgPath = "https://image.tmdb.org/t/p/original";
5 |
6 |
7 | const apiPaths = {
8 | fetchAllCategories: `${apiEndpoint}/genre/movie/list?api_key=${apikey}`,
9 | fetchMoviesList: (id) => `${apiEndpoint}/discover/movie?api_key=${apikey}&with_genres=${id}`,
10 | fetchTrending:`${apiEndpoint}/trending/all/day?api_key=${apikey}&language=en-US`,
11 | searchOnYoutube: (query) => `https://www.googleapis.com/youtube/v3/search?part=snippet&q=${query}&key=AIzaSyC0SZJkHFX-fQ7NrsxdI4l4mGwYuY4l7P8`
12 | }
13 |
14 |
15 | // Boots up the app
16 | function init() {
17 | fetchTrendingMovies();
18 | fetchAndBuildAllSections();
19 | }
20 |
21 | function fetchTrendingMovies(){
22 | fetchAndbuildMovieSection(apiPaths.fetchTrending, 'Trending Now')
23 | .then(list => {
24 | const randomIndex = parseInt(Math.random() * list.length);
25 | buildBannerSection(list[randomIndex]);
26 | }).catch(err=>{
27 | console.error(err);
28 | });
29 | }
30 |
31 | function buildBannerSection(movie){
32 | const bannerCont = document.getElementById('banner-section');
33 |
34 | bannerCont.style.backgroundImage = `url('${imgPath}${movie.backdrop_path}')`;
35 |
36 | const div = document.createElement('div');
37 |
38 | div.innerHTML = `
39 | ${movie.title}
40 | Trending in movies | Released - ${movie.release_date}
41 | ${movie.overview && movie.overview.length > 200 ? movie.overview.slice(0,200).trim()+ '...':movie.overview}
42 |
46 | `;
47 | div.className = "banner-content container";
48 |
49 | bannerCont.append(div);
50 | }
51 |
52 |
53 | function fetchAndBuildAllSections(){
54 | fetch(apiPaths.fetchAllCategories)
55 | .then(res => res.json())
56 | .then(res => {
57 | const categories = res.genres;
58 | if (Array.isArray(categories) && categories.length) {
59 | categories.forEach(category => {
60 | fetchAndbuildMovieSection(
61 | apiPaths.fetchMoviesList(category.id),
62 | category.name
63 | );
64 | });
65 | }
66 | // console.table(movies);
67 | })
68 | .catch(err=>console.error(err));
69 | }
70 |
71 | function fetchAndbuildMovieSection(fetchUrl, categoryName){
72 | console.log(fetchUrl,categoryName);
73 | return fetch(fetchUrl)
74 | .then(res => res.json())
75 | .then(res => {
76 | // console.table(res.results);
77 | const movies = res.results;
78 | if (Array.isArray(movies) && movies.length) {
79 | buildMoviesSection(movies.slice(0,6), categoryName);
80 | }
81 | return movies;
82 | })
83 | .catch(err=>console.error(err))
84 | }
85 |
86 | function buildMoviesSection(list, categoryName){
87 | console.log(list, categoryName);
88 |
89 | const moviesCont = document.getElementById('movies-cont');
90 |
91 | const moviesListHTML = list.map(item => {
92 | return `
93 |
94 |

95 |
96 |
`;
97 | }).join('');
98 |
99 | const moviesSectionHTML = `
100 | ${categoryName} Explore All
101 |
102 | ${moviesListHTML}
103 |
104 | `
105 |
106 | const div = document.createElement('div');
107 | div.className = "movies-section"
108 | div.innerHTML = moviesSectionHTML;
109 |
110 | // append html into movies container
111 | moviesCont.append(div);
112 | }
113 |
114 | function searchMovieTrailer(movieName, iframId) {
115 | if (!movieName) return;
116 |
117 | fetch(apiPaths.searchOnYoutube(movieName))
118 | .then(res => res.json())
119 | .then(res => {
120 | const bestResult = res.items[0];
121 |
122 | const elements = document.getElementById(iframId);
123 | console.log(elements, iframId);
124 |
125 | const div = document.createElement('div');
126 | div.innerHTML = ``
127 |
128 | elements.append(div);
129 |
130 | })
131 | .catch(err=>console.log(err));
132 | }
133 |
134 |
135 | window.addEventListener('load',function() {
136 | init();
137 | window.addEventListener('scroll', function(){
138 | // header ui update
139 | const header = document.getElementById('header');
140 | if (window.scrollY > 5) header.classList.add('black-bg')
141 | else header.classList.remove('black-bg');
142 | })
143 | })
144 |
--------------------------------------------------------------------------------