Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

HW-9 async by IgorFromUA #403

Merged
merged 1 commit into from
Dec 7, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 35 additions & 18 deletions homeworks/ihor.zapisochniy_IgorFromUA/GamesProject/games.html
Original file line number Diff line number Diff line change
Expand Up @@ -40,30 +40,44 @@
<main>
<form action="" class="filter">
<label for="filter__select">
<select id="filter__select" name="genre" data-filter-select class="filter__select">
<select id="filter__select" name="genre" data-filter-select="genre" class="filter__select">
<option class="select__option" selected value="genre">Genre</option>
<option class="select__option" value="sport">Sport</option>
<option class="select__option" value="strategy">Strategy</option>
<option class="select__option" value="shooter">Shooter</option>
<option class="select__option" value="racing">Racing</option>
<option class="select__option" value="horror">Horror</option>
<option class="select__option" value="arpg">ARPG</option>
<option class="select__option" value="fighting">Fighting</option>
<option class="select__option" value="mmorpg">MMORPG</option>
<option class="select__option" value="card">Card Game</option>
<option class="select__option" value="action-rpg">Action RPG</option>
<option class="select__option" value="open-world">Open-world</option>
<option class="select__option" value="sports">sports</option>
<option class="select__option" value="racing">racing</option>
<option class="select__option" value="social">social</option>
<option class="select__option" value="superhero">superhero</option>
<option class="select__option" value="horror">horror</option>
<option class="select__option" value="military">military</option>
<option class="select__option" value="action">action</option>
<option class="select__option" value="space">space</option>
<option class="select__option" value="tank">tank</option>
<option class="select__option" value="sailing">sailing</option>
<option class="select__option" value="3d">sports</option>
<option class="select__option" value="2d">sports</option>
</select>
</label>
<input type="radio" name="type-games" data-type-games="platform" class="radio-input" id="type-games-1">
<label for="type-games-1" class="radio-text">
Platform
</label>

<input type="radio" name="type-games" data-type-games="online" class="radio-input" id="type-games-2">
<label for="type-games-2" class="radio-text">
Online games
<label for="filter__platform">
<select name="platform" id="filter__platform" data-filter-select="platform" class="filter__select">
<option class="select__option" selected value="all">Platform</option>
<option class="select__option" value="pc">PC</option>
<option class="select__option" value="browser">Browser</option>
</select>
</label>
<label for="age-1" class="checkbox-text">
<input type="checkbox" data-age-games="new" class="checkbox-input" name="age" id="age-1">
New
<input type="radio" data-age-games="new" class="radio-input" name="age" id="age-1">
<label for="age-1" class="radio-text ">
New first
</label>
<label for="age-2" class="checkbox-text">
<input type="checkbox" data-age-games="old" class="checkbox-input" name="age" id="age-2">
Old
<input type="radio" data-age-games="old" class="radio-input" name="age" id="age-2">
<label for="age-2" class="radio-text">
Old first
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm curious to know why you changed filters.
This is the screen from the mockup:
Screenshot 2023-12-06 at 04 47 17

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

#396
here in the description:
Знімок екрана з 2023-12-06 08-35-52

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I got it! Thank you, @IgorFromUA , for pointing it out

</label>
<div>
<label for="filter__search">
Expand All @@ -74,6 +88,9 @@
</form>
<h1 class="title">Study project "Games"</h1>
<ul class="cards" data-cards></ul>
<div class="loading">
<div class="loading__spin" data-loading></div>
</div>
</main>
</div>
<script src="./scripts/games.js"></script>
Expand Down
243 changes: 74 additions & 169 deletions homeworks/ihor.zapisochniy_IgorFromUA/GamesProject/scripts/games.js
Original file line number Diff line number Diff line change
@@ -1,142 +1,7 @@
const mocGames = [
{
id: 1136,
title: 'Overwatch 2',
thumbnail: 'https://www.mmobomb.com/g/1136/thumbnail.jpg',
short_description: 'Big changes come to the Overwatch formula in this sequel...and so does PvE content, eventually.',
game_url: 'https://www.mmobomb.com/open/overwatch-2',
genre: 'Shooter',
platform: 'PC (Windows)',
publisher: 'Activision Blizzard King',
developer: 'Blizzard Entertainment',
release_date: '2022-10-04',
profile_url: 'https://www.mmobomb.com/overwatch-2',
},
{
id: 523,
title: 'Lost Ark',
thumbnail: 'https://www.mmobomb.com/g/523/thumbnail.jpg',
short_description: 'Journey throughout the realm of Arkesia and do battle against a demon invasion in Smilegate\'s free-to-play ARPG Lost Ark!',
game_url: 'https://www.mmobomb.com/open/lost-ark',
genre: 'ARPG',
platform: 'PC (Windows)',
publisher: 'Amazon Games',
developer: 'Smilegate',
release_date: '2022-02-11',
profile_url: 'https://www.mmobomb.com/lost-ark',
},
{
id: 1113,
title: 'PUBG: BATTLEGROUNDS',
thumbnail: 'https://www.mmobomb.com/g/1113/thumbnail.jpg',
short_description: 'Battle the odds in a 100v1 death match in PUBG: Battlegrounds, the classic free-to-play battle royale experience.',
game_url: 'https://www.mmobomb.com/open/pubg',
genre: 'Shooter',
platform: 'PC (Windows)',
publisher: 'KRAFTON, Inc.',
developer: 'KRAFTON, Inc.',
release_date: '2022-01-12',
profile_url: 'https://www.mmobomb.com/pubg',
},
{
id: 508,
title: 'Enlisted',
thumbnail: 'https://www.mmobomb.com/g/508/thumbnail.jpg',
short_description: 'Step into the most famous battles of World War II in Enlisted, a free-to-play shooter from the makers of War Thunder. Experience squad-based combat from the ground level, as you command your troops, outfitted with era-authentic weapons and gear, in massive battles with over a hundred soldiers apiece.',
game_url: 'https://www.mmobomb.com/open/enlisted',
genre: 'Shooter',
platform: 'PC (Windows)',
publisher: 'Gaijin Entertainment',
developer: 'Darkflow Software',
release_date: '2021-04-08',
profile_url: 'https://www.mmobomb.com/enlisted',
},
{
id: 1120,
title: 'Fall Guys',
thumbnail: 'https://www.mmobomb.com/g/1120/thumbnail.jpg',
short_description: 'Fall Guys is a free-to-play massively multiplayer party royale game.',
game_url: 'https://www.mmobomb.com/open/fall-guys',
genre: 'Battle Royale',
platform: 'PC (Windows)',
publisher: 'Mediatonic',
developer: 'Mediatonic',
release_date: '2020-08-04',
profile_url: 'https://www.mmobomb.com/fall-guys',
},
{
id: 340,
title: 'Game Of Thrones Winter Is Coming',
thumbnail: 'https://www.mmobomb.com/g/340/thumbnail.jpg',
short_description: 'Fame and glory await you in Westeros, in Game of Thrones: Winter Is Coming, the officially licensed free-to-play browser game based on the epic fantasy series by George R.R. Martin.',
game_url: 'https://www.mmobomb.com/open/game-of-thrones-winter-is-coming',
genre: 'Strategy',
platform: 'Web Browser',
publisher: 'GTArcade',
developer: 'YOOZOO Games ',
release_date: '2019-11-14',
profile_url: 'https://www.mmobomb.com/game-of-thrones-winter-is-coming',
},
{
id: 427,
title: 'Drakensang Online',
thumbnail: 'https://www.mmobomb.com/g/427/thumbnail.jpg',
short_description: 'Drakensang Online is a free to play 3D action RPG game that features extraordinary 3D graphics and effects and heralds the next generation of free-to-play online browser games. With the ability to customize your character, skills and magic powers like never before, join your comrades to wage a brutal war against evil.',
game_url: 'https://www.mmobomb.com/open/drakensang-online',
genre: 'MMORPG',
platform: 'Web Browser',
publisher: 'Bigpoint',
developer: 'Bigpoint',
release_date: '2011-08-08',
profile_url: 'https://www.mmobomb.com/drakensang-online',
},
{
id: 380,
title: 'Dark Orbit Reloaded',
thumbnail: 'https://www.mmobomb.com/g/380/thumbnail.jpg',
short_description: 'Take part in huge intergalactic battles and take on the whole galaxy in DarkOrbit, the free-to-play browser-based space combat MMO from Bigpoint -- now in 3-D! Choose your faction and your ship, each with their own strengths, and take off into adventure!',
game_url: 'https://www.mmobomb.com/open/darkorbit',
genre: 'Shooter',
platform: 'Web Browser',
publisher: 'Bigpoint',
developer: 'Bigpoint',
release_date: '2006-12-11',
profile_url: 'https://www.mmobomb.com/darkorbit',
},
{
id: 1122,
title: 'MultiVersus',
thumbnail: 'https://www.mmobomb.com/g/1122/thumbnail.jpg',
short_description: 'Match up in 1v1, 2v2 co-op, or 4-person free-for-all modes in this free-to-play Smash-Style Brawler!',
game_url: 'https://www.mmobomb.com/open/multiversus',
genre: 'Fighting',
platform: 'PC (Windows)',
publisher: 'Warner Bros. Games',
developer: 'Player First Games',
release_date: '2022-07-19',
profile_url: 'https://www.mmobomb.com/multiversus',
},
{
id: 5,
title: 'Crossout',
thumbnail: 'https://www.mmobomb.com/g/5/thumbnail.jpg',
short_description: 'Trick out your ride and take to the post-apocalyptic roads for battle in Crossout, the free-to-play vehicular combat game from Gaijin Entertainment! Featuring a vehicle design system with endless customization and fast-paced, armor-crunching combat, Crossout offers high-octane excitement in brief and explosive matches.',
game_url: 'https://www.mmobomb.com/open/crossout',
genre: 'Shooter',
platform: 'PC (Windows)',
publisher: 'Targem',
developer: 'Gaijin',
release_date: '2017-05-30',
profile_url: 'https://www.mmobomb.com/crossout',
},
];
const games = mocGames.map((game) => {
const copyGame = { ...game };
copyGame.small_description = `${game.short_description.slice(0, 60)}...`;
return copyGame;
});
const CARDS_LIST = document.querySelector('[data-cards]');
const FORM_BUTTON = document.querySelector('[data-filter-button]');
const LOADING_ELEMENT = document.querySelector('[data-loading]');
const urlGames = 'https://mmo-games.p.rapidapi.com/games';

function createGameCardStr(game) {
const {
Expand Down Expand Up @@ -183,27 +48,9 @@ function createCardElement(game) {
}

function filterGames(gamesArr) {
const selectedGenre = document.querySelector('[data-filter-select]').value;
const isPlatformGame = document.querySelector('[data-type-games="platform"]').checked;
const isOnlineGame = document.querySelector('[data-type-games="online"]').checked;
const isNewGame = document.querySelector('[data-age-games="new"]').checked;
const isOldGame = document.querySelector('[data-age-games="old"]').checked;
const searchTerm = document.querySelector('[data-filter-search]').value;
return gamesArr.filter((game) => {
const {
genre,
platform,
release_date: releaseDate,
title,
short_description: description,
} = game;
const releaseYear = new Date(releaseDate).getFullYear();
if (selectedGenre !== 'genre' && selectedGenre !== genre.toLowerCase()) return false;
if (isPlatformGame && platform !== 'PC (Windows)') return false;
if (isOnlineGame && platform !== 'Web Browser') return false;
if (isNewGame && !isOldGame && releaseYear < 2020) return false;
if (isOldGame && !isNewGame && releaseYear > 2010) return false;
if (isOldGame && isNewGame && releaseYear < 2020 && releaseYear > 2010) return false;
const { title, short_description: description } = game;
return !(searchTerm !== '' && !title.toLowerCase().includes(searchTerm.toLowerCase())
&& !description.toLowerCase().includes(searchTerm.toLowerCase()));
});
Expand All @@ -215,6 +62,14 @@ function markedSearchText(search, originString) {
return originString.replaceAll(regex, (match) => `<span class="filter-matched-text">${match}</span>`);
}

function creatSearchQueryString() {
const selectedGenre = document.querySelector('[data-filter-select="genre"]').value;
const selectedPlatform = document.querySelector('[data-filter-select="platform"]').value;
const isNewGame = document.querySelector('[data-age-games="new"]').checked;
const isOldGame = document.querySelector('[data-age-games="old"]').checked;
return `${selectedGenre !== 'genre' ? `category=${selectedGenre}` : ''}&platform=${selectedPlatform}${(isNewGame || isOldGame) ? '&sort-by=release-date' : ''}`;
}

function renderCards(container, arrGames) {
container.innerHTML = '';
const fragment = new DocumentFragment();
Expand All @@ -224,21 +79,71 @@ function renderCards(container, arrGames) {
container.append(fragment);
}

function reRenderCards() {
const searchTerm = document.querySelector('[data-filter-search]').value;
const filterArrGames = filterGames(games);
const markedTextFilterArrGames = filterArrGames.map((game) => {
const copyGame = { ...game };
copyGame.title = markedSearchText(searchTerm, game.title);
copyGame.small_description = markedSearchText(searchTerm, game.small_description);
return copyGame;
});
renderCards(CARDS_LIST, markedTextFilterArrGames);
function loadingSwitch(switching) {
if (switching) CARDS_LIST.innerHTML = '';
LOADING_ELEMENT.style.visibility = switching ? 'visible' : 'hidden';
}

function getGames(url = urlGames) {
loadingSwitch(true);
const optionsGamesUr = {
method: 'GET',
headers: {
'X-RapidAPI-Key': '1c3169c707mshb51bff34cbc9ff6p1749b9jsn648a19134256',
'X-RapidAPI-Host': 'mmo-games.p.rapidapi.com',
},
};
return fetch(url, optionsGamesUr)
.then((response) => {
if (response.status < 200 || response.status >= 300) {
throw new Error(response.status);
} else {
return response.json();
}
})
.then((result) => result.slice(0, 50))
.then((result) => result.map((game) => {
const copyGame = { ...game };
copyGame.small_description = `${game.short_description.slice(0, 52)}...`;
return copyGame;
}))
.catch((error) => {
CARDS_LIST.innerHTML = `<span class="error-message">Щось пішло не так! помилка: ${error.message}</span>`;
console.log('get error', error);
})
.finally(() => loadingSwitch(false));
}

async function applyFilter() {
try {
const urlGamesQuery = `${urlGames}?${creatSearchQueryString()}`;
const isOldGame = document.querySelector('[data-age-games="old"]').checked;
const games = await getGames(urlGamesQuery);
if (isOldGame) games.reverse();
const searchTerm = document.querySelector('[data-filter-search]').value;
const filterArrGames = filterGames(games);
const markedTextFilterArrGames = filterArrGames.map((game) => {
const copyGame = { ...game };
copyGame.title = markedSearchText(searchTerm, game.title);
copyGame.small_description = markedSearchText(searchTerm, game.small_description);
return copyGame;
});
renderCards(CARDS_LIST, markedTextFilterArrGames);
} catch (e) {
console.log('filter error: ', e);
}
}

function init() {
renderCards(CARDS_LIST, games);
FORM_BUTTON.addEventListener('click', reRenderCards);
async function init() {
try {
const games = await getGames();
if (!Array.isArray(games)) throw new Error('is not Array');
renderCards(CARDS_LIST, games);
} catch (e) {
console.log('init error: ', e.message);
} finally {
FORM_BUTTON.addEventListener('click', applyFilter);
}
}

init();
Original file line number Diff line number Diff line change
Expand Up @@ -58,8 +58,38 @@

.card__actor {
line-height: 26px;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}

.filter-matched-text {
background: #FFD500;
}

.loading {
width: 100%;
text-align: center;
}

.error-message {
font-size: 24px;
color: #F00;
grid-column: 2/4;
text-align: center;
}

.loading__spin {
display: inline-block;
width: 50px;
height: 50px;
border: 3px solid rgba(255,213,0,.3);
border-radius: 50%;
border-top-color: #FFD500;
animation: spin 1s ease-in-out infinite;
visibility: hidden;
}

@keyframes spin {
to { transform: rotate(360deg); }
}
Loading