Add a setting allowing the use of system's default font in Web UI (#4033)

* add a system_font_ui setting on the server

* Plug the system_font_ui on the front-end

* add EN/FR locales for the new setting

* put Roboto after all other fonts

* remove trailing whitespace so CodeClimate is happy

* fix user_spec.rb

* correctly write user_spect this time

* slightly better way of adding the classes

* add comments to the system-font stack for clarification

* use .system-font for the class instead

* don't use multiple lines for comments

* remove trailing whitespace

* use the classnames module for consistency

* use `mastodon-font-sans-serif` instead of Roboto directly
main
Damien Erambert 2017-07-06 13:39:56 -07:00 committed by Eugen Rochko
parent f76e71825d
commit 18d3fa953b
12 changed files with 57 additions and 2 deletions

View File

@ -37,6 +37,7 @@ class Settings::PreferencesController < ApplicationController
:setting_boost_modal, :setting_boost_modal,
:setting_delete_modal, :setting_delete_modal,
:setting_auto_play_gif, :setting_auto_play_gif,
:setting_system_font_ui,
notification_emails: %i(follow follow_request reblog favourite mention digest), notification_emails: %i(follow follow_request reblog favourite mention digest),
interactions: %i(must_be_follower must_be_following) interactions: %i(must_be_follower must_be_following)
) )

View File

@ -1,4 +1,5 @@
import React from 'react'; import React from 'react';
import classNames from 'classnames';
import Switch from 'react-router-dom/Switch'; import Switch from 'react-router-dom/Switch';
import Route from 'react-router-dom/Route'; import Route from 'react-router-dom/Route';
import Redirect from 'react-router-dom/Redirect'; import Redirect from 'react-router-dom/Redirect';
@ -72,12 +73,17 @@ class WrappedRoute extends React.Component {
} }
@connect() const mapStateToProps = state => ({
systemFontUi: state.getIn(['meta', 'system_font_ui']),
});
@connect(mapStateToProps)
export default class UI extends React.PureComponent { export default class UI extends React.PureComponent {
static propTypes = { static propTypes = {
dispatch: PropTypes.func.isRequired, dispatch: PropTypes.func.isRequired,
children: PropTypes.node, children: PropTypes.node,
systemFontUi: PropTypes.bool,
}; };
state = { state = {
@ -176,8 +182,12 @@ export default class UI extends React.PureComponent {
const { width, draggingOver } = this.state; const { width, draggingOver } = this.state;
const { children } = this.props; const { children } = this.props;
const className = classNames('ui', {
'system-font': this.props.systemFontUi,
});
return ( return (
<div className='ui' ref={this.setRef}> <div className={className} ref={this.setRef}>
<TabsBar /> <TabsBar />
<ColumnsAreaContainer singleColumn={isMobile(width)}> <ColumnsAreaContainer singleColumn={isMobile(width)}>
<WrappedSwitch> <WrappedSwitch>

View File

@ -63,3 +63,18 @@ button {
align-items: center; align-items: center;
justify-content: center; justify-content: center;
} }
.system-font {
// system-ui => standard property (Chrome/Android WebView 56+, Opera 43+, Safari 11+)
// -apple-system => Safari <11 specific
// BlinkMacSystemFont => Chrome <56 on macOS specific
// Segoe UI => Windows 7/8/10
// Oxygen => KDE
// Ubuntu => Unity/Ubuntu
// Cantarell => GNOME
// Fira Sans => Firefox OS
// Droid Sans => Older Androids (<4.0)
// Helvetica Neue => Older macOS <10.11
// mastodon-font-sans-serif => web-font (Roboto) fallback and newer Androids (>=4.0)
font-family: system-ui, -apple-system,BlinkMacSystemFont, "Segoe UI","Oxygen", "Ubuntu","Cantarell","Fira Sans","Droid Sans","Helvetica Neue",mastodon-font-sans-serif, sans-serif;
}

View File

@ -21,6 +21,7 @@ class UserSettingsDecorator
user.settings['boost_modal'] = boost_modal_preference user.settings['boost_modal'] = boost_modal_preference
user.settings['delete_modal'] = delete_modal_preference user.settings['delete_modal'] = delete_modal_preference
user.settings['auto_play_gif'] = auto_play_gif_preference user.settings['auto_play_gif'] = auto_play_gif_preference
user.settings['system_font_ui'] = system_font_ui_preference
end end
def merged_notification_emails def merged_notification_emails
@ -43,6 +44,10 @@ class UserSettingsDecorator
boolean_cast_setting 'setting_delete_modal' boolean_cast_setting 'setting_delete_modal'
end end
def system_font_ui_preference
boolean_cast_setting 'setting_system_font_ui'
end
def auto_play_gif_preference def auto_play_gif_preference
boolean_cast_setting 'setting_auto_play_gif' boolean_cast_setting 'setting_auto_play_gif'
end end

View File

@ -91,6 +91,10 @@ class User < ApplicationRecord
settings.auto_play_gif settings.auto_play_gif
end end
def setting_system_font_ui
settings.system_font_ui
end
def activate_session(request) def activate_session(request)
session_activations.activate(session_id: SecureRandom.hex, session_activations.activate(session_id: SecureRandom.hex,
user_agent: request.user_agent, user_agent: request.user_agent,

View File

@ -11,6 +11,7 @@ node(:meta) do
boost_modal: current_account.user.setting_boost_modal, boost_modal: current_account.user.setting_boost_modal,
delete_modal: current_account.user.setting_delete_modal, delete_modal: current_account.user.setting_delete_modal,
auto_play_gif: current_account.user.setting_auto_play_gif, auto_play_gif: current_account.user.setting_auto_play_gif,
system_font_ui: current_account.user.setting_system_font_ui,
} }
end end

View File

@ -44,6 +44,7 @@
.fields-group .fields-group
= f.input :setting_auto_play_gif, as: :boolean, wrapper: :with_label = f.input :setting_auto_play_gif, as: :boolean, wrapper: :with_label
= f.input :setting_system_font_ui, as: :boolean, wrapper: :with_label
.actions .actions
= f.button :button, t('generic.save_changes'), type: :submit = f.button :button, t('generic.save_changes'), type: :submit

View File

@ -38,6 +38,7 @@ en:
setting_boost_modal: Show confirmation dialog before boosting setting_boost_modal: Show confirmation dialog before boosting
setting_default_privacy: Post privacy setting_default_privacy: Post privacy
setting_delete_modal: Show confirmation dialog before deleting a toot setting_delete_modal: Show confirmation dialog before deleting a toot
setting_system_font_ui: Use system's default font
severity: Severity severity: Severity
type: Import type type: Import type
username: Username username: Username

View File

@ -28,6 +28,7 @@ fr:
password: Mot de passe password: Mot de passe
setting_boost_modal: Afficher un dialogue de confirmation avant de partager setting_boost_modal: Afficher un dialogue de confirmation avant de partager
setting_default_privacy: Confidentialité des statuts setting_default_privacy: Confidentialité des statuts
setting_system_font_ui: Utiliser la police par défaut du système
severity: Séverité severity: Séverité
type: Type d'import type: Type d'import
username: Identifiant username: Identifiant

View File

@ -19,6 +19,7 @@ defaults: &defaults
boost_modal: false boost_modal: false
auto_play_gif: true auto_play_gif: true
delete_modal: true delete_modal: true
system_font_ui: false
notification_emails: notification_emails:
follow: false follow: false
reblog: false reblog: false

View File

@ -48,5 +48,12 @@ describe UserSettingsDecorator do
settings.update(values) settings.update(values)
expect(user.settings['auto_play_gif']).to eq false expect(user.settings['auto_play_gif']).to eq false
end end
it 'updates the user settings value for system font in UI' do
values = { 'setting_system_font_ui' => '0' }
settings.update(values)
expect(user.settings['system_font_ui']).to eq false
end
end end
end end

View File

@ -185,6 +185,14 @@ RSpec.describe User, type: :model do
end end
end end
describe '#setting_system_font_ui' do
it 'returns system font ui setting' do
user = Fabricate(:user)
user.settings[:system_font_ui] = false
expect(user.setting_system_font_ui).to eq false
end
end
describe '#setting_boost_modal' do describe '#setting_boost_modal' do
it 'returns boost modal setting' do it 'returns boost modal setting' do
user = Fabricate(:user) user = Fabricate(:user)