mirror of
https://github.com/LemmyNet/lemmy-ui.git
synced 2024-11-26 14:21:13 +00:00
Merge pull request #174 from LemmyNet/more_accessibility
More accessibility
This commit is contained in:
commit
01152eccbb
8 changed files with 169 additions and 19 deletions
18
accessibility_tests.sh
Executable file
18
accessibility_tests.sh
Executable file
|
@ -0,0 +1,18 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
ignores="WCAG2AA.Principle1.Guideline1_4.1_4_3.G18.Fail"
|
||||||
|
base_url="http://192.168.50.60:1234"
|
||||||
|
|
||||||
|
test_urls=(
|
||||||
|
$base_url
|
||||||
|
$base_url/communities
|
||||||
|
$base_url/login
|
||||||
|
$base_url/search
|
||||||
|
$base_url/c/announcements
|
||||||
|
$base_url/u/dessalines
|
||||||
|
$base_url/post/34286
|
||||||
|
)
|
||||||
|
|
||||||
|
for i in "${test_urls[@]}"; do
|
||||||
|
pa11y --ignore="$ignores" "$i"
|
||||||
|
done
|
|
@ -205,7 +205,14 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
onClick={linkEvent(node, this.handleCommentUpvote)}
|
onClick={linkEvent(node, this.handleCommentUpvote)}
|
||||||
data-tippy-content={this.pointsTippy}
|
data-tippy-content={this.pointsTippy}
|
||||||
>
|
>
|
||||||
<span class="mr-1 font-weight-bold">{this.state.score}</span>
|
<span
|
||||||
|
class="mr-1 font-weight-bold"
|
||||||
|
aria-label={i18n.t('number_of_points', {
|
||||||
|
count: this.state.score,
|
||||||
|
})}
|
||||||
|
>
|
||||||
|
{this.state.score}
|
||||||
|
</span>
|
||||||
</a>
|
</a>
|
||||||
<span className="mr-1">•</span>
|
<span className="mr-1">•</span>
|
||||||
<span>
|
<span>
|
||||||
|
@ -409,6 +416,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModRemoveShow
|
this.handleModRemoveShow
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('remove')}
|
||||||
>
|
>
|
||||||
{i18n.t('remove')}
|
{i18n.t('remove')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -419,6 +427,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModRemoveSubmit
|
this.handleModRemoveSubmit
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('restore')}
|
||||||
>
|
>
|
||||||
{i18n.t('restore')}
|
{i18n.t('restore')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -436,6 +445,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanFromCommunityShow
|
this.handleModBanFromCommunityShow
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('ban')}
|
||||||
>
|
>
|
||||||
{i18n.t('ban')}
|
{i18n.t('ban')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -446,6 +456,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanFromCommunitySubmit
|
this.handleModBanFromCommunitySubmit
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('unban')}
|
||||||
>
|
>
|
||||||
{i18n.t('unban')}
|
{i18n.t('unban')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -459,6 +470,11 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmAppointAsMod
|
this.handleShowConfirmAppointAsMod
|
||||||
)}
|
)}
|
||||||
|
aria-label={
|
||||||
|
this.isMod
|
||||||
|
? i18n.t('remove_as_mod')
|
||||||
|
: i18n.t('appoint_as_mod')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
{this.isMod
|
{this.isMod
|
||||||
? i18n.t('remove_as_mod')
|
? i18n.t('remove_as_mod')
|
||||||
|
@ -466,7 +482,10 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
</button>
|
</button>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<button class="btn btn-link btn-animate text-muted">
|
<button
|
||||||
|
class="btn btn-link btn-animate text-muted"
|
||||||
|
aria-label={i18n.t('are_you_sure')}
|
||||||
|
>
|
||||||
{i18n.t('are_you_sure')}
|
{i18n.t('are_you_sure')}
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
|
@ -475,6 +494,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleAddModToCommunity
|
this.handleAddModToCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -484,6 +504,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleCancelConfirmAppointAsMod
|
this.handleCancelConfirmAppointAsMod
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -502,12 +523,16 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmTransferCommunity
|
this.handleShowConfirmTransferCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('transfer_community')}
|
||||||
>
|
>
|
||||||
{i18n.t('transfer_community')}
|
{i18n.t('transfer_community')}
|
||||||
</button>
|
</button>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<button class="btn btn-link btn-animate text-muted">
|
<button
|
||||||
|
class="btn btn-link btn-animate text-muted"
|
||||||
|
aria-label={i18n.t('are_you_sure')}
|
||||||
|
>
|
||||||
{i18n.t('are_you_sure')}
|
{i18n.t('are_you_sure')}
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
|
@ -516,6 +541,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleTransferCommunity
|
this.handleTransferCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -526,6 +552,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this
|
this
|
||||||
.handleCancelShowConfirmTransferCommunity
|
.handleCancelShowConfirmTransferCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -542,6 +569,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanShow
|
this.handleModBanShow
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('ban_from_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('ban_from_site')}
|
{i18n.t('ban_from_site')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -552,6 +580,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanSubmit
|
this.handleModBanSubmit
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('unban_from_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('unban_from_site')}
|
{i18n.t('unban_from_site')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -565,6 +594,11 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmAppointAsAdmin
|
this.handleShowConfirmAppointAsAdmin
|
||||||
)}
|
)}
|
||||||
|
aria-label={
|
||||||
|
this.isAdmin
|
||||||
|
? i18n.t('remove_as_admin')
|
||||||
|
: i18n.t('appoint_as_admin')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
{this.isAdmin
|
{this.isAdmin
|
||||||
? i18n.t('remove_as_admin')
|
? i18n.t('remove_as_admin')
|
||||||
|
@ -581,6 +615,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleAddAdmin
|
this.handleAddAdmin
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -590,6 +625,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleCancelConfirmAppointAsAdmin
|
this.handleCancelConfirmAppointAsAdmin
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -608,12 +644,16 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmTransferSite
|
this.handleShowConfirmTransferSite
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('transfer_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('transfer_site')}
|
{i18n.t('transfer_site')}
|
||||||
</button>
|
</button>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<button class="btn btn-link btn-animate text-muted">
|
<button
|
||||||
|
class="btn btn-link btn-animate text-muted"
|
||||||
|
aria-label={i18n.t('are_you_sure')}
|
||||||
|
>
|
||||||
{i18n.t('are_you_sure')}
|
{i18n.t('are_you_sure')}
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
|
@ -622,6 +662,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleTransferSite
|
this.handleTransferSite
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -631,6 +672,7 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
this,
|
this,
|
||||||
this.handleCancelShowConfirmTransferSite
|
this.handleCancelShowConfirmTransferSite
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -652,14 +694,25 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
class="form-inline"
|
class="form-inline"
|
||||||
onSubmit={linkEvent(this, this.handleModRemoveSubmit)}
|
onSubmit={linkEvent(this, this.handleModRemoveSubmit)}
|
||||||
>
|
>
|
||||||
|
<label
|
||||||
|
class="sr-only"
|
||||||
|
htmlFor={`mod-remove-reason-${cv.comment.id}`}
|
||||||
|
>
|
||||||
|
{i18n.t('reason')}
|
||||||
|
</label>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
|
id={`mod-remove-reason-${cv.comment.id}`}
|
||||||
class="form-control mr-2"
|
class="form-control mr-2"
|
||||||
placeholder={i18n.t('reason')}
|
placeholder={i18n.t('reason')}
|
||||||
value={this.state.removeReason}
|
value={this.state.removeReason}
|
||||||
onInput={linkEvent(this, this.handleModRemoveReasonChange)}
|
onInput={linkEvent(this, this.handleModRemoveReasonChange)}
|
||||||
/>
|
/>
|
||||||
<button type="submit" class="btn btn-secondary">
|
<button
|
||||||
|
type="submit"
|
||||||
|
class="btn btn-secondary"
|
||||||
|
aria-label={i18n.t('remove_comment')}
|
||||||
|
>
|
||||||
{i18n.t('remove_comment')}
|
{i18n.t('remove_comment')}
|
||||||
</button>
|
</button>
|
||||||
</form>
|
</form>
|
||||||
|
@ -702,7 +755,11 @@ export class CommentNode extends Component<CommentNodeProps, CommentNodeState> {
|
||||||
{/* <input type="date" class="form-control mr-2" placeholder={i18n.t('expires')} value={this.state.banExpires} onInput={linkEvent(this, this.handleModBanExpiresChange)} /> */}
|
{/* <input type="date" class="form-control mr-2" placeholder={i18n.t('expires')} value={this.state.banExpires} onInput={linkEvent(this, this.handleModBanExpiresChange)} /> */}
|
||||||
{/* </div> */}
|
{/* </div> */}
|
||||||
<div class="form-group row">
|
<div class="form-group row">
|
||||||
<button type="submit" class="btn btn-secondary">
|
<button
|
||||||
|
type="submit"
|
||||||
|
class="btn btn-secondary"
|
||||||
|
aria-label={i18n.t('ban')}
|
||||||
|
>
|
||||||
{i18n.t('ban')} {cv.creator.name}
|
{i18n.t('ban')} {cv.creator.name}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -198,6 +198,7 @@ export class Communities extends Component<any, CommunitiesState> {
|
||||||
>
|
>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
|
id="communities-search"
|
||||||
class="form-control mr-2 mb-2"
|
class="form-control mr-2 mb-2"
|
||||||
value={this.state.searchText}
|
value={this.state.searchText}
|
||||||
placeholder={`${i18n.t('search')}...`}
|
placeholder={`${i18n.t('search')}...`}
|
||||||
|
@ -205,6 +206,9 @@ export class Communities extends Component<any, CommunitiesState> {
|
||||||
required
|
required
|
||||||
minLength={3}
|
minLength={3}
|
||||||
/>
|
/>
|
||||||
|
<label class="sr-only" htmlFor="communities-search">
|
||||||
|
{i18n.t('search')}
|
||||||
|
</label>
|
||||||
<button type="submit" class="btn btn-secondary mr-2 mb-2">
|
<button type="submit" class="btn btn-secondary mr-2 mb-2">
|
||||||
<span>{i18n.t('search')}</span>
|
<span>{i18n.t('search')}</span>
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -253,6 +253,7 @@ export class Login extends Component<any, State> {
|
||||||
type="button"
|
type="button"
|
||||||
class="btn btn-secondary"
|
class="btn btn-secondary"
|
||||||
onClick={linkEvent(this, this.handleRegenCaptcha)}
|
onClick={linkEvent(this, this.handleRegenCaptcha)}
|
||||||
|
aria-label={i18n.t('captcha')}
|
||||||
>
|
>
|
||||||
<Icon icon="refresh-cw" classes="icon-refresh-cw" />
|
<Icon icon="refresh-cw" classes="icon-refresh-cw" />
|
||||||
</button>
|
</button>
|
||||||
|
|
|
@ -139,6 +139,9 @@ export class MarkdownTextArea extends Component<
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
<label class="sr-only" htmlFor={this.id}>
|
||||||
|
{i18n.t('body')}
|
||||||
|
</label>
|
||||||
</div>
|
</div>
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-sm-12 d-flex flex-wrap">
|
<div class="col-sm-12 d-flex flex-wrap">
|
||||||
|
@ -179,6 +182,7 @@ export class MarkdownTextArea extends Component<
|
||||||
<button
|
<button
|
||||||
class="btn btn-sm text-muted"
|
class="btn btn-sm text-muted"
|
||||||
data-tippy-content={i18n.t('bold')}
|
data-tippy-content={i18n.t('bold')}
|
||||||
|
aria-label={i18n.t('bold')}
|
||||||
onClick={linkEvent(this, this.handleInsertBold)}
|
onClick={linkEvent(this, this.handleInsertBold)}
|
||||||
>
|
>
|
||||||
<Icon icon="bold" classes="icon-inline" />
|
<Icon icon="bold" classes="icon-inline" />
|
||||||
|
@ -186,6 +190,7 @@ export class MarkdownTextArea extends Component<
|
||||||
<button
|
<button
|
||||||
class="btn btn-sm text-muted"
|
class="btn btn-sm text-muted"
|
||||||
data-tippy-content={i18n.t('italic')}
|
data-tippy-content={i18n.t('italic')}
|
||||||
|
aria-label={i18n.t('italic')}
|
||||||
onClick={linkEvent(this, this.handleInsertItalic)}
|
onClick={linkEvent(this, this.handleInsertItalic)}
|
||||||
>
|
>
|
||||||
<Icon icon="italic" classes="icon-inline" />
|
<Icon icon="italic" classes="icon-inline" />
|
||||||
|
@ -193,6 +198,7 @@ export class MarkdownTextArea extends Component<
|
||||||
<button
|
<button
|
||||||
class="btn btn-sm text-muted"
|
class="btn btn-sm text-muted"
|
||||||
data-tippy-content={i18n.t('link')}
|
data-tippy-content={i18n.t('link')}
|
||||||
|
aria-label={i18n.t('link')}
|
||||||
onClick={linkEvent(this, this.handleInsertLink)}
|
onClick={linkEvent(this, this.handleInsertLink)}
|
||||||
>
|
>
|
||||||
<Icon icon="link" classes="icon-inline" />
|
<Icon icon="link" classes="icon-inline" />
|
||||||
|
|
|
@ -201,7 +201,12 @@ export class Navbar extends Component<NavbarProps, NavbarState> {
|
||||||
>
|
>
|
||||||
<Icon icon="bell" />
|
<Icon icon="bell" />
|
||||||
{this.state.unreadCount > 0 && (
|
{this.state.unreadCount > 0 && (
|
||||||
<span class="mx-1 badge badge-light">
|
<span
|
||||||
|
class="mx-1 badge badge-light"
|
||||||
|
aria-label={`${this.state.unreadCount} ${i18n.t(
|
||||||
|
'unread_messages'
|
||||||
|
)}`}
|
||||||
|
>
|
||||||
{this.state.unreadCount}
|
{this.state.unreadCount}
|
||||||
</span>
|
</span>
|
||||||
)}
|
)}
|
||||||
|
@ -281,6 +286,7 @@ export class Navbar extends Component<NavbarProps, NavbarState> {
|
||||||
onSubmit={linkEvent(this, this.handleSearchSubmit)}
|
onSubmit={linkEvent(this, this.handleSearchSubmit)}
|
||||||
>
|
>
|
||||||
<input
|
<input
|
||||||
|
id="search-input"
|
||||||
class={`form-control mr-0 search-input ${
|
class={`form-control mr-0 search-input ${
|
||||||
this.state.toggleSearch ? 'show-input' : 'hide-input'
|
this.state.toggleSearch ? 'show-input' : 'hide-input'
|
||||||
}`}
|
}`}
|
||||||
|
@ -291,11 +297,15 @@ export class Navbar extends Component<NavbarProps, NavbarState> {
|
||||||
placeholder={i18n.t('search')}
|
placeholder={i18n.t('search')}
|
||||||
onBlur={linkEvent(this, this.handleSearchBlur)}
|
onBlur={linkEvent(this, this.handleSearchBlur)}
|
||||||
></input>
|
></input>
|
||||||
|
<label class="sr-only" htmlFor="search-input">
|
||||||
|
{i18n.t('search')}
|
||||||
|
</label>
|
||||||
<button
|
<button
|
||||||
name="search-btn"
|
name="search-btn"
|
||||||
onClick={linkEvent(this, this.handleSearchBtn)}
|
onClick={linkEvent(this, this.handleSearchBtn)}
|
||||||
class="px-1 btn btn-link"
|
class="px-1 btn btn-link"
|
||||||
style="color: var(--gray)"
|
style="color: var(--gray)"
|
||||||
|
aria-label={i18n.t('search')}
|
||||||
>
|
>
|
||||||
<Icon icon="search" />
|
<Icon icon="search" />
|
||||||
</button>
|
</button>
|
||||||
|
@ -312,7 +322,12 @@ export class Navbar extends Component<NavbarProps, NavbarState> {
|
||||||
>
|
>
|
||||||
<Icon icon="bell" />
|
<Icon icon="bell" />
|
||||||
{this.state.unreadCount > 0 && (
|
{this.state.unreadCount > 0 && (
|
||||||
<span class="ml-1 badge badge-light">
|
<span
|
||||||
|
class="ml-1 badge badge-light"
|
||||||
|
aria-label={`${this.state.unreadCount} ${i18n.t(
|
||||||
|
'unread_messages'
|
||||||
|
)}`}
|
||||||
|
>
|
||||||
{this.state.unreadCount}
|
{this.state.unreadCount}
|
||||||
</span>
|
</span>
|
||||||
)}
|
)}
|
||||||
|
|
|
@ -27,7 +27,6 @@ import {
|
||||||
debounce,
|
debounce,
|
||||||
isImage,
|
isImage,
|
||||||
toast,
|
toast,
|
||||||
randomStr,
|
|
||||||
setupTippy,
|
setupTippy,
|
||||||
hostname,
|
hostname,
|
||||||
pictrsDeleteToast,
|
pictrsDeleteToast,
|
||||||
|
@ -72,7 +71,6 @@ interface PostFormState {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class PostForm extends Component<PostFormProps, PostFormState> {
|
export class PostForm extends Component<PostFormProps, PostFormState> {
|
||||||
private id = `post-form-${randomStr()}`;
|
|
||||||
private subscription: Subscription;
|
private subscription: Subscription;
|
||||||
private choices: any;
|
private choices: any;
|
||||||
private emptyState: PostFormState = {
|
private emptyState: PostFormState = {
|
||||||
|
@ -278,9 +276,7 @@ export class PostForm extends Component<PostFormProps, PostFormState> {
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="form-group row">
|
<div class="form-group row">
|
||||||
<label class="col-sm-2 col-form-label" htmlFor={this.id}>
|
<label class="col-sm-2 col-form-label">{i18n.t('body')}</label>
|
||||||
{i18n.t('body')}
|
|
||||||
</label>
|
|
||||||
<div class="col-sm-10">
|
<div class="col-sm-10">
|
||||||
<MarkdownTextArea
|
<MarkdownTextArea
|
||||||
initialContent={this.state.postForm.body}
|
initialContent={this.state.postForm.body}
|
||||||
|
|
|
@ -639,6 +639,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleEditClick)}
|
onClick={linkEvent(this, this.handleEditClick)}
|
||||||
data-tippy-content={i18n.t('edit')}
|
data-tippy-content={i18n.t('edit')}
|
||||||
|
aria-label={i18n.t('edit')}
|
||||||
>
|
>
|
||||||
<Icon icon="edit" classes="icon-inline" />
|
<Icon icon="edit" classes="icon-inline" />
|
||||||
</button>
|
</button>
|
||||||
|
@ -648,6 +649,9 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
data-tippy-content={
|
data-tippy-content={
|
||||||
!post_view.post.deleted ? i18n.t('delete') : i18n.t('restore')
|
!post_view.post.deleted ? i18n.t('delete') : i18n.t('restore')
|
||||||
}
|
}
|
||||||
|
aria-label={
|
||||||
|
!post_view.post.deleted ? i18n.t('delete') : i18n.t('restore')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
<Icon
|
<Icon
|
||||||
icon="trash"
|
icon="trash"
|
||||||
|
@ -675,6 +679,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleViewSource)}
|
onClick={linkEvent(this, this.handleViewSource)}
|
||||||
data-tippy-content={i18n.t('view_source')}
|
data-tippy-content={i18n.t('view_source')}
|
||||||
|
aria-label={i18n.t('view_source')}
|
||||||
>
|
>
|
||||||
<Icon
|
<Icon
|
||||||
icon="file-text"
|
icon="file-text"
|
||||||
|
@ -692,6 +697,9 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
data-tippy-content={
|
data-tippy-content={
|
||||||
post_view.post.locked ? i18n.t('unlock') : i18n.t('lock')
|
post_view.post.locked ? i18n.t('unlock') : i18n.t('lock')
|
||||||
}
|
}
|
||||||
|
aria-label={
|
||||||
|
post_view.post.locked ? i18n.t('unlock') : i18n.t('lock')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
<Icon
|
<Icon
|
||||||
icon="lock"
|
icon="lock"
|
||||||
|
@ -708,6 +716,11 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
? i18n.t('unsticky')
|
? i18n.t('unsticky')
|
||||||
: i18n.t('sticky')
|
: i18n.t('sticky')
|
||||||
}
|
}
|
||||||
|
aria-label={
|
||||||
|
post_view.post.stickied
|
||||||
|
? i18n.t('unsticky')
|
||||||
|
: i18n.t('sticky')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
<Icon
|
<Icon
|
||||||
icon="pin"
|
icon="pin"
|
||||||
|
@ -724,6 +737,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleModRemoveShow)}
|
onClick={linkEvent(this, this.handleModRemoveShow)}
|
||||||
|
aria-label={i18n.t('remove')}
|
||||||
>
|
>
|
||||||
{i18n.t('remove')}
|
{i18n.t('remove')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -731,6 +745,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleModRemoveSubmit)}
|
onClick={linkEvent(this, this.handleModRemoveSubmit)}
|
||||||
|
aria-label={i18n.t('restore')}
|
||||||
>
|
>
|
||||||
{i18n.t('restore')}
|
{i18n.t('restore')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -745,6 +760,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanFromCommunityShow
|
this.handleModBanFromCommunityShow
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('ban')}
|
||||||
>
|
>
|
||||||
{i18n.t('ban')}
|
{i18n.t('ban')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -755,6 +771,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleModBanFromCommunitySubmit
|
this.handleModBanFromCommunitySubmit
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('unban')}
|
||||||
>
|
>
|
||||||
{i18n.t('unban')}
|
{i18n.t('unban')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -764,6 +781,11 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleAddModToCommunity)}
|
onClick={linkEvent(this, this.handleAddModToCommunity)}
|
||||||
|
aria-label={
|
||||||
|
this.isMod
|
||||||
|
? i18n.t('remove_as_mod')
|
||||||
|
: i18n.t('appoint_as_mod')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
{this.isMod
|
{this.isMod
|
||||||
? i18n.t('remove_as_mod')
|
? i18n.t('remove_as_mod')
|
||||||
|
@ -783,16 +805,21 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmTransferCommunity
|
this.handleShowConfirmTransferCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('transfer_community')}
|
||||||
>
|
>
|
||||||
{i18n.t('transfer_community')}
|
{i18n.t('transfer_community')}
|
||||||
</button>
|
</button>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<button class="d-inline-block mr-1 btn btn-link btn-animate text-muted py-0">
|
<button
|
||||||
|
class="d-inline-block mr-1 btn btn-link btn-animate text-muted py-0"
|
||||||
|
aria-label={i18n.t('are_you_sure')}
|
||||||
|
>
|
||||||
{i18n.t('are_you_sure')}
|
{i18n.t('are_you_sure')}
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1"
|
class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1"
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
onClick={linkEvent(this, this.handleTransferCommunity)}
|
onClick={linkEvent(this, this.handleTransferCommunity)}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
|
@ -803,6 +830,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleCancelShowConfirmTransferCommunity
|
this.handleCancelShowConfirmTransferCommunity
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -816,6 +844,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleModBanShow)}
|
onClick={linkEvent(this, this.handleModBanShow)}
|
||||||
|
aria-label={i18n.t('ban_from_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('ban_from_site')}
|
{i18n.t('ban_from_site')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -823,6 +852,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleModBanSubmit)}
|
onClick={linkEvent(this, this.handleModBanSubmit)}
|
||||||
|
aria-label={i18n.t('unban_from_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('unban_from_site')}
|
{i18n.t('unban_from_site')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -831,6 +861,11 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0"
|
class="btn btn-link btn-animate text-muted py-0"
|
||||||
onClick={linkEvent(this, this.handleAddAdmin)}
|
onClick={linkEvent(this, this.handleAddAdmin)}
|
||||||
|
aria-label={
|
||||||
|
this.isAdmin
|
||||||
|
? i18n.t('remove_as_admin')
|
||||||
|
: i18n.t('appoint_as_admin')
|
||||||
|
}
|
||||||
>
|
>
|
||||||
{this.isAdmin
|
{this.isAdmin
|
||||||
? i18n.t('remove_as_admin')
|
? i18n.t('remove_as_admin')
|
||||||
|
@ -849,17 +884,22 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleShowConfirmTransferSite
|
this.handleShowConfirmTransferSite
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('transfer_site')}
|
||||||
>
|
>
|
||||||
{i18n.t('transfer_site')}
|
{i18n.t('transfer_site')}
|
||||||
</button>
|
</button>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<button class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1">
|
<button
|
||||||
|
class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1"
|
||||||
|
aria-label={i18n.t('are_you_sure')}
|
||||||
|
>
|
||||||
{i18n.t('are_you_sure')}
|
{i18n.t('are_you_sure')}
|
||||||
</button>
|
</button>
|
||||||
<button
|
<button
|
||||||
class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1"
|
class="btn btn-link btn-animate text-muted py-0 d-inline-block mr-1"
|
||||||
onClick={linkEvent(this, this.handleTransferSite)}
|
onClick={linkEvent(this, this.handleTransferSite)}
|
||||||
|
aria-label={i18n.t('yes')}
|
||||||
>
|
>
|
||||||
{i18n.t('yes')}
|
{i18n.t('yes')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -869,6 +909,7 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
this,
|
this,
|
||||||
this.handleCancelShowConfirmTransferSite
|
this.handleCancelShowConfirmTransferSite
|
||||||
)}
|
)}
|
||||||
|
aria-label={i18n.t('no')}
|
||||||
>
|
>
|
||||||
{i18n.t('no')}
|
{i18n.t('no')}
|
||||||
</button>
|
</button>
|
||||||
|
@ -890,14 +931,22 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
class="form-inline"
|
class="form-inline"
|
||||||
onSubmit={linkEvent(this, this.handleModRemoveSubmit)}
|
onSubmit={linkEvent(this, this.handleModRemoveSubmit)}
|
||||||
>
|
>
|
||||||
|
<label class="sr-only" htmlFor="post-listing-remove-reason">
|
||||||
|
{i18n.t('reason')}
|
||||||
|
</label>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
|
id="post-listing-remove-reason"
|
||||||
class="form-control mr-2"
|
class="form-control mr-2"
|
||||||
placeholder={i18n.t('reason')}
|
placeholder={i18n.t('reason')}
|
||||||
value={this.state.removeReason}
|
value={this.state.removeReason}
|
||||||
onInput={linkEvent(this, this.handleModRemoveReasonChange)}
|
onInput={linkEvent(this, this.handleModRemoveReasonChange)}
|
||||||
/>
|
/>
|
||||||
<button type="submit" class="btn btn-secondary">
|
<button
|
||||||
|
type="submit"
|
||||||
|
class="btn btn-secondary"
|
||||||
|
aria-label={i18n.t('remove_post')}
|
||||||
|
>
|
||||||
{i18n.t('remove_post')}
|
{i18n.t('remove_post')}
|
||||||
</button>
|
</button>
|
||||||
</form>
|
</form>
|
||||||
|
@ -905,12 +954,12 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
{this.state.showBanDialog && (
|
{this.state.showBanDialog && (
|
||||||
<form onSubmit={linkEvent(this, this.handleModBanBothSubmit)}>
|
<form onSubmit={linkEvent(this, this.handleModBanBothSubmit)}>
|
||||||
<div class="form-group row">
|
<div class="form-group row">
|
||||||
<label class="col-form-label" htmlFor="post-listing-reason">
|
<label class="col-form-label" htmlFor="post-listing-ban-reason">
|
||||||
{i18n.t('reason')}
|
{i18n.t('reason')}
|
||||||
</label>
|
</label>
|
||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
id="post-listing-reason"
|
id="post-listing-ban-reason"
|
||||||
class="form-control mr-2"
|
class="form-control mr-2"
|
||||||
placeholder={i18n.t('reason')}
|
placeholder={i18n.t('reason')}
|
||||||
value={this.state.banReason}
|
value={this.state.banReason}
|
||||||
|
@ -937,7 +986,11 @@ export class PostListing extends Component<PostListingProps, PostListingState> {
|
||||||
{/* <input type="date" class="form-control mr-2" placeholder={i18n.t('expires')} value={this.state.banExpires} onInput={linkEvent(this, this.handleModBanExpiresChange)} /> */}
|
{/* <input type="date" class="form-control mr-2" placeholder={i18n.t('expires')} value={this.state.banExpires} onInput={linkEvent(this, this.handleModBanExpiresChange)} /> */}
|
||||||
{/* </div> */}
|
{/* </div> */}
|
||||||
<div class="form-group row">
|
<div class="form-group row">
|
||||||
<button type="submit" class="btn btn-secondary">
|
<button
|
||||||
|
type="submit"
|
||||||
|
class="btn btn-secondary"
|
||||||
|
aria-label={i18n.t('ban')}
|
||||||
|
>
|
||||||
{i18n.t('ban')} {post.creator.name}
|
{i18n.t('ban')} {post.creator.name}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
Loading…
Reference in a new issue