Skip to content

Commit

Permalink
minor SRO UI updates (#2529)
Browse files Browse the repository at this point in the history
* minor character UI updates

* update name

* update

* add compact version of lightcone and relic cards

* fix CharacterGenderedKey

* fix key

* typeguard
  • Loading branch information
frzyc authored Nov 5, 2024
1 parent 92112fd commit 1e12c1a
Show file tree
Hide file tree
Showing 34 changed files with 920 additions and 184 deletions.
4 changes: 2 additions & 2 deletions apps/somnia/src/commands/databank.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import { error } from '../lib/message'
import { cwd } from '../lib/util'

import type {
CharacterDataKey,
CharacterGenderedKey,
LightConeKey,
RelicSetKey,
} from '@genshin-optimizer/sr/consts'
Expand Down Expand Up @@ -179,7 +179,7 @@ export function databankMessage(subcommand: string, id: string, arg: string) {
if (!(id in databank[subcommand])) throw `Invalid ${subcommand} name.`
//character archive
if (subcommand === 'char') {
return charBank(id as CharacterDataKey, name, data, arg)
return charBank(id as CharacterGenderedKey, name, data, arg)
}
//weapons archive
else if (subcommand === 'lightcone') {
Expand Down
17 changes: 10 additions & 7 deletions apps/somnia/src/commands/databank/char.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
import { AssetData } from '@genshin-optimizer/sr/assets-data'
import type { AbilityKey, CharacterDataKey } from '@genshin-optimizer/sr/consts'
import type {
AbilityKey,
CharacterGenderedKey,
} from '@genshin-optimizer/sr/consts'
import {
ActionRowBuilder,
EmbedBuilder,
Expand All @@ -10,7 +13,7 @@ import { hsrURL } from '../../lib/util'
import { clean, skillsList } from '../databank'

function getEmbed(
id: CharacterDataKey,
id: CharacterGenderedKey,
name: string,
data: any,
talent: string
Expand All @@ -33,11 +36,11 @@ function getEmbed(
else throw 'Invalid talent name.'
}

function getAssets(id: CharacterDataKey) {
function getAssets(id: CharacterGenderedKey) {
return AssetData.chars[id]
}

function baseEmbed(id: CharacterDataKey, name: string) {
function baseEmbed(id: CharacterGenderedKey, name: string) {
// TODO: const icon = getAssets(id).icon
// TODO: const element = allStats.char[id].damageType
const thumbnail = getAssets(id).icon
Expand All @@ -54,7 +57,7 @@ function baseEmbed(id: CharacterDataKey, name: string) {

function skillEmbed(
ability: AbilityKey,
id: CharacterDataKey,
id: CharacterGenderedKey,
name: string,
data: any
) {
Expand All @@ -73,7 +76,7 @@ function skillEmbed(
}

function eidolonsEmbed(
id: CharacterDataKey,
id: CharacterGenderedKey,
name: string,
data: any,
arg: string
Expand All @@ -99,7 +102,7 @@ function eidolonsEmbed(
}

export function charBank(
id: CharacterDataKey,
id: CharacterGenderedKey,
name: string,
data: any,
args: string
Expand Down
4 changes: 2 additions & 2 deletions libs/sr/assets-data/src/executors/gen-assets-data/executor.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { dumpFile } from '@genshin-optimizer/common/pipeline'
import type {
CharacterDataKey,
CharacterGenderedKey,
LightConeKey,
RelicCavernSetKey,
RelicCavernSlotKey,
Expand Down Expand Up @@ -61,7 +61,7 @@ type RelicIcons = RelicPlanarIcons & RelicCavernIcons
const assetData = {
// artifacts: {},
lightCones: {} as Record<LightConeKey, LightConeIcon>,
chars: {} as Record<CharacterDataKey, CharacterIcon>,
chars: {} as Record<CharacterGenderedKey, CharacterIcon>,
relics: {} as RelicIcons,
}
export type AssetData = typeof assetData
Expand Down
27 changes: 21 additions & 6 deletions libs/sr/assets/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,14 @@
import type {
LightConeKey,
NonTrailblazerCharacterKey,
RelicSetKey,
RelicSlotKey,
TrailblazerGenderedKey,
CharacterGenderedKey,
CharacterKey,
} from '@genshin-optimizer/sr/consts'
import {
isTrailblazerKey,
type LightConeKey,
type NonTrailblazerCharacterKey,
type RelicSetKey,
type RelicSlotKey,
type TrailblazerGenderedKey,
} from '@genshin-optimizer/sr/consts'
import chars from './gen/chars'
import lightCones from './gen/lightCones'
Expand All @@ -27,11 +32,21 @@ type characterAssetKey =
| 'bonusAbility3'

export function characterAsset(
ck: NonTrailblazerCharacterKey | TrailblazerGenderedKey,
ck: CharacterGenderedKey,
asset: characterAssetKey
) {
return chars[ck][asset]
}
export function characterKeyToGenderedKey(
ck: CharacterKey
): CharacterGenderedKey {
if (isTrailblazerKey(ck)) {
// TODO: implement gender
return `${ck}F` as TrailblazerGenderedKey
} else {
return ck as NonTrailblazerCharacterKey
}
}
type LightConeAssetKey = 'icon' | 'cover'
export function lightConeAsset(lck: LightConeKey, asset: LightConeAssetKey) {
return lightCones[lck][asset]
Expand Down
8 changes: 6 additions & 2 deletions libs/sr/consts/src/character.ts
Original file line number Diff line number Diff line change
Expand Up @@ -99,11 +99,11 @@ export const allCharacterKeys = [
] as const
export type CharacterKey = (typeof allCharacterKeys)[number]

export const allCharacterDataKeys = [
export const allCharacterGenderedKeys = [
...nonTrailblazerCharacterKeys,
...allTrailblazerGenderedKeys,
] as const
export type CharacterDataKey = (typeof allCharacterDataKeys)[number]
export type CharacterGenderedKey = (typeof allCharacterGenderedKeys)[number]

export const maxEidolonCount = 6 as const

Expand Down Expand Up @@ -131,3 +131,7 @@ export type AbilityKey = (typeof allAbilityKeys)[number]

// TODO: need to check for correctness
export const talentLimits = [1, 1, 2, 4, 6, 8, 10] as const

export function isTrailblazerKey(key: CharacterKey): key is TrailblazerKey {
return allTrailblazerKeys.includes(key as TrailblazerKey)
}
12 changes: 12 additions & 0 deletions libs/sr/consts/src/relic.ts
Original file line number Diff line number Diff line change
Expand Up @@ -151,3 +151,15 @@ export const allRelicMainSubStatKeys = Array.from(
new Set([...allRelicSubStatKeys, ...allRelicMainStatKeys] as const)
)
export type RelicMainSubStatKey = (typeof allRelicMainSubStatKeys)[number]

export function isCavernRelicSetKey(
key: RelicSetKey
): key is RelicCavernSetKey {
return allRelicCavernSetKeys.includes(key as RelicCavernSetKey)
}

export function isPlanarRelicSetKey(
key: RelicSetKey
): key is RelicPlanarSetKey {
return allRelicPlanarSetKeys.includes(key as RelicPlanarSetKey)
}
1 change: 1 addition & 0 deletions libs/sr/db-ui/src/hooks/index.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
export * from './useBuild'
export * from './useCharacter'
export * from './useLightCone'
export * from './useRelic'
export * from './useRelics'
export * from './useTeam'
6 changes: 6 additions & 0 deletions libs/sr/db-ui/src/hooks/useRelic.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { useDataManagerBase } from '@genshin-optimizer/common/database-ui'
import { useDatabaseContext } from '../context'
export function useRelic(relicId: string | undefined) {
const { database } = useDatabaseContext()
return useDataManagerBase(database.relics, relicId ?? '')
}
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
import { verifyObjKeys } from '@genshin-optimizer/common/util'
import type { AbilityKey, CharacterDataKey } from '@genshin-optimizer/sr/consts'
import type {
AbilityKey,
CharacterGenderedKey,
} from '@genshin-optimizer/sr/consts'
import {
allAbilityKeys,
allCharacterDataKeys,
allCharacterGenderedKeys,
allTrailblazerGenderedKeys,
} from '@genshin-optimizer/sr/consts'
import type { AvatarSkillTreeConfig, Rank } from '@genshin-optimizer/sr/dm'
Expand Down Expand Up @@ -115,7 +118,7 @@ const charArray = Object.entries(avatarConfig).map(([charId, charConfig]) => {
const ranks = Object.fromEntries(rankArray)
verifyObjKeys(ranks, ['1', '2', '3', '4', '5', '6'] as const)

const tuple: [CharacterDataKey, CharData] = [
const tuple: [CharacterGenderedKey, CharData] = [
charKey,
{
name,
Expand All @@ -127,5 +130,5 @@ const charArray = Object.entries(avatarConfig).map(([charId, charConfig]) => {
})

const data = Object.fromEntries(charArray)
verifyObjKeys(data, allCharacterDataKeys)
verifyObjKeys(data, allCharacterGenderedKeys)
export const allCharHashData = data
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { verifyObjKeys } from '@genshin-optimizer/common/util'
import {
allCharacterDataKeys,
allCharacterGenderedKeys,
allLightConeKeys,
allRelicSetKeys,
} from '@genshin-optimizer/sr/consts'
Expand All @@ -14,7 +14,7 @@ export type LanguageData = typeof HashData
const charNames = Object.fromEntries(
Object.entries(allCharHashData).map(([key, data]) => [key, data.name])
)
verifyObjKeys(charNames, allCharacterDataKeys)
verifyObjKeys(charNames, allCharacterGenderedKeys)

const relicNames = Object.fromEntries(
Object.entries(allRelicHashData).map(([key, data]) => [key, data.setName])
Expand Down
4 changes: 2 additions & 2 deletions libs/sr/dm/src/mapping/character.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
import type {
CharacterDataKey,
CharacterGenderedKey,
ElementalTypeKey,
PathKey,
RarityKey,
} from '@genshin-optimizer/sr/consts'
import type { AvatarRarity } from '../dm'
import type { AvatarDamageType } from '../dm/character/AvatarConfig'

export const characterIdMap: Record<string, CharacterDataKey> = {
export const characterIdMap: Record<string, CharacterGenderedKey> = {
1001: 'March7th',
1002: 'DanHeng',
1003: 'Himeko',
Expand Down
6 changes: 2 additions & 4 deletions libs/sr/formula-ui/src/util.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type {
CharacterGenderedKey,
LightConeKey,
NonTrailblazerCharacterKey,
RelicSetKey,
Expand All @@ -19,10 +20,7 @@ type Translated = [
tr: (i18key: string, values?: Record<string, string | number>) => ReactNode
]

export function trans(
typeKey: 'char',
key: NonTrailblazerCharacterKey | TrailblazerGenderedKey
): Translated
export function trans(typeKey: 'char', key: CharacterGenderedKey): Translated
export function trans(typeKey: 'lightcone', key: LightConeKey): Translated
export function trans(typeKey: 'relic', key: RelicSetKey): Translated
export function trans(
Expand Down
75 changes: 17 additions & 58 deletions libs/sr/page-team/src/BuildsDisplay.tsx
Original file line number Diff line number Diff line change
@@ -1,35 +1,26 @@
import { useForceUpdate } from '@genshin-optimizer/common/react-util'
import { CardThemed } from '@genshin-optimizer/common/ui'
import type { RelicSlotKey } from '@genshin-optimizer/sr/consts'
import { allRelicSlotKeys } from '@genshin-optimizer/sr/consts'
import type {
ICachedRelic,
RelicIds,
TeammateDatum,
} from '@genshin-optimizer/sr/db'
import type { RelicIds, TeammateDatum } from '@genshin-optimizer/sr/db'
import {
useBuild,
useCharacterContext,
useDatabaseContext,
useLightCone,
useRelics,
} from '@genshin-optimizer/sr/db-ui'
import {
EmptyRelicCard,
LightConeCard,
RelicCard,
LightConeCardCompact,
RelicCardCompact,
} from '@genshin-optimizer/sr/ui'
import type { GridOwnProps } from '@mui/material'
import {
Box,
CardActionArea,
CardContent,
CardHeader,
Divider,
Grid,
Stack,
} from '@mui/material'
import type { ReactNode } from 'react'
import { memo, useEffect, useMemo } from 'react'
import { useEffect, useMemo } from 'react'
import { useTeamContext } from './context'
export function BuildsDisplay() {
const { database } = useDatabaseContext()
Expand Down Expand Up @@ -113,10 +104,7 @@ export function EquippedBuild() {
onClick={onClick}
active={active}
buildGrid={
<BuildGridBase
relicIds={equippedRelics}
lightConeId={equippedLightCone}
/>
<EquipRow relicIds={equippedRelics} lightConeId={equippedLightCone} />
}
/>
)
Expand All @@ -131,9 +119,7 @@ export function Build({ buildId }: { buildId: string }) {
description={description}
onClick={onClick}
active={active}
buildGrid={
<BuildGridBase relicIds={relicIds} lightConeId={lightConeId} />
}
buildGrid={<EquipRow relicIds={relicIds} lightConeId={lightConeId} />}
/>
)
}
Expand Down Expand Up @@ -166,52 +152,25 @@ function BuildBase({
)
}

/**
* A Grid of Lightcone + relics
* @returns
*/
export function BuildGridBase({
export function EquipRow({
relicIds,
lightConeId,
columns = 3,
}: {
relicIds: RelicIds
lightConeId?: string
columns?: GridOwnProps['columns']
}) {
const relics = useRelics(relicIds)
const lightcone = useLightCone(lightConeId)
return (
<Grid container columns={columns} spacing={1}>
{lightcone && (
<Grid item xs={1}>
<LightConeCard lightCone={lightcone} />
</Grid>
)}
<Box sx={{ display: 'flex', gap: 1, flexWrap: 'wrap' }}>
<LightConeCardCompact bgt="light" lightConeId={lightConeId} />
{allRelicSlotKeys.map((slot) => (
<GridItem
key={`${slot}_${relics[slot]?.id}`}
slot={slot}
relic={relics[slot]}
<RelicCardCompact
key={slot}
bgt="light"
relicId={relicIds[slot]}
slotKey={slot}
showLocation
/>
))}
</Grid>
</Box>
)
}
const GridItem = memo(function GridItem({
slot,
relic,
}: {
slot: RelicSlotKey
relic?: ICachedRelic
}) {
return (
<Grid item xs={1}>
{relic ? (
<RelicCard relic={relic} />
) : (
<EmptyRelicCard slot={slot} bgt="light" />
)}
</Grid>
)
})
Loading

0 comments on commit 1e12c1a

Please sign in to comment.