Implement quote posts in Moderator UI (#35964)
This commit is contained in:
@@ -113,6 +113,7 @@ module ApplicationHelper
|
||||
end
|
||||
|
||||
def material_symbol(icon, attributes = {})
|
||||
whitespace = attributes.delete(:whitespace) { true }
|
||||
safe_join(
|
||||
[
|
||||
inline_svg_tag(
|
||||
@@ -121,7 +122,7 @@ module ApplicationHelper
|
||||
role: :img,
|
||||
data: attributes[:data]
|
||||
),
|
||||
' ',
|
||||
whitespace ? ' ' : '',
|
||||
]
|
||||
)
|
||||
end
|
||||
|
||||
@@ -46,6 +46,14 @@ module StatusesHelper
|
||||
status.preloadable_poll.options.map { |o| "[ ] #{o}" }.join("\n")
|
||||
end
|
||||
|
||||
def status_classnames(status, is_quote)
|
||||
if is_quote
|
||||
'status--is-quote'
|
||||
elsif status.quote.present?
|
||||
'status--has-quote'
|
||||
end
|
||||
end
|
||||
|
||||
def status_description(status)
|
||||
components = [[media_summary(status), status_text_summary(status)].compact_blank.join(' · ')]
|
||||
|
||||
|
||||
@@ -1955,15 +1955,33 @@ a.sparkline {
|
||||
box-sizing: border-box;
|
||||
min-height: 100%;
|
||||
|
||||
&.status--has-quote {
|
||||
.quote-inline {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.status__quote & {
|
||||
// Remove the border from the .status__card within .status__quote
|
||||
border: none;
|
||||
|
||||
.display-name__account {
|
||||
line-height: inherit;
|
||||
}
|
||||
|
||||
.status__avatar,
|
||||
.status__avatar .account__avatar {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
}
|
||||
}
|
||||
|
||||
.status__prepend {
|
||||
padding: 0 0 15px;
|
||||
gap: 4px;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.status__content {
|
||||
padding-top: 0;
|
||||
|
||||
> details {
|
||||
summary {
|
||||
display: block;
|
||||
@@ -2009,7 +2027,6 @@ a.sparkline {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.preview-card {
|
||||
position: relative;
|
||||
@@ -2065,6 +2082,14 @@ a.sparkline {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.detailed-status__meta {
|
||||
.detailed-status__application,
|
||||
.detailed-status__datetime,
|
||||
.detailed-status__link {
|
||||
color: inherit;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.admin {
|
||||
|
||||
@@ -356,7 +356,7 @@ a.table-action-link {
|
||||
|
||||
// Reset the status card to not have borders, background or padding when
|
||||
// inline in the table of statuses
|
||||
.status__card {
|
||||
.batch-table__row__content > .status__card {
|
||||
border: none;
|
||||
background: none;
|
||||
padding: 0;
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
-# locals: (status:)
|
||||
|
||||
.status__card><
|
||||
-# locals: (status:, is_quote: false)
|
||||
.status__card{ class: status_classnames(status, is_quote) }
|
||||
- if status.reblog?
|
||||
.status__prepend
|
||||
= material_symbol('repeat')
|
||||
@@ -10,12 +9,26 @@
|
||||
= material_symbol('reply')
|
||||
= t('admin.statuses.replied_to_html', acct_link: admin_account_inline_link_to(status.in_reply_to_account, path: status.thread.present? ? admin_account_status_path(status.thread.account_id, status.in_reply_to_id) : nil))
|
||||
|
||||
= render partial: 'admin/shared/status_content', locals: { status: status.proper }
|
||||
- if is_quote
|
||||
.status__info
|
||||
= conditional_link_to can?(:show, status), admin_account_status_path(status.account.id, status), class: 'status__relative-time' do
|
||||
%span.status__visibility-icon{ title: t("statuses.visibilities.#{status.visibility}") }><
|
||||
= material_symbol(visibility_icon(status), whitespace: false)
|
||||
%time.relative-formatted{ datetime: status.created_at.iso8601, title: l(status.created_at) }><= l(status.created_at)
|
||||
= link_to admin_account_path(status.account.id), class: 'status__display-name' do
|
||||
.status__avatar
|
||||
.account__avatar
|
||||
= image_tag status.account.avatar.url(:original), alt: '', width: 46, height: 46, class: 'avatar'
|
||||
.display-name
|
||||
%bdi
|
||||
%strong.display-name__html.emojify.p-name= display_name(status.account, custom_emojify: true)
|
||||
%span.display-name__account
|
||||
= acct(status.account)
|
||||
|
||||
= render partial: 'admin/shared/status_content', locals: { status: status.proper, is_quote: is_quote }
|
||||
|
||||
- unless is_quote
|
||||
.detailed-status__meta
|
||||
- if status.application
|
||||
= status.application.name
|
||||
·
|
||||
= conditional_link_to can?(:show, status), admin_account_status_path(status.account.id, status), class: 'detailed-status__datetime' do
|
||||
%time.formatted{ datetime: status.created_at.iso8601, title: l(status.created_at) }><= l(status.created_at)
|
||||
- if status.edited?
|
||||
@@ -25,6 +38,9 @@
|
||||
- if status.discarded?
|
||||
·
|
||||
%span.negative-hint= t('admin.statuses.deleted')
|
||||
- if status.application
|
||||
·
|
||||
= status.application.name
|
||||
- unless status.reblog?
|
||||
·
|
||||
%span<
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
-# locals: (status:, is_quote: false)
|
||||
- if status.with_poll?
|
||||
.poll
|
||||
%ul
|
||||
@@ -23,3 +24,24 @@
|
||||
= render_audio_component(status)
|
||||
- else
|
||||
= render_media_gallery_component(status, visible: false)
|
||||
|
||||
- if status.quote
|
||||
- if status.quote.accepted? && status.quote.quoted_status.present?
|
||||
- if is_quote
|
||||
.status__quote-author-button
|
||||
%span= t('statuses.quote_post_author', acct: acct(status.account))
|
||||
- else
|
||||
.status__quote
|
||||
= render partial: 'admin/shared/status', object: status.quote.quoted_status, locals: { is_quote: true }
|
||||
- else
|
||||
.status__quote.status__quote--error
|
||||
- if status.quote.pending?
|
||||
%span= t('statuses.quote_error.pending_approval')
|
||||
- elsif status.quote.revoked?
|
||||
%span= t('statuses.quote_error.revoked')
|
||||
- else
|
||||
%span= t('statuses.quote_error.not_available')
|
||||
|
||||
- if status.quote.quoted_status.present? && can?(:show, status.quote.quoted_status)
|
||||
= link_to admin_account_status_path(status.quote.quoted_status.account.id, status.quote.quoted_status), class: 'link-button' do
|
||||
= t('admin.statuses.view_quoted_post')
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
.status__content><
|
||||
-# locals: (status:, is_quote: false)
|
||||
- if status.spoiler_text.present?
|
||||
%details<
|
||||
%summary{
|
||||
@@ -9,8 +9,10 @@
|
||||
}><
|
||||
%strong>
|
||||
= prerender_custom_emojis(h(status.spoiler_text), status.emojis)
|
||||
.status__content><
|
||||
= prerender_custom_emojis(status_content_format(status), status.emojis)
|
||||
= render partial: 'admin/shared/status_attachments', locals: { status: status.proper }
|
||||
= render partial: 'admin/shared/status_attachments', locals: { status: status.proper, is_quote: is_quote }
|
||||
- else
|
||||
.status__content><
|
||||
= prerender_custom_emojis(status_content_format(status), status.emojis)
|
||||
= render partial: 'admin/shared/status_attachments', locals: { status: status.proper }
|
||||
= render partial: 'admin/shared/status_attachments', locals: { status: status.proper, is_quote: is_quote }
|
||||
|
||||
@@ -45,6 +45,9 @@
|
||||
%tr
|
||||
%th= t('admin.statuses.reblogs')
|
||||
%td= friendly_number_to_human @status.reblogs_count
|
||||
%tr
|
||||
%th= t('admin.statuses.quotes')
|
||||
%td= friendly_number_to_human @status.quotes_count
|
||||
%tr
|
||||
%th= t('admin.statuses.favourites')
|
||||
%td= friendly_number_to_human @status.favourites_count
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
%tr
|
||||
%td
|
||||
%span{ title: session.user_agent }<
|
||||
= material_symbol session_device_icon(session), 'aria-label': session_device_icon(session)
|
||||
= material_symbol session_device_icon(session)
|
||||
|
||||
= t 'sessions.description',
|
||||
browser: t("sessions.browsers.#{session.browser}", default: session.browser.to_s),
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
- @verified_links.each do |field|
|
||||
%li
|
||||
%span.verified-badge
|
||||
= material_symbol 'check', class: 'verified-badge__mark'
|
||||
= material_symbol 'check', { class: 'verified-badge__mark' }
|
||||
%span= field.value
|
||||
|
||||
= simple_form_for @account, url: settings_verification_path, html: { class: 'form-section' } do |f|
|
||||
|
||||
@@ -905,6 +905,7 @@ en:
|
||||
no_status_selected: No posts were changed as none were selected
|
||||
open: Open post
|
||||
original_status: Original post
|
||||
quotes: Quotes
|
||||
reblogs: Reblogs
|
||||
replied_to_html: Replied to %{acct_link}
|
||||
status_changed: Post changed
|
||||
@@ -912,6 +913,7 @@ en:
|
||||
title: Account posts - @%{name}
|
||||
trending: Trending
|
||||
view_publicly: View publicly
|
||||
view_quoted_post: View quoted post
|
||||
visibility: Visibility
|
||||
with_media: With media
|
||||
strikes:
|
||||
@@ -1925,10 +1927,15 @@ en:
|
||||
limit: You have already pinned the maximum number of posts
|
||||
ownership: Someone else's post cannot be pinned
|
||||
reblog: A boost cannot be pinned
|
||||
quote_error:
|
||||
not_available: Post unavailable
|
||||
pending_approval: Post pending
|
||||
revoked: Post removed by author
|
||||
quote_policies:
|
||||
followers: Followers only
|
||||
nobody: Just me
|
||||
public: Anyone
|
||||
quote_post_author: Quoted a post by %{acct}
|
||||
title: '%{name}: "%{quote}"'
|
||||
visibilities:
|
||||
direct: Private mention
|
||||
|
||||
Reference in New Issue
Block a user