@@ -12,7 +12,7 @@ | |||
} | |||
h1 { | |||
font: 46px/52px -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif; | |||
font: 46px/52px 'Roboto', sans-serif; | |||
font-weight: 600; | |||
margin-bottom: 20px; | |||
color: $color4; | |||
@@ -1,16 +1,20 @@ | |||
.admin-wrapper { | |||
width: 100%; | |||
display: flex; | |||
justify-content: center; | |||
height: 100%; | |||
position: fixed; | |||
background: darken($color1, 2%); | |||
overflow-y: scroll; | |||
.sidebar-wrapper { | |||
flex: 1; | |||
height: 100%; | |||
background: $color1; | |||
display: flex; | |||
justify-content: flex-end; | |||
} | |||
.sidebar { | |||
width: 240px; | |||
position: fixed; | |||
left: 0; | |||
height: 100%; | |||
background: $color1; | |||
padding: 20px 0; | |||
.logo { | |||
display: block; | |||
@@ -21,6 +25,8 @@ | |||
ul { | |||
list-style: none; | |||
border-radius: 4px 0 0 4px; | |||
overflow: hidden; | |||
a { | |||
display: block; | |||
@@ -28,6 +34,7 @@ | |||
color: rgba($color5, 0.7); | |||
text-decoration: none; | |||
transition: all 200ms linear; | |||
border-radius: 4px 0 0 4px; | |||
i.fa { | |||
margin-right: 5px; | |||
@@ -40,27 +47,72 @@ | |||
} | |||
&.selected { | |||
color: $color5; | |||
background-color: $color4; | |||
background: darken($color1, 2%); | |||
border-radius: 4px 0 0 0; | |||
} | |||
} | |||
ul { | |||
background: darken($color1, 4%); | |||
border-radius: 0 0 0 4px; | |||
a { | |||
border: 0; | |||
&:hover { | |||
background-color: lighten($color4, 5%); | |||
&.selected { | |||
color: $color5; | |||
background-color: $color4; | |||
border-bottom: 0; | |||
border-radius: 0; | |||
&:hover { | |||
background-color: lighten($color4, 5%); | |||
} | |||
} | |||
} | |||
} | |||
} | |||
} | |||
.content-wrapper { | |||
flex: 2; | |||
} | |||
.content { | |||
margin-left: 240px; | |||
padding: 15px; | |||
max-width: 700px; | |||
padding: 20px 15px; | |||
padding-top: 60px; | |||
padding-left: 25px; | |||
h2 { | |||
color: $color2; | |||
font-size: 24px; | |||
line-height: 28px; | |||
font-weight: 400; | |||
margin-bottom: 40px; | |||
} | |||
p { | |||
font-size: 14px; | |||
line-height: 18px; | |||
color: $color2; | |||
margin-bottom: 20px; | |||
strong { | |||
color: $color5; | |||
font-weight: 500; | |||
} | |||
} | |||
} | |||
.simple_form { | |||
max-width: 400px; | |||
} | |||
} | |||
.filters { | |||
display: flex; | |||
margin-bottom: 20px; | |||
padding-left: 8px; | |||
.filter-subset { | |||
flex: 0 0 auto; | |||
@@ -115,6 +115,7 @@ body { | |||
width: 100%; | |||
height: 100%; | |||
padding: 0; | |||
background: $color1; | |||
} | |||
&.embed { | |||
@@ -129,6 +130,14 @@ body { | |||
} | |||
} | |||
&.admin { | |||
background: darken($color1, 4%); | |||
position: fixed; | |||
width: 100%; | |||
height: 100%; | |||
padding: 0; | |||
} | |||
@media screen and (max-width: 360px) { | |||
padding-bottom: 0; | |||
} | |||
@@ -7,18 +7,6 @@ code { | |||
max-width: 400px; | |||
padding: 20px; | |||
margin: 0 auto; | |||
p { | |||
font-size: 14px; | |||
line-height: 18px; | |||
color: $color2; | |||
margin-bottom: 20px; | |||
strong { | |||
color: $color5; | |||
font-weight: 500; | |||
} | |||
} | |||
} | |||
.simple_form { | |||
@@ -28,28 +16,35 @@ code { | |||
.hint { | |||
display: block; | |||
color: rgba($color5, 0.8); | |||
color: $color3; | |||
font-size: 12px; | |||
margin-top: 4px; | |||
} | |||
.label_input { | |||
display: flex; | |||
label { | |||
flex: 0 0 auto; | |||
width: 100px; | |||
} | |||
input { | |||
flex: 1 1 auto; | |||
} | |||
} | |||
.input.file, .input.select { | |||
padding: 15px 0; | |||
margin-bottom: 0; | |||
display: flex; | |||
label { | |||
font-family: inherit; | |||
font-size: 16px; | |||
color: $color5; | |||
width: 100px; | |||
display: block; | |||
flex: 0 0 auto; | |||
padding-top: 5px; | |||
} | |||
input[type=file], select { | |||
flex: 1 1 auto; | |||
} | |||
} | |||
.fields-group { | |||
@@ -64,6 +59,7 @@ code { | |||
font-size: 14px; | |||
color: white; | |||
display: block; | |||
width: auto; | |||
} | |||
label.checkbox { | |||
@@ -80,6 +76,7 @@ code { | |||
.hint { | |||
padding-left: 25px; | |||
margin-left: 0; | |||
} | |||
} | |||
@@ -116,13 +113,19 @@ code { | |||
} | |||
.input.field_with_errors { | |||
label { | |||
color: $color6; | |||
} | |||
input[type=text], input[type=email], input[type=password] { | |||
border-bottom-color: $color6; | |||
} | |||
.error { | |||
display: block; | |||
font-weight: 500; | |||
color: $color6; | |||
margin-top: 4px; | |||
} | |||
} | |||
@@ -2,6 +2,7 @@ | |||
class Auth::RegistrationsController < Devise::RegistrationsController | |||
layout 'auth' | |||
layout 'admin', only: [:edit] | |||
before_action :check_single_user_mode | |||
before_action :configure_sign_up_params, only: [:create] | |||
@@ -1,7 +1,7 @@ | |||
# frozen_string_literal: true | |||
class Settings::PreferencesController < ApplicationController | |||
layout 'auth' | |||
layout 'admin' | |||
before_action :authenticate_user! | |||
@@ -3,7 +3,7 @@ | |||
class Settings::ProfilesController < ApplicationController | |||
include ObfuscateFilename | |||
layout 'auth' | |||
layout 'admin' | |||
before_action :authenticate_user! | |||
before_action :set_account | |||
@@ -1,7 +1,7 @@ | |||
# frozen_string_literal: true | |||
class Settings::TwoFactorAuthsController < ApplicationController | |||
layout 'auth' | |||
layout 'admin' | |||
before_action :authenticate_user! | |||
@@ -54,8 +54,8 @@ | |||
- else | |||
%i.fa.fa-times | |||
%td | |||
= table_link_to 'circle', 'Open in web', web_path("accounts/#{account.id}") | |||
= table_link_to 'globe', 'Open public', TagManager.instance.url_for(account) | |||
= table_link_to 'circle', 'Web', web_path("accounts/#{account.id}") | |||
= table_link_to 'globe', 'Public', TagManager.instance.url_for(account) | |||
= table_link_to 'pencil', 'Edit', admin_account_path(account.id) | |||
= will_paginate @accounts, pagination_options |
@@ -1,3 +1,6 @@ | |||
- content_for :page_title do | |||
= @account.acct | |||
%table.table | |||
%tbody | |||
%tr | |||
@@ -11,5 +11,3 @@ | |||
.actions | |||
= f.button :button, t('generic.save_changes'), type: :submit | |||
.form-footer= render "settings/shared/links" |
@@ -1,14 +1,17 @@ | |||
- content_for :header_tags do | |||
= javascript_include_tag 'application_public' | |||
- content_for :content do | |||
.admin-wrapper | |||
.sidebar | |||
= link_to root_path do | |||
= image_tag 'logo.png', class: 'logo' | |||
.sidebar-wrapper | |||
.sidebar | |||
= link_to root_path do | |||
= image_tag 'logo.png', class: 'logo' | |||
= render_navigation | |||
.content | |||
= yield | |||
= render_navigation | |||
.content-wrapper | |||
.content | |||
%h2= yield :page_title | |||
= yield | |||
= render template: "layouts/application" | |||
= render template: "layouts/application", locals: { body_classes: 'admin' } |
@@ -20,5 +20,7 @@ | |||
= yield :header_tags | |||
%body{ class: @body_classes } | |||
- body_classes ||= @body_classes | |||
%body{ class: body_classes } | |||
= content_for?(:content) ? yield(:content) : yield |
@@ -4,14 +4,16 @@ | |||
= simple_form_for current_user, url: settings_preferences_path, html: { method: :put } do |f| | |||
= render 'shared/error_messages', object: current_user | |||
= f.input :locale, collection: I18n.available_locales, wrapper: :with_label, include_blank: false, label_method: lambda { |locale| human_locale(locale) } | |||
.fields-group | |||
= f.input :locale, collection: I18n.available_locales, wrapper: :with_label, include_blank: false, label_method: lambda { |locale| human_locale(locale) } | |||
= f.simple_fields_for :notification_emails, hash_to_object(current_user.settings.notification_emails) do |ff| | |||
= ff.input :follow, as: :boolean, wrapper: :with_label | |||
= ff.input :follow_request, as: :boolean, wrapper: :with_label | |||
= ff.input :reblog, as: :boolean, wrapper: :with_label | |||
= ff.input :favourite, as: :boolean, wrapper: :with_label | |||
= ff.input :mention, as: :boolean, wrapper: :with_label | |||
.fields-group | |||
= f.simple_fields_for :notification_emails, hash_to_object(current_user.settings.notification_emails) do |ff| | |||
= ff.input :follow, as: :boolean, wrapper: :with_label | |||
= ff.input :follow_request, as: :boolean, wrapper: :with_label | |||
= ff.input :reblog, as: :boolean, wrapper: :with_label | |||
= ff.input :favourite, as: :boolean, wrapper: :with_label | |||
= ff.input :mention, as: :boolean, wrapper: :with_label | |||
= f.simple_fields_for :interactions, hash_to_object(current_user.settings.interactions) do |ff| | |||
= ff.input :must_be_follower, as: :boolean, wrapper: :with_label | |||
@@ -19,5 +21,3 @@ | |||
.actions | |||
= f.button :button, t('generic.save_changes'), type: :submit | |||
.form-footer= render "settings/shared/links" |
@@ -7,12 +7,10 @@ | |||
.fields-group | |||
= f.input :display_name, placeholder: t('simple_form.labels.defaults.display_name') | |||
= f.input :note, placeholder: t('simple_form.labels.defaults.note') | |||
= f.input :avatar, wrapper: :with_label | |||
= f.input :header, wrapper: :with_label | |||
= f.input :avatar, wrapper: :with_label, hint: t('simple_form.hints.defaults.avatar') | |||
= f.input :header, wrapper: :with_label, hint: t('simple_form.hints.defaults.header') | |||
= f.input :locked, as: :boolean, wrapper: :with_label, hint: t('simple_form.hints.defaults.locked') | |||
.actions | |||
= f.button :button, t('generic.save_changes'), type: :submit | |||
.form-footer= render "settings/shared/links" |
@@ -1,17 +1,13 @@ | |||
- content_for :page_title do | |||
= t('settings.two_factor_auth') | |||
- if current_user.otp_required_for_login | |||
%p= t('two_factor_auth.instructions_html') | |||
.simple_form | |||
- if current_user.otp_required_for_login | |||
%p= t('two_factor_auth.instructions_html') | |||
.qr-code= raw @qrcode.as_svg(padding: 0, module_size: 5) | |||
.qr-code= raw @qrcode.as_svg(padding: 0, module_size: 5) | |||
.simple_form | |||
= link_to t('two_factor_auth.disable'), disable_settings_two_factor_auth_path, data: { method: 'POST' }, class: 'block-button' | |||
- else | |||
%p= t('two_factor_auth.description_html') | |||
.simple_form | |||
- else | |||
%p= t('two_factor_auth.description_html') | |||
= link_to t('two_factor_auth.enable'), enable_settings_two_factor_auth_path, data: { method: 'POST' }, class: 'block-button' | |||
.form-footer= render "settings/shared/links" |
@@ -46,6 +46,7 @@ module Mastodon | |||
config.to_prepare do | |||
Doorkeeper::AuthorizationsController.layout 'public' | |||
Doorkeeper::AuthorizedApplicationsController.layout 'admin' | |||
Doorkeeper::Application.send :include, ApplicationExtension | |||
end | |||
@@ -18,6 +18,7 @@ data: | |||
search: | |||
paths: | |||
- app/ | |||
- config/navigation.rb | |||
relative_roots: | |||
- app/controllers | |||
@@ -52,7 +52,7 @@ SimpleForm.setup do |config| | |||
config.wrappers :with_label, class: :input, hint_class: :field_with_hint, error_class: :field_with_errors do |b| | |||
b.use :html5 | |||
b.use :label_input | |||
b.use :label_input, wrap_with: { tag: :div, class: :label_input } | |||
b.use :hint, wrap_with: { tag: :span, class: :hint } | |||
b.use :error, wrap_with: { tag: :span, class: :error } | |||
end | |||
@@ -31,10 +31,11 @@ en: | |||
applications: | |||
invalid_url: The provided URL is invalid | |||
auth: | |||
change_password: Change password | |||
change_password: Credentials | |||
didnt_get_confirmation: Didn't receive confirmation instructions? | |||
forgot_password: Forgot your password? | |||
login: Log in | |||
logout: Logout | |||
register: Sign up | |||
resend_confirmation: Resend confirmation instructions | |||
reset_password: Reset password | |||
@@ -93,6 +94,7 @@ en: | |||
back: Back to Mastodon | |||
edit_profile: Edit profile | |||
preferences: Preferences | |||
settings: Settings | |||
two_factor_auth: Two-factor Authentication | |||
statuses: | |||
over_character_limit: character limit of %{max} exceeded | |||
@@ -3,7 +3,11 @@ en: | |||
simple_form: | |||
hints: | |||
defaults: | |||
avatar: PNG, GIF or JPG. At most 2MB. Will be downscaled to 120x120px | |||
display_name: At most 30 characters | |||
header: PNG, GIF or JPG. At most 2MB. Will be downscaled to 700x335px | |||
locked: Requires you to manually approve followers and defaults post privacy to followers-only | |||
note: At most 160 characters | |||
labels: | |||
defaults: | |||
avatar: Avatar | |||
@@ -2,11 +2,25 @@ | |||
SimpleNavigation::Configuration.run do |navigation| | |||
navigation.items do |primary| | |||
primary.item :accounts, safe_join([fa_icon('users fw'), 'Accounts']), admin_accounts_url | |||
primary.item :pubsubhubbubs, safe_join([fa_icon('paper-plane-o fw'), 'PubSubHubbub']), admin_pubsubhubbub_index_url | |||
primary.item :domain_blocks, safe_join([fa_icon('lock fw'), 'Domain Blocks']), admin_domain_blocks_url | |||
primary.item :sidekiq, safe_join([fa_icon('diamond fw'), 'Sidekiq']), sidekiq_url | |||
primary.item :pghero, safe_join([fa_icon('database fw'), 'PgHero']), pghero_url | |||
primary.item :settings, safe_join([fa_icon('cogs fw'), 'Site Settings']), admin_settings_url | |||
primary.item :web, safe_join([fa_icon('chevron-left fw'), t('settings.back')]), root_url | |||
primary.item :settings, safe_join([fa_icon('cog fw'), t('settings.settings')]), settings_profile_url do |settings| | |||
settings.item :profile, safe_join([fa_icon('user fw'), t('settings.edit_profile')]), settings_profile_url | |||
settings.item :preferences, safe_join([fa_icon('sliders fw'), t('settings.preferences')]), settings_preferences_url | |||
settings.item :password, safe_join([fa_icon('cog fw'), t('auth.change_password')]), edit_user_registration_url | |||
settings.item :two_factor_auth, safe_join([fa_icon('mobile fw'), t('settings.two_factor_auth')]), settings_two_factor_auth_url | |||
# settings.item :authorized_apps, safe_join([fa_icon('list fw'), 'Authorized Apps']), oauth_authorized_applications_url | |||
end | |||
primary.item :admin, safe_join([fa_icon('cogs fw'), 'Administration']), admin_accounts_url, if: proc { current_user.admin? } do |admin| | |||
admin.item :accounts, safe_join([fa_icon('users fw'), 'Accounts']), admin_accounts_url, highlights_on: %r{/admin/accounts} | |||
admin.item :pubsubhubbubs, safe_join([fa_icon('paper-plane-o fw'), 'PubSubHubbub']), admin_pubsubhubbub_index_url | |||
admin.item :domain_blocks, safe_join([fa_icon('lock fw'), 'Domain Blocks']), admin_domain_blocks_url | |||
admin.item :sidekiq, safe_join([fa_icon('diamond fw'), 'Sidekiq']), sidekiq_url | |||
admin.item :pghero, safe_join([fa_icon('database fw'), 'PgHero']), pghero_url | |||
admin.item :settings, safe_join([fa_icon('cogs fw'), 'Site Settings']), admin_settings_url | |||
end | |||
primary.item :logout, safe_join([fa_icon('sign-out fw'), t('auth.logout')]), destroy_user_session_url, link_html: { 'data-method' => 'delete' } | |||
end | |||
end |