v3: localization fixes, char counters & limits on all text fields, ux fixes

This commit is contained in:
khannurien
2026-04-03 19:47:37 +00:00
parent 0ce80398a4
commit a69788c15b
48 changed files with 1133 additions and 305 deletions

View File

@@ -1,8 +1,8 @@
import React, { useMemo, useRef, useState } from "react";
import { Link } from "react-router";
import { t } from "@lingui/core/macro"
import { t } from "@lingui/core/macro";
import { Plural, Trans } from "@lingui/react/macro";
import { API_URL } from "../config/api.ts";
import { API_URL, VALIDATION } from "../config/api.ts";
import type {
Comment,
CreateCommentRequest,
@@ -79,7 +79,10 @@ function CommentNode({
async function handleReply(e?: React.SubmitEvent) {
e?.preventDefault();
if (!replyBody.trim() || !token) return;
if (
!replyBody.trim() || !token ||
replyBody.length > VALIDATION.COMMENT_BODY_MAX
) return;
setSubmitting(true);
setReplyError(null);
try {
@@ -124,7 +127,10 @@ function CommentNode({
async function handleEditSave(e?: React.SubmitEvent) {
e?.preventDefault();
if (!editBody.trim() || !token) return;
if (
!editBody.trim() || !token ||
editBody.length > VALIDATION.COMMENT_BODY_MAX
) return;
setEditSubmitting(true);
setEditError(null);
try {
@@ -244,17 +250,24 @@ function CommentNode({
onSubmit={handleEditSave}
autoResize
rows={1}
maxLength={VALIDATION.COMMENT_BODY_MAX}
/>
{editError && (
<ErrorCard title={t`Failed to save edit`} message={editError} />
<ErrorCard
title={t`Failed to save edit`}
message={editError}
/>
)}
<div className="comment-form-actions">
<button
type="submit"
className="comment-submit-btn"
disabled={editSubmitting || !editBody.trim()}
disabled={editSubmitting || !editBody.trim() ||
editBody.length > VALIDATION.COMMENT_BODY_MAX}
>
{editSubmitting ? <Trans>Saving…</Trans> : <Trans>Save</Trans>}
{editSubmitting
? <Trans>Saving…</Trans>
: <Trans>Save</Trans>}
</button>
<button
type="button"
@@ -329,17 +342,24 @@ function CommentNode({
placeholder={t`Write a reply…`}
autoResize
rows={1}
maxLength={VALIDATION.COMMENT_BODY_MAX}
/>
{replyError && (
<ErrorCard title={t`Failed to post reply`} message={replyError} />
<ErrorCard
title={t`Failed to post reply`}
message={replyError}
/>
)}
<div className="comment-form-actions">
<button
type="submit"
className="comment-submit-btn"
disabled={submitting || !replyBody.trim()}
disabled={submitting || !replyBody.trim() ||
replyBody.length > VALIDATION.COMMENT_BODY_MAX}
>
{submitting ? <Trans>Posting…</Trans> : <Trans>Post reply</Trans>}
{submitting
? <Trans>Posting…</Trans>
: <Trans>Post reply</Trans>}
</button>
<button
type="button"
@@ -400,7 +420,10 @@ export function CommentThread({
async function handleTopLevelSubmit(e?: React.SubmitEvent) {
e?.preventDefault();
if (!topLevelBody.trim() || !token) return;
if (
!topLevelBody.trim() || !token ||
topLevelBody.length > VALIDATION.COMMENT_BODY_MAX
) return;
setSubmitting(true);
setTopLevelError(null);
try {
@@ -456,6 +479,7 @@ export function CommentThread({
placeholder={t`Add a comment…`}
autoResize
rows={1}
maxLength={VALIDATION.COMMENT_BODY_MAX}
/>
{topLevelError && (
<ErrorCard
@@ -467,9 +491,12 @@ export function CommentThread({
<button
type="submit"
className="comment-submit-btn"
disabled={submitting || !topLevelBody.trim()}
disabled={submitting || !topLevelBody.trim() ||
topLevelBody.length > VALIDATION.COMMENT_BODY_MAX}
>
{submitting ? <Trans>Posting…</Trans> : <Trans>Post comment</Trans>}
{submitting
? <Trans>Posting…</Trans>
: <Trans>Post comment</Trans>}
</button>
{topLevelBody.trim() && (
<button