From: xangelo Date: Fri, 15 Nov 2024 20:22:33 +0000 (-0500) Subject: fix(inventory): clean up requirement display X-Git-Tag: v0.4.3~4 X-Git-Url: https://git.xangelo.ca/?a=commitdiff_plain;h=24b9193b3cf871081d80fffb609a449280ec117d;p=risinglegends.git fix(inventory): clean up requirement display Between requirements and boosts the items were getting a bit messy. This makes sure that the content is the boost, but the requirements are easily accessible if they matter. --- diff --git a/public/assets/css/base.css b/public/assets/css/base.css index 39e515a..92a43f9 100644 --- a/public/assets/css/base.css +++ b/public/assets/css/base.css @@ -47,6 +47,10 @@ p:last-child { display: none !important; } +.right { + float: right; +} + .flex { display: flex; justify-content: space-around; diff --git a/public/assets/css/game.css b/public/assets/css/game.css index 80edc64..f7cc76a 100644 --- a/public/assets/css/game.css +++ b/public/assets/css/game.css @@ -255,6 +255,11 @@ button.error { line-height: 110%; } +.progress-bar.vertical { + height: 100%; + width: 10px; +} + #map { width: 75%; margin: 0rem auto 1rem; diff --git a/public/assets/css/inventory.css b/public/assets/css/inventory.css index bb56a94..50d348f 100644 --- a/public/assets/css/inventory.css +++ b/public/assets/css/inventory.css @@ -96,4 +96,49 @@ p { margin: 1rem; } +} + + +.inventory-listing { + + .requirements { + display: none !important; + } + + .requirement-hover { + cursor: help; + position: relative; + font-size: 0.8rem; + font-weight: normal; + } + + .requirement-hover:hover+.requirements, + .requirements:hover { + padding: 0.5rem; + border-radius: 4px; + font-size: 0.8rem; + width: max-content; + max-width: 200px; + position: absolute; + background: #2d2d2d; + color: #fff; + display: grid !important; + top: 100%; + right: 0; + transition: opacity 0.2s; + z-index: 100; + } + +} + +.icon-durability-container { + position: relative; + display: flex; + flex-direction: row; + align-items: center; + height: 64px; +} + +.icon-durability-container .icon { + margin-right: 3px; } \ No newline at end of file diff --git a/public/assets/css/store.css b/public/assets/css/store.css index 9473b8b..9a546e4 100644 --- a/public/assets/css/store.css +++ b/public/assets/css/store.css @@ -1,4 +1,28 @@ #explore .shop-inventory-listing { margin: 2rem auto 1rem; width: 90%; +} + +.shop-inventory-listing { + + .list-item:nth-child(even) .requirements { + background-color: #f5e6d3; + } + + .requirements { + background-color: #faf3ea; + + border-radius: 6px; + padding: 0.5rem; + margin-top: 0.5rem; + + &:before { + content: 'REQUIREMENTS'; + font-weight: bold; + display: block; + margin-bottom: 0.3rem; + color: #6d251c; + grid-column: 1 / -1; + } + } } \ No newline at end of file diff --git a/public/assets/css/tabs.css b/public/assets/css/tabs.css index 88d871f..0789a22 100644 --- a/public/assets/css/tabs.css +++ b/public/assets/css/tabs.css @@ -91,6 +91,7 @@ nav { display: flex; text-align: left; padding: 0.5rem; + overflow: hidden; &:nth-child(even) { background-color: #f2f0ec; @@ -99,6 +100,7 @@ nav { .icon-wrapper { position: relative; margin-right: 0.5rem; + width: 77px; .icon { width: 64px; @@ -112,7 +114,6 @@ nav { } .actions { - width: 64px; margin-top: 0.2rem; button { @@ -129,6 +130,7 @@ nav { padding: 0 0.4rem; line-height: 1rem; flex-grow: 2; + width: 100%; &>div { margin-bottom: 4px; @@ -144,16 +146,16 @@ nav { .stat-mods { font-size: 0.8rem; + display: grid; + grid-template-columns: repeat(auto-fill, minmax(80px, 1fr)); + gap: 0.2rem; } .requirements { font-size: 0.8rem; - - &::before { - content: 'REQ: '; - font-weight: bold; - text-transform: uppercase; - } + display: grid; + grid-template-columns: repeat(auto-fill, minmax(80px, 1fr)); + gap: 0.2rem; .requirement-title { font-weight: bold; diff --git a/src/server/views/components/progress-bar.ts b/src/server/views/components/progress-bar.ts index 9d9a290..8ec7149 100644 --- a/src/server/views/components/progress-bar.ts +++ b/src/server/views/components/progress-bar.ts @@ -3,6 +3,8 @@ export interface ProgressBarOptions { endingColor?: string; title?: string displayPercent?: boolean; + vertical?: boolean; + noContent?: boolean; } export function ProgressBar(current: number, max: number, id: string, opts: ProgressBarOptions) { @@ -19,6 +21,6 @@ export function ProgressBar(current: number, max: number, id: string, opts: Prog display.push(`${percent}%`); } - return `
${title} ${display.join(" - ")}
`; + return `
${opts.noContent ? '' : `${title} ${display.join(" - ")}`}
`; } diff --git a/src/server/views/inventory.ts b/src/server/views/inventory.ts index ca9cd47..1cd533f 100644 --- a/src/server/views/inventory.ts +++ b/src/server/views/inventory.ts @@ -1,6 +1,6 @@ -import { EquipmentSlot, meetsRequirements } from "@shared/inventory"; +import { EquipmentSlot, InventoryItem, meetsRequirements, requirementMap } from "@shared/inventory"; import { EquippedItemDetails } from "@shared/equipped"; -import { PlayerItem } from "@shared/items"; +import { Item, PlayerItem } from "@shared/items"; import { capitalize } from "lodash"; import { ProgressBar } from "./components/progress-bar"; import { Player } from "@shared/player"; @@ -73,6 +73,15 @@ function renderInventoryItems(items: PlayerItem[]): string { }).join("
"); } +function renderRequirements(requirements: InventoryItem['requirements'], player: Player): string { + return ` +
+ ${Object.entries(requirements).filter(([key, val]) => val !== 0).map(([key, val]) => { + return renderRequirement(key, val, player[key]); + }).join('')} +
+ `; +} function renderRequirement(name: string, val: number | string, currentVal?: number): string { let colorIndicator = ''; @@ -92,17 +101,26 @@ function renderStatBoost(name: string, val: number | string, percent: boolean = function renderInventoryItem(player: Player, item: EquippedItemDetails , action: (item: EquippedItemDetails) => string): string { const itemLevel = levelFromExp(item.current_exp); - const requirements = meetsRequirements(item, player); + const meetsAllRequirements = meetsRequirements(item, player); return `
-
+
+
+
+ ${ProgressBar(item.currentAp, item.maxAp, `durability-${item.item_id}`, { + startingColor: '#7be67b', + endingColor: '#7be67b', + title: 'Durability', + vertical: true, + noContent: true + })}
${action(item)}
-
${item.name} ${item.profession} (REQ)
+
${item.name} ${item.profession} (REQ)${renderRequirements(item.requirements, player)}
${item.boosts.defence ? renderStatBoost('DEF', item.boosts.defence) : ''} ${item.boosts.strength ? renderStatBoost('STR', item.boosts.strength) : ''} @@ -112,13 +130,6 @@ function renderInventoryItem(player: Player, item: EquippedItemDetails , action: ${item.boosts.damage ? renderStatBoostWithPlayerIncrease(player, item.affectedSkills.includes('restoration_magic') ? 'HP' : 'DMG', item) : ''} ${item.boosts.damage_mitigation ? renderStatBoost('MIT', item.boosts.damage_mitigation.toString(), true) : ''}
-
- ${item.requirements.level ? renderRequirement('LVL', item.requirements.level): ''} - ${item.requirements.strength ? renderRequirement('STR', item.requirements.strength): ''} - ${item.requirements.constitution ? renderRequirement('CON', item.requirements.constitution): ''} - ${item.requirements.dexterity ? renderRequirement('DEX', item.requirements.dexterity): ''} - ${item.requirements.intelligence ? renderRequirement('INT', item.requirements.intelligence): ''} -
${ProgressBar(item.current_exp - expToLevel(itemLevel), expToLevel(itemLevel + 1) - expToLevel(itemLevel), `exp-${item.item_id}`, { startingColor: '#7be67b', endingColor: '#7be67b', @@ -135,10 +146,16 @@ function renderInventorySection(player: Player, inventory: EquippedItemDetails[] return inventory.map(item => { return renderInventoryItem(player, item, item => { + + const meetsAllRequirements = meetsRequirements(item, player); if(item.is_equipped) { return ``; } else { + if(!meetsAllRequirements) { + return ``; + } + if(['ANY_HAND', 'LEFT_HAND', 'RIGHT_HAND'].includes(item.equipment_slot)) { const str: string[] = [ ``, diff --git a/src/server/views/stores.ts b/src/server/views/stores.ts index 29c9709..33413ff 100644 --- a/src/server/views/stores.ts +++ b/src/server/views/stores.ts @@ -62,14 +62,6 @@ export function renderEquipmentDetails(item: ShopEquipment, player: Player): str return `
${item.name}${item.equipment_slot === 'TWO_HANDED' ? ' (2H)': ''}
-
- ${item.requirements.level ? renderRequirement('LVL', item.requirements.level, player.level): ''} - ${item.requirements.strength ? renderRequirement('STR', item.requirements.strength, player.strength): ''} - ${item.requirements.constitution ? renderRequirement('CON', item.requirements.constitution, player.constitution): ''} - ${item.requirements.dexterity ? renderRequirement('DEX', item.requirements.dexterity, player.dexterity): ''} - ${item.requirements.intelligence ? renderRequirement('INT', item.requirements.intelligence, player.intelligence): ''} - ${renderRequirement('PRF', item.profession)} -
${item.boosts.defence ? renderStatBoost('DEF', item.boosts.defence) : ''} ${item.boosts.strength ? renderStatBoost('STR', item.boosts.strength) : ''} @@ -81,6 +73,14 @@ export function renderEquipmentDetails(item: ShopEquipment, player: Player): str ${renderStat(isSpell ? 'Uses': 'Durability', isSpell ? 'Uses': 'DUR', item.maxAp, { unsigned: true })}
${item.hasOwnProperty('id') ? `
${item.cost.toLocaleString()}G
` : ''} +
+ ${item.requirements.level ? renderRequirement('LVL', item.requirements.level, player.level): ''} + ${item.requirements.strength ? renderRequirement('STR', item.requirements.strength, player.strength): ''} + ${item.requirements.constitution ? renderRequirement('CON', item.requirements.constitution, player.constitution): ''} + ${item.requirements.dexterity ? renderRequirement('DEX', item.requirements.dexterity, player.dexterity): ''} + ${item.requirements.intelligence ? renderRequirement('INT', item.requirements.intelligence, player.intelligence): ''} + ${renderRequirement('PRF', item.profession)} +
` diff --git a/src/shared/inventory.ts b/src/shared/inventory.ts index 2cb1da4..16d5852 100644 --- a/src/shared/inventory.ts +++ b/src/shared/inventory.ts @@ -1,3 +1,4 @@ +import { Player } from "./player"; import {Profession} from "./profession"; import {SkillID} from "./skills"; import { max } from 'lodash'; @@ -116,3 +117,16 @@ export function getDurabilityApproximation(item?: InventoryItem): DurabilityAppr return "About to Break"; } } + +export function requirementMap(item: InventoryItem, player: Player): Map { + const requirements = new Map(); + Object.entries(item.requirements).forEach(([key, value]) => { + requirements.set(key, player[key] >= value); + }); + return requirements; +} + +export function meetsRequirements(item: InventoryItem, player: Player): boolean { + const requirements = requirementMap(item, player); + return Array.from(requirements.values()).every(val => val); +} \ No newline at end of file