Improve looks of research menu
After Width: | Height: | Size: 33 KiB |
After Width: | Height: | Size: 25 KiB |
After Width: | Height: | Size: 37 KiB |
After Width: | Height: | Size: 28 KiB |
After Width: | Height: | Size: 29 KiB |
After Width: | Height: | Size: 34 KiB |
After Width: | Height: | Size: 32 KiB |
After Width: | Height: | Size: 37 KiB |
|
@ -40,6 +40,11 @@ export const Buildings = async() => {
|
||||||
return db.collection('buildings');
|
return db.collection('buildings');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export const Research = async() => {
|
||||||
|
const db = await getDB();
|
||||||
|
return db.collection('research');
|
||||||
|
}
|
||||||
|
|
||||||
export const Lang = async (language = "en") => {
|
export const Lang = async (language = "en") => {
|
||||||
const db = await getDB(`${config.MONGODB_DB}_${language}`);
|
const db = await getDB(`${config.MONGODB_DB}_${language}`);
|
||||||
return [
|
return [
|
||||||
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
import DBResearch from '../../types/DBResearch';
|
||||||
|
import { Research } from '../db/mongodb';
|
||||||
|
|
||||||
|
export const getAllResearch = async () => {
|
||||||
|
return (await Research()).find({}).toArray() as unknown as Array<DBResearch>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const getResearchById = async (id: string) => {
|
||||||
|
return (await Research()).findOne({
|
||||||
|
id
|
||||||
|
}) as unknown as DBResearch;
|
||||||
|
}
|
|
@ -1,15 +1,15 @@
|
||||||
---
|
---
|
||||||
import { Icon } from 'astro-icon/components'
|
|
||||||
|
|
||||||
import Layout from '../../layouts/Layout.astro';
|
import Layout from '../../layouts/Layout.astro';
|
||||||
import NavBar from '../../components/NavBar.astro';
|
import NavBar from '../../components/NavBar.astro';
|
||||||
import { getUserByAccessToken } from '../../lib/db/users';
|
import { getUserByAccessToken } from '../../lib/db/users';
|
||||||
import { getHighestWeightedLanguage, getLocales, getName, getObj } from '../../lib/utils/langDriver';
|
import { getHighestWeightedLanguage, getLocales, getName, getObj } from '../../lib/utils/langDriver';
|
||||||
import ResourceBar from '../../components/ResourceBar.astro';
|
import ResourceBar from '../../components/ResourceBar.astro';
|
||||||
|
import ItemCard from '../../components/ItemCard.astro';
|
||||||
|
import DBResearch from '../../types/DBResearch';
|
||||||
|
import { getAllResearch } from '../../lib/db/research';
|
||||||
|
|
||||||
type ResearchDetail = { id: string, level: number, requiredResearch: { id: string, level: number}[], cost: { [key: string]: number } };
|
// const researchList = (await import('../../lib/data/research.json')).default;
|
||||||
|
const researchList = await getAllResearch();
|
||||||
const researchList = (await import('../../lib/data/research.json')).default;
|
|
||||||
|
|
||||||
const loggedToken = Astro.cookies.get('sessionToken')?.value ?? null;
|
const loggedToken = Astro.cookies.get('sessionToken')?.value ?? null;
|
||||||
const username = Astro.cookies.get('username')?.value ?? "";
|
const username = Astro.cookies.get('username')?.value ?? "";
|
||||||
|
@ -22,57 +22,57 @@ const locale = await getHighestWeightedLanguage(Astro.request.headers.get('accep
|
||||||
|
|
||||||
const lang = await getLocales(locale);
|
const lang = await getLocales(locale);
|
||||||
|
|
||||||
const researchDetails: ResearchDetail[] = []; //TODO: Add union type for cost keys
|
// type DBResearchDetails = DBResearch & { level: number };
|
||||||
researchList.forEach(element => {
|
// const researchDetails: DBResearchDetails[] = [];
|
||||||
const userLevel = checkUser.research.find(x => x.id === element.id)?.level ?? 0;
|
// researchList.forEach(element => {
|
||||||
const tempResDetails: ResearchDetail = {
|
// const userLevel = checkUser.research.find(x => x.id === element.id)?.level ?? 0;
|
||||||
id: element.id,
|
// const tempResDetails: DBResearchDetails = {
|
||||||
level: userLevel,
|
// level: userLevel,
|
||||||
requiredResearch: element.requirements.research,
|
// ...element
|
||||||
cost: {}
|
// }
|
||||||
}
|
|
||||||
|
|
||||||
Object.entries(element.requirements.resources).forEach(([key, value]) => {
|
// researchDetails.push(tempResDetails);
|
||||||
tempResDetails.cost[key] = value * Math.pow(element.multiplier, userLevel);
|
// });
|
||||||
});
|
|
||||||
researchDetails.push(tempResDetails);
|
|
||||||
});
|
const modalSet: { [key: string]: { resources: Array<any>, research: Array<any>, buildings: Array<any> } } = {};
|
||||||
|
|
||||||
|
for(const research of researchList) {
|
||||||
|
modalSet[research.id] = {
|
||||||
|
resources: research.requirements.resources,
|
||||||
|
research: research.requirements.research,
|
||||||
|
buildings: research.requirements.buildings,
|
||||||
|
// energy: building.energy
|
||||||
|
};
|
||||||
|
}
|
||||||
---
|
---
|
||||||
|
|
||||||
<Layout title="Research">
|
<Layout title="Research">
|
||||||
<NavBar loggedIn="true" active="research" />
|
<NavBar loggedIn="true" active="research" />
|
||||||
<ResourceBar />
|
<ResourceBar />
|
||||||
|
|
||||||
{researchDetails.map(research => (
|
<div id="research-modal-background">
|
||||||
<div class="research-card">
|
<div id="research-modal-details" data-building-id="">
|
||||||
<h2>{getObj(lang, "research", research.id).name}</h2>
|
<h3>Required resources</h3>
|
||||||
<div class="research-card-wrapper">
|
<div class="research-modal-text" id="research-modal-req-resources">None</div>
|
||||||
<div class="research-image"></div>
|
<h3>Required buildings</h3>
|
||||||
{getObj(lang, "research", research.id).description}<br />
|
<div class="research-modal-text" id="research-modal-req-buildings">None</div>
|
||||||
|
<h3>Required research</h3>
|
||||||
<a id={`research_${research.id}`} href="#" class="a-button">{getName(lang, "general", "nav-research")}</a>
|
<div class="research-modal-text" id="research-modal-req-research">None</div>
|
||||||
<div class="research-req-icon">
|
|
||||||
<Icon class="research-req-icon-proper" name="mdi:help" />
|
|
||||||
<div class="research-req-tooltip">
|
|
||||||
<div>{getName(lang, "general", "required")}:</div>
|
|
||||||
{research.requiredResearch.length !== 0 ? research.requiredResearch.map(req => (
|
|
||||||
<div>
|
|
||||||
{getObj(lang, "research", req.id).name} - {req.level}
|
|
||||||
</div>
|
|
||||||
)) : getName(lang, "general", "none")}
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
Level: {research.level}
|
|
||||||
</div>
|
|
||||||
<div class="research-cost-wrapper">
|
|
||||||
{Object.entries(research.cost).map(([key, value]) => <div>
|
|
||||||
{getName(lang, "resources", key)}: {value} ||
|
|
||||||
</div>)}
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
))}
|
</div>
|
||||||
|
|
||||||
|
<div class="research-cards">
|
||||||
|
{researchList.map(research => <>
|
||||||
|
<ItemCard
|
||||||
|
id={research.id}
|
||||||
|
name={getObj(lang, "research", research.id).name}
|
||||||
|
description={getObj(lang, "research", research.id).description ?? ""}
|
||||||
|
image={`/images/research/${research.id}.jpeg`}
|
||||||
|
button_type="general"
|
||||||
|
button_name="nav-research" />
|
||||||
|
</>)}
|
||||||
|
</div>
|
||||||
</Layout>
|
</Layout>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
@ -154,53 +154,90 @@ researchList.forEach(element => {
|
||||||
color: lime;
|
color: lime;
|
||||||
}
|
}
|
||||||
|
|
||||||
.research-card {
|
.research-cards {
|
||||||
background: rgba(0, 0, 0, 0.5);
|
|
||||||
padding: 1rem;
|
|
||||||
margin: 1rem;
|
|
||||||
border-radius: 8px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.research-card-wrapper {
|
|
||||||
display: flex;
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
row-gap: 40px;
|
||||||
|
column-gap: 2%;
|
||||||
|
margin-top: 40px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.research-image {
|
#research-modal-background {
|
||||||
background-color: pink;
|
display: none;
|
||||||
border-radius: 20px;
|
position: fixed;
|
||||||
width: 10em;
|
top: 0;
|
||||||
height: 10em;
|
left: 0;
|
||||||
}
|
|
||||||
|
|
||||||
.research-cost-wrapper {
|
|
||||||
display: flex;
|
|
||||||
}
|
|
||||||
|
|
||||||
.research-req-icon {
|
|
||||||
background-color: gray;
|
|
||||||
width: 2em;
|
|
||||||
height: 2em;
|
|
||||||
font-size: 1em;
|
|
||||||
}
|
|
||||||
|
|
||||||
.research-req-icon-proper {
|
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
|
background: rgba(0, 0, 0, 0.5);
|
||||||
|
z-index: 100;
|
||||||
}
|
}
|
||||||
|
|
||||||
.research-req-icon .research-req-tooltip {
|
#research-modal-details {
|
||||||
position: absolute;
|
display: none;
|
||||||
background-color: grey;
|
position: fixed;
|
||||||
border-radius: 5px;
|
top: 50%;
|
||||||
transition: opacity 1s;
|
left: 50%;
|
||||||
opacity: 0;
|
transform: translate(-50%, -50%);
|
||||||
}
|
width: 80%;
|
||||||
|
max-width: 800px;
|
||||||
.research-req-icon:hover .research-req-tooltip {
|
background: rgba(0, 0, 0, 0.9);
|
||||||
opacity: 1;
|
border-radius: 8px;
|
||||||
|
padding: 1rem;
|
||||||
|
z-index: 101;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
<script>
|
<script define:vars={{ modalSet, lang }}>
|
||||||
|
const modalResources = document.getElementById("research-modal-req-resources");
|
||||||
|
const modalBuildings = document.getElementById("research-modal-req-buildings");
|
||||||
|
const modalResearch = document.getElementById("research-modal-req-research");
|
||||||
|
|
||||||
|
document.querySelectorAll('.item-card-info-button').forEach((el) => {
|
||||||
|
el.addEventListener('click', () => {
|
||||||
|
// modal
|
||||||
|
const modalDiv = document.getElementById('research-modal-details');
|
||||||
|
if(!modalDiv) return;
|
||||||
|
modalDiv.style.display = 'block';
|
||||||
|
|
||||||
|
console.log(modalSet)
|
||||||
|
|
||||||
|
const reqResources = modalSet[el.parentElement.parentElement.dataset.id]?.resources ?? [];
|
||||||
|
const reqBuildings = modalSet[el.parentElement.parentElement.dataset.id]?.buildings ?? [];
|
||||||
|
const reqResearch = modalSet[el.parentElement.parentElement.dataset.id]?.research ?? [];
|
||||||
|
|
||||||
|
modalResources.innerHTML = reqResources.length === 0 ? "None" : reqResources.map(resource => {
|
||||||
|
return `${lang['resources'].find(r => r.id === resource.id).name}: ${resource.amount}`;
|
||||||
|
}).join("<br />");
|
||||||
|
|
||||||
|
modalBuildings.innerHTML = reqBuildings.length === 0 ? "None" : reqBuildings.map(building => {
|
||||||
|
return `${lang['buildings'].find(b => b.id === building.id).name}: ${building.level}`;
|
||||||
|
}).join("<br />");
|
||||||
|
|
||||||
|
modalResearch.innerHTML = reqResearch.length === 0 ? "None" : reqResearch.map(research => {
|
||||||
|
return `${lang['research'].find(r => r.id === research.id).name}: ${research.level}`;
|
||||||
|
}).join("<br />");
|
||||||
|
|
||||||
|
// background
|
||||||
|
const backgroundDiv = document.getElementById('research-modal-background');
|
||||||
|
if(!backgroundDiv) return;
|
||||||
|
backgroundDiv.style.display = 'block';
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// close modal on background click
|
||||||
|
const bg = document.getElementById('research-modal-background');
|
||||||
|
|
||||||
|
bg?.addEventListener('click', () => {
|
||||||
|
const modalDiv = document.getElementById('research-modal-details');
|
||||||
|
if(!modalDiv) return;
|
||||||
|
modalDiv.style.display = 'none';
|
||||||
|
|
||||||
|
const backgroundDiv = document.getElementById('research-modal-background');
|
||||||
|
if(!backgroundDiv) return;
|
||||||
|
backgroundDiv.style.display = 'none';
|
||||||
|
});
|
||||||
|
|
||||||
const allButtons = document.getElementsByClassName("a-button");
|
const allButtons = document.getElementsByClassName("a-button");
|
||||||
|
|
||||||
for(const researchButton of allButtons) {
|
for(const researchButton of allButtons) {
|
||||||
|
|
|
@ -0,0 +1,10 @@
|
||||||
|
export default interface DBResearch {
|
||||||
|
id: string,
|
||||||
|
requirements: {
|
||||||
|
buildings: Array<{ id: string, level: number }>,
|
||||||
|
research: Array<{ id: string, level: number }>,
|
||||||
|
resources: Array<{ name: string, amount: number }>,
|
||||||
|
},
|
||||||
|
time: number,
|
||||||
|
multiplier: number,
|
||||||
|
}
|