인게임 예약 명령과 장수 상태 표시를 바로잡음
This commit is contained in:
@@ -12,6 +12,7 @@ import {
|
||||
} from '../command/commandArgumentDraft';
|
||||
import { legacyNationTextColor } from '../../utils/legacyNationColor';
|
||||
import { getNpcColor } from '../../utils/npcColor';
|
||||
import { getLegacyStringWidth } from '@sammo-ts/logic/troop/management.js';
|
||||
import type {
|
||||
CommandInputContext,
|
||||
CommandInputField,
|
||||
@@ -309,6 +310,14 @@ const setNumberPreset = (field: CommandInputField, rawValue: string, tupleIndex?
|
||||
const effectiveMin = (field: CommandInputField): number | undefined => amountPreset.value?.min ?? field.min;
|
||||
const effectiveMax = (field: CommandInputField): number | undefined => amountPreset.value?.max ?? field.max;
|
||||
const effectiveStep = (field: CommandInputField): number | undefined => amountPreset.value?.step ?? field.step;
|
||||
const textFieldError = (field: CommandInputField): string => {
|
||||
const value = values[field.key];
|
||||
if (field.kind !== 'text' || typeof value !== 'string') return '';
|
||||
if (field.legacyWidthMax !== undefined && getLegacyStringWidth(value.trim()) > field.legacyWidthMax) {
|
||||
return `${field.label}은 전각 ${Math.floor(field.legacyWidthMax / 2)}자 또는 반각 ${field.legacyWidthMax}자 이하여야 합니다.`;
|
||||
}
|
||||
return '';
|
||||
};
|
||||
|
||||
const OPTION_CARD_COMMANDS = new Set([
|
||||
'che_물자원조',
|
||||
@@ -334,7 +343,8 @@ const isValid = computed(() =>
|
||||
return (
|
||||
(!field.required || length > 0) &&
|
||||
(field.min === undefined || length >= field.min) &&
|
||||
(field.max === undefined || length <= field.max)
|
||||
(field.max === undefined || length <= field.max) &&
|
||||
!textFieldError(field)
|
||||
);
|
||||
}
|
||||
if (field.kind === 'number') {
|
||||
@@ -429,8 +439,18 @@ watch(
|
||||
:value="String(values[field.key] ?? '')"
|
||||
:minlength="field.min"
|
||||
:maxlength="field.max"
|
||||
:aria-invalid="Boolean(textFieldError(field))"
|
||||
:aria-describedby="textFieldError(field) ? `command-arg-${field.key}-error` : undefined"
|
||||
@input="values[field.key] = ($event.target as HTMLInputElement).value"
|
||||
/>
|
||||
<small
|
||||
v-if="field.kind === 'text' && textFieldError(field)"
|
||||
:id="`command-arg-${field.key}-error`"
|
||||
class="argument-error"
|
||||
role="alert"
|
||||
>
|
||||
{{ textFieldError(field) }}
|
||||
</small>
|
||||
<div v-else-if="field.kind === 'number'" class="number-options">
|
||||
<input
|
||||
:id="`command-arg-${field.key}`"
|
||||
@@ -647,6 +667,12 @@ watch(
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.argument-error {
|
||||
grid-column: 2;
|
||||
margin: -2px 6px 5px 0;
|
||||
color: #ff9a9a;
|
||||
}
|
||||
|
||||
.option-detail {
|
||||
grid-column: 2;
|
||||
display: flex;
|
||||
|
||||
@@ -9,6 +9,7 @@ import { legacyExperiencePercent, ratioPercent } from '../../utils/legacyProgres
|
||||
import { DEFAULT_GENERAL_ICON_URL, resolveGeneralIconUrl, useDefaultGeneralIcon } from '../../utils/generalIcon';
|
||||
import { configuredGameAssetUrl } from '../../utils/imageAssets';
|
||||
import { legacyLuminanceTextColor } from '../../utils/legacyNationColor';
|
||||
import { generalInjuryPresentation } from '../../utils/generalInjury';
|
||||
|
||||
interface GeneralStats {
|
||||
leadership: number;
|
||||
@@ -175,14 +176,7 @@ const crewTypeIconBackground = computed(() => {
|
||||
return `url(${JSON.stringify(crewTypeUrl)}), url(${JSON.stringify(DEFAULT_GENERAL_ICON_URL)})`;
|
||||
});
|
||||
|
||||
const injuryInfo = computed(() => {
|
||||
const injury = props.general?.injury ?? 0;
|
||||
if (injury > 60) return { text: '위독', color: '#ff0000' };
|
||||
if (injury > 40) return { text: '심각', color: '#ff00ff' };
|
||||
if (injury > 20) return { text: '중상', color: '#ffa500' };
|
||||
if (injury > 0) return { text: '경상', color: '#ffff00' };
|
||||
return { text: '건강', color: '#ffffff' };
|
||||
});
|
||||
const injuryInfo = computed(() => generalInjuryPresentation(props.general?.injury ?? 0));
|
||||
|
||||
const titleStyle = computed(() => {
|
||||
const backgroundColor = props.nationColor || '#173d27';
|
||||
|
||||
@@ -55,6 +55,7 @@ const destination = computed<MessageTarget>(
|
||||
);
|
||||
|
||||
const invalid = computed(() => props.message.option?.invalid === true);
|
||||
const permissionRedacted = computed(() => props.message.option?.permissionRedacted === true);
|
||||
const hasAction = computed(() => typeof props.message.option?.action === 'string');
|
||||
const nationDirection = computed(() => {
|
||||
if (props.message.src.nationId === destination.value.nationId) {
|
||||
@@ -134,7 +135,12 @@ onBeforeUnmount(() => {
|
||||
<template>
|
||||
<article
|
||||
:id="`msg_${message.id}`"
|
||||
:class="['msg-plate', `msg-plate-${message.msgType}`, `msg-plate-${nationDirection}`]"
|
||||
:class="[
|
||||
'msg-plate',
|
||||
`msg-plate-${message.msgType}`,
|
||||
`msg-plate-${nationDirection}`,
|
||||
{ 'msg-plate-permission-redacted': permissionRedacted },
|
||||
]"
|
||||
:data-id="message.id"
|
||||
>
|
||||
<div class="msg-icon">
|
||||
@@ -262,7 +268,13 @@ onBeforeUnmount(() => {
|
||||
<span class="msg-time"><{{ message.time }}></span>
|
||||
</div>
|
||||
|
||||
<div :class="['msg-content', invalid ? 'msg-invalid' : 'msg-valid']">
|
||||
<div
|
||||
:class="[
|
||||
'msg-content',
|
||||
invalid ? 'msg-invalid' : permissionRedacted ? 'msg-permission-redacted' : 'msg-valid',
|
||||
]"
|
||||
>
|
||||
<strong v-if="permissionRedacted" class="permission-redacted-label">권한 제한</strong>
|
||||
{{ invalid ? '삭제된 메시지입니다' : message.text }}
|
||||
</div>
|
||||
|
||||
@@ -411,6 +423,30 @@ button.msg-target {
|
||||
color: rgba(255, 255, 255, 0.5);
|
||||
}
|
||||
|
||||
.msg-plate-permission-redacted {
|
||||
outline: 1px dashed #d7b86c;
|
||||
background: #3b3427;
|
||||
}
|
||||
|
||||
.msg-plate-permission-redacted .general-icon {
|
||||
filter: grayscale(1);
|
||||
opacity: 0.55;
|
||||
}
|
||||
|
||||
.msg-permission-redacted {
|
||||
color: rgba(255, 244, 214, 0.72);
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
.permission-redacted-label {
|
||||
display: inline-block;
|
||||
margin-right: 6px;
|
||||
border: 1px solid #d7b86c;
|
||||
padding: 1px 4px;
|
||||
color: #ffe0a0;
|
||||
font-style: normal;
|
||||
}
|
||||
|
||||
.message-response {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
|
||||
Reference in New Issue
Block a user