Merge pull request #229 from glitch-soc/glitch-theme
Advanced Next-Level Flavours And Skins For Mastodon™
This commit is contained in:
		
						commit
						f0b37f92a9
					
				
					 387 changed files with 2930 additions and 936 deletions
				
			
		
							
								
								
									
										3
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										3
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							|  | @ -1,3 +0,0 @@ | |||
| [submodule "app/javascript/themes/mastodon-go"] | ||||
| 	path = app/javascript/themes/mastodon-go | ||||
| 	url = https://github.com/marrus-sh/mastodon-go | ||||
|  | @ -1,6 +1,7 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class AboutController < ApplicationController | ||||
|   before_action :set_pack | ||||
|   before_action :set_body_classes | ||||
|   before_action :set_instance_presenter, only: [:show, :more, :terms] | ||||
| 
 | ||||
|  | @ -21,6 +22,10 @@ class AboutController < ApplicationController | |||
| 
 | ||||
|   helper_method :new_user | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack action_name == 'show' ? 'about' : 'common' | ||||
|   end | ||||
| 
 | ||||
|   def set_instance_presenter | ||||
|     @instance_presenter = InstancePresenter.new | ||||
|   end | ||||
|  |  | |||
|  | @ -7,6 +7,7 @@ class AccountsController < ApplicationController | |||
|   def show | ||||
|     respond_to do |format| | ||||
|       format.html do | ||||
|         use_pack 'public' | ||||
|         @pinned_statuses = [] | ||||
| 
 | ||||
|         if current_account && @account.blocking?(current_account) | ||||
|  |  | |||
|  | @ -5,8 +5,13 @@ module Admin | |||
|     include Authorization | ||||
|     include AccountableConcern | ||||
| 
 | ||||
|     before_action :require_staff! | ||||
| 
 | ||||
|     layout 'admin' | ||||
| 
 | ||||
|     before_action :require_staff! | ||||
|     before_action :set_pack | ||||
| 
 | ||||
|     def set_pack | ||||
|       use_pack 'admin' | ||||
|     end | ||||
|   end | ||||
| end | ||||
|  |  | |||
|  | @ -12,8 +12,8 @@ class ApplicationController < ActionController::Base | |||
| 
 | ||||
|   helper_method :current_account | ||||
|   helper_method :current_session | ||||
|   helper_method :current_theme | ||||
|   helper_method :theme_data | ||||
|   helper_method :current_flavour | ||||
|   helper_method :current_skin | ||||
|   helper_method :single_user_mode? | ||||
| 
 | ||||
|   rescue_from ActionController::RoutingError, with: :not_found | ||||
|  | @ -54,6 +54,73 @@ class ApplicationController < ActionController::Base | |||
|     new_user_session_path | ||||
|   end | ||||
| 
 | ||||
|   def pack(data, pack_name, skin = 'default') | ||||
|     return nil unless pack?(data, pack_name) | ||||
|     pack_data = { | ||||
|       common: pack_name == 'common' ? nil : resolve_pack(data['name'] ? Themes.instance.flavour(current_flavour) : Themes.instance.core, 'common'), | ||||
|       flavour: data['name'], | ||||
|       pack: pack_name, | ||||
|       preload: nil, | ||||
|       skin: nil, | ||||
|     } | ||||
|     if data['pack'][pack_name].is_a?(Hash) | ||||
|       pack_data[:common] = nil if data['pack'][pack_name]['use_common'] == false | ||||
|       pack_data[:pack] = nil unless data['pack'][pack_name]['filename'] | ||||
|       if data['pack'][pack_name]['preload'] | ||||
|         pack_data[:preload] = [data['pack'][pack_name]['preload']] if data['pack'][pack_name]['preload'].is_a?(String) | ||||
|         pack_data[:preload] = data['pack'][pack_name]['preload'] if data['pack'][pack_name]['preload'].is_a?(Array) | ||||
|       end | ||||
|       if skin != 'default' && data['skin'][skin] | ||||
|         pack_data[:skin] = skin if data['skin'][skin].include?(pack_name) | ||||
|       else  #  default skin | ||||
|         pack_data[:skin] = 'default' if data['pack'][pack_name]['stylesheet'] | ||||
|       end | ||||
|     end | ||||
|     pack_data | ||||
|   end | ||||
| 
 | ||||
|   def pack?(data, pack_name) | ||||
|     if data['pack'].is_a?(Hash) && data['pack'].key?(pack_name) | ||||
|       return true if data['pack'][pack_name].is_a?(String) || data['pack'][pack_name].is_a?(Hash) | ||||
|     end | ||||
|     false | ||||
|   end | ||||
| 
 | ||||
|   def nil_pack(data, pack_name, skin = 'default') | ||||
|     { | ||||
|       common: pack_name == 'common' ? nil : resolve_pack(data['name'] ? Themes.instance.flavour(current_flavour) : Themes.instance.core, 'common', skin), | ||||
|       flavour: data['name'], | ||||
|       pack: nil, | ||||
|       preload: nil, | ||||
|       skin: nil, | ||||
|     } | ||||
|   end | ||||
| 
 | ||||
|   def resolve_pack(data, pack_name, skin = 'default') | ||||
|     result = pack(data, pack_name, skin) | ||||
|     unless result | ||||
|       if data['name'] && data.key?('fallback') | ||||
|         if data['fallback'].nil? | ||||
|           return nil_pack(data, pack_name, skin) | ||||
|         elsif data['fallback'].is_a?(String) && Themes.instance.flavour(data['fallback']) | ||||
|           return resolve_pack(Themes.instance.flavour(data['fallback']), pack_name, skin) | ||||
|         elsif data['fallback'].is_a?(Array) | ||||
|           data['fallback'].each do |fallback| | ||||
|             return resolve_pack(Themes.instance.flavour(fallback), pack_name, skin) if Themes.instance.flavour(fallback) | ||||
|           end | ||||
|         end | ||||
|         return nil_pack(data, pack_name, skin) | ||||
|       end | ||||
|       return data.key?('name') && data['name'] != Setting.default_settings['flavour'] ? resolve_pack(Themes.instance.flavour(Setting.default_settings['flavour']), pack_name, skin) : nil_pack(data, pack_name, skin) | ||||
|     end | ||||
|     result | ||||
|   end | ||||
| 
 | ||||
|   def use_pack(pack_name) | ||||
|     @core = resolve_pack(Themes.instance.core, pack_name) | ||||
|     @theme = resolve_pack(Themes.instance.flavour(current_flavour), pack_name, current_skin) | ||||
|   end | ||||
| 
 | ||||
|   protected | ||||
| 
 | ||||
|   def forbidden | ||||
|  | @ -84,13 +151,14 @@ class ApplicationController < ActionController::Base | |||
|     @current_session ||= SessionActivation.find_by(session_id: cookies.signed['_session_id']) | ||||
|   end | ||||
| 
 | ||||
|   def current_theme | ||||
|     return Setting.default_settings['theme'] unless Themes.instance.names.include? current_user&.setting_theme | ||||
|     current_user.setting_theme | ||||
|   def current_flavour | ||||
|     return Setting.default_settings['flavour'] unless Themes.instance.flavours.include? current_user&.setting_flavour | ||||
|     current_user.setting_flavour | ||||
|   end | ||||
| 
 | ||||
|   def theme_data | ||||
|     Themes.instance.get(current_theme) | ||||
|   def current_skin | ||||
|     return 'default' unless Themes.instance.skins_for(current_flavour).include? current_user&.setting_skin | ||||
|     current_user.setting_skin | ||||
|   end | ||||
| 
 | ||||
|   def cache_collection(raw, klass) | ||||
|  |  | |||
|  | @ -2,10 +2,17 @@ | |||
| 
 | ||||
| class Auth::ConfirmationsController < Devise::ConfirmationsController | ||||
|   layout 'auth' | ||||
|   before_action :set_pack | ||||
| 
 | ||||
|   def show | ||||
|     super do |user| | ||||
|       BootstrapTimelineWorker.perform_async(user.account_id) if user.errors.empty? | ||||
|     end | ||||
|   end | ||||
|    | ||||
|   private | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'auth' | ||||
|   end | ||||
| end | ||||
|  |  | |||
|  | @ -2,6 +2,7 @@ | |||
| 
 | ||||
| class Auth::PasswordsController < Devise::PasswordsController | ||||
|   before_action :check_validity_of_reset_password_token, only: :edit | ||||
|   before_action :set_pack | ||||
| 
 | ||||
|   layout 'auth' | ||||
| 
 | ||||
|  | @ -17,4 +18,8 @@ class Auth::PasswordsController < Devise::PasswordsController | |||
|   def reset_password_token_is_valid? | ||||
|     resource_class.with_reset_password_token(params[:reset_password_token]).present? | ||||
|   end | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'auth' | ||||
|   end | ||||
| end | ||||
|  |  | |||
|  | @ -5,6 +5,7 @@ class Auth::RegistrationsController < Devise::RegistrationsController | |||
| 
 | ||||
|   before_action :check_enabled_registrations, only: [:new, :create] | ||||
|   before_action :configure_sign_up_params, only: [:create] | ||||
|   before_action :set_pack | ||||
|   before_action :set_sessions, only: [:edit, :update] | ||||
|   before_action :set_instance_presenter, only: [:new, :create, :update] | ||||
| 
 | ||||
|  | @ -55,6 +56,10 @@ class Auth::RegistrationsController < Devise::RegistrationsController | |||
| 
 | ||||
|   private | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack %w(edit update).include?(action_name) ? 'admin' : 'auth' | ||||
|   end | ||||
| 
 | ||||
|   def set_instance_presenter | ||||
|     @instance_presenter = InstancePresenter.new | ||||
|   end | ||||
|  |  | |||
|  | @ -9,6 +9,7 @@ class Auth::SessionsController < Devise::SessionsController | |||
|   skip_before_action :check_suspension, only: [:destroy] | ||||
|   prepend_before_action :authenticate_with_two_factor, if: :two_factor_enabled?, only: [:create] | ||||
|   before_action :set_instance_presenter, only: [:new] | ||||
|   before_action :set_pack | ||||
| 
 | ||||
|   def create | ||||
|     super do |resource| | ||||
|  | @ -85,6 +86,10 @@ class Auth::SessionsController < Devise::SessionsController | |||
| 
 | ||||
|   private | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'auth' | ||||
|   end | ||||
| 
 | ||||
|   def set_instance_presenter | ||||
|     @instance_presenter = InstancePresenter.new | ||||
|   end | ||||
|  |  | |||
|  | @ -4,6 +4,7 @@ class AuthorizeFollowsController < ApplicationController | |||
|   layout 'modal' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_pack | ||||
| 
 | ||||
|   def show | ||||
|     @account = located_account || render(:error) | ||||
|  | @ -23,6 +24,10 @@ class AuthorizeFollowsController < ApplicationController | |||
| 
 | ||||
|   private | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'modal' | ||||
|   end | ||||
| 
 | ||||
|   def follow_attempt | ||||
|     FollowService.new.call(current_account, acct_without_prefix) | ||||
|   end | ||||
|  |  | |||
|  | @ -7,7 +7,9 @@ class FollowerAccountsController < ApplicationController | |||
|     @follows = Follow.where(target_account: @account).recent.page(params[:page]).per(FOLLOW_PER_PAGE).preload(:account) | ||||
| 
 | ||||
|     respond_to do |format| | ||||
|       format.html | ||||
|       format.html do | ||||
|         use_pack 'public' | ||||
|       end | ||||
| 
 | ||||
|       format.json do | ||||
|         render json: collection_presenter, | ||||
|  |  | |||
|  | @ -7,7 +7,9 @@ class FollowingAccountsController < ApplicationController | |||
|     @follows = Follow.where(account: @account).recent.page(params[:page]).per(FOLLOW_PER_PAGE).preload(:target_account) | ||||
| 
 | ||||
|     respond_to do |format| | ||||
|       format.html | ||||
|       format.html do | ||||
|         use_pack 'public' | ||||
|       end | ||||
| 
 | ||||
|       format.json do | ||||
|         render json: collection_presenter, | ||||
|  |  | |||
|  | @ -2,6 +2,7 @@ | |||
| 
 | ||||
| class HomeController < ApplicationController | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_pack | ||||
|   before_action :set_initial_state_json | ||||
| 
 | ||||
|   def index | ||||
|  | @ -37,6 +38,10 @@ class HomeController < ApplicationController | |||
|     redirect_to(default_redirect_path) | ||||
|   end | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'home' | ||||
|   end | ||||
| 
 | ||||
|   def set_initial_state_json | ||||
|     serializable_resource = ActiveModelSerializers::SerializableResource.new(InitialStatePresenter.new(initial_state_params), serializer: InitialStateSerializer) | ||||
|     @initial_state_json   = serializable_resource.to_json | ||||
|  |  | |||
|  | @ -4,6 +4,7 @@ class RemoteFollowController < ApplicationController | |||
|   layout 'modal' | ||||
| 
 | ||||
|   before_action :set_account | ||||
|   before_action :set_pack | ||||
|   before_action :gone, if: :suspended_account? | ||||
| 
 | ||||
|   def new | ||||
|  | @ -31,6 +32,10 @@ class RemoteFollowController < ApplicationController | |||
|     { acct: session[:remote_follow] } | ||||
|   end | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'modal' | ||||
|   end | ||||
| 
 | ||||
|   def set_account | ||||
|     @account = Account.find_local!(params[:account_username]) | ||||
|   end | ||||
|  |  | |||
|  | @ -1,9 +1,7 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::ApplicationsController < ApplicationController | ||||
|   layout 'admin' | ||||
| class Settings::ApplicationsController < Settings::BaseController | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_application, only: [:show, :update, :destroy, :regenerate] | ||||
|   before_action :prepare_scopes, only: [:create, :update] | ||||
| 
 | ||||
|  |  | |||
							
								
								
									
										12
									
								
								app/controllers/settings/base_controller.rb
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										12
									
								
								app/controllers/settings/base_controller.rb
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,12 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::BaseController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_pack | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'settings' | ||||
|   end | ||||
| end | ||||
|  | @ -1,10 +1,8 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::DeletesController < ApplicationController | ||||
|   layout 'admin' | ||||
| class Settings::DeletesController < Settings::BaseController | ||||
| 
 | ||||
|   before_action :check_enabled_deletion | ||||
|   before_action :authenticate_user! | ||||
|   prepend_before_action :check_enabled_deletion | ||||
| 
 | ||||
|   def show | ||||
|     @confirmation = Form::DeleteConfirmation.new | ||||
|  |  | |||
|  | @ -1,10 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::ExportsController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| 
 | ||||
| class Settings::ExportsController < Settings::BaseController | ||||
|   def show | ||||
|     @export = Export.new(current_account) | ||||
|   end | ||||
|  |  | |||
|  | @ -2,11 +2,7 @@ | |||
| 
 | ||||
| require 'sidekiq-bulk' | ||||
| 
 | ||||
| class Settings::FollowerDomainsController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| 
 | ||||
| class Settings::FollowerDomainsController < Settings::BaseController | ||||
|   def show | ||||
|     @account = current_account | ||||
|     @domains = current_account.followers.reorder('MIN(follows.id) DESC').group('accounts.domain').select('accounts.domain, count(accounts.id) as accounts_from_domain').page(params[:page]).per(10) | ||||
|  |  | |||
|  | @ -1,9 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::ImportsController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| class Settings::ImportsController < Settings::BaseController | ||||
|   before_action :set_account | ||||
| 
 | ||||
|   def show | ||||
|  |  | |||
|  | @ -1,9 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::KeywordMutesController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| class Settings::KeywordMutesController < Settings::BaseController | ||||
|   before_action :load_keyword_mute, only: [:edit, :update, :destroy] | ||||
| 
 | ||||
|   def index | ||||
|  |  | |||
|  | @ -1,10 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::NotificationsController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| 
 | ||||
| class Settings::NotificationsController < Settings::BaseController | ||||
|   def show; end | ||||
| 
 | ||||
|   def update | ||||
|  |  | |||
|  | @ -1,10 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::PreferencesController < ApplicationController | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
| 
 | ||||
| class Settings::PreferencesController < Settings::BaseController | ||||
|   def show; end | ||||
| 
 | ||||
|   def update | ||||
|  | @ -42,7 +38,8 @@ class Settings::PreferencesController < ApplicationController | |||
|       :setting_reduce_motion, | ||||
|       :setting_system_font_ui, | ||||
|       :setting_noindex, | ||||
|       :setting_theme, | ||||
|       :setting_flavour, | ||||
|       :setting_skin, | ||||
|       notification_emails: %i(follow follow_request reblog favourite mention digest), | ||||
|       interactions: %i(must_be_follower must_be_following) | ||||
|     ) | ||||
|  |  | |||
|  | @ -1,11 +1,8 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| class Settings::ProfilesController < ApplicationController | ||||
| class Settings::ProfilesController < Settings::BaseController | ||||
|   include ObfuscateFilename | ||||
| 
 | ||||
|   layout 'admin' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_account | ||||
| 
 | ||||
|   obfuscate_filename [:account, :avatar] | ||||
|  |  | |||
|  | @ -1,5 +1,6 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| #  Intentionally does not inherit from BaseController | ||||
| class Settings::SessionsController < ApplicationController | ||||
|   before_action :set_session, only: :destroy | ||||
| 
 | ||||
|  |  | |||
|  | @ -1,10 +1,7 @@ | |||
| # frozen_string_literal: true | ||||
| 
 | ||||
| module Settings | ||||
|   class TwoFactorAuthenticationsController < ApplicationController | ||||
|     layout 'admin' | ||||
| 
 | ||||
|     before_action :authenticate_user! | ||||
|   class TwoFactorAuthenticationsController < BaseController | ||||
|     before_action :verify_otp_required, only: [:create] | ||||
| 
 | ||||
|     def show | ||||
|  |  | |||
|  | @ -4,6 +4,7 @@ class SharesController < ApplicationController | |||
|   layout 'modal' | ||||
| 
 | ||||
|   before_action :authenticate_user! | ||||
|   before_action :set_pack | ||||
|   before_action :set_body_classes | ||||
| 
 | ||||
|   def show | ||||
|  | @ -24,6 +25,10 @@ class SharesController < ApplicationController | |||
|     } | ||||
|   end | ||||
| 
 | ||||
|   def set_pack | ||||
|     use_pack 'share' | ||||
|   end | ||||
| 
 | ||||
|   def set_body_classes | ||||
|     @body_classes = 'compose-standalone' | ||||
|   end | ||||
|  |  | |||
|  | @ -14,6 +14,7 @@ class StatusesController < ApplicationController | |||
|   def show | ||||
|     respond_to do |format| | ||||
|       format.html do | ||||
|         use_pack 'public' | ||||
|         @ancestors   = @status.reply? ? cache_collection(@status.ancestors(current_account), Status) : [] | ||||
|         @descendants = cache_collection(@status.descendants(current_account), Status) | ||||
| 
 | ||||
|  | @ -37,6 +38,7 @@ class StatusesController < ApplicationController | |||
|   end | ||||
| 
 | ||||
|   def embed | ||||
|     use_pack 'embed' | ||||
|     response.headers['X-Frame-Options'] = 'ALLOWALL' | ||||
|     render 'stream_entries/embed', layout: 'embedded' | ||||
|   end | ||||
|  |  | |||
|  | @ -14,6 +14,7 @@ class StreamEntriesController < ApplicationController | |||
|   def show | ||||
|     respond_to do |format| | ||||
|       format.html do | ||||
|         use_pack 'public' | ||||
|         @ancestors   = @stream_entry.activity.reply? ? cache_collection(@stream_entry.activity.ancestors(current_account), Status) : [] | ||||
|         @descendants = cache_collection(@stream_entry.activity.descendants(current_account), Status) | ||||
|       end | ||||
|  |  | |||
|  | @ -9,6 +9,7 @@ class TagsController < ApplicationController | |||
| 
 | ||||
|     respond_to do |format| | ||||
|       format.html do | ||||
|         use_pack 'about' | ||||
|         serializable_resource = ActiveModelSerializers::SerializableResource.new(InitialStatePresenter.new(initial_state_params), serializer: InitialStateSerializer) | ||||
|         @initial_state_json   = serializable_resource.to_json | ||||
|       end | ||||
|  |  | |||
|  | @ -1,3 +1,5 @@ | |||
| //  This file will be loaded on admin pages, regardless of theme.
 | ||||
| 
 | ||||
| import { delegate } from 'rails-ujs'; | ||||
| 
 | ||||
| function handleDeleteStatus(event) { | ||||
							
								
								
									
										8
									
								
								app/javascript/core/common.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										8
									
								
								app/javascript/core/common.js
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,8 @@ | |||
| //  This file will be loaded on all pages, regardless of theme.
 | ||||
| 
 | ||||
| import { start } from 'rails-ujs'; | ||||
| import 'font-awesome/css/font-awesome.css'; | ||||
| 
 | ||||
| require.context('../images/', true); | ||||
| 
 | ||||
| start(); | ||||
							
								
								
									
										23
									
								
								app/javascript/core/embed.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										23
									
								
								app/javascript/core/embed.js
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,23 @@ | |||
| //  This file will be loaded on embed pages, regardless of theme.
 | ||||
| 
 | ||||
| window.addEventListener('message', e => { | ||||
|   const data = e.data || {}; | ||||
| 
 | ||||
|   if (!window.parent || data.type !== 'setHeight') { | ||||
|     return; | ||||
|   } | ||||
| 
 | ||||
|   function setEmbedHeight () { | ||||
|     window.parent.postMessage({ | ||||
|       type: 'setHeight', | ||||
|       id: data.id, | ||||
|       height: document.getElementsByTagName('html')[0].scrollHeight, | ||||
|     }, '*'); | ||||
|   }; | ||||
| 
 | ||||
|   if (['interactive', 'complete'].includes(document.readyState)) { | ||||
|     setEmbedHeight(); | ||||
|   } else { | ||||
|     document.addEventListener('DOMContentLoaded', setEmbedHeight); | ||||
|   } | ||||
| }); | ||||
							
								
								
									
										25
									
								
								app/javascript/core/public.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								app/javascript/core/public.js
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,25 @@ | |||
| //  This file will be loaded on public pages, regardless of theme.
 | ||||
| 
 | ||||
| const { delegate } = require('rails-ujs'); | ||||
| 
 | ||||
| delegate(document, '.webapp-btn', 'click', ({ target, button }) => { | ||||
|   if (button !== 0) { | ||||
|     return true; | ||||
|   } | ||||
|   window.location.href = target.href; | ||||
|   return false; | ||||
| }); | ||||
| 
 | ||||
| delegate(document, '.status__content__spoiler-link', 'click', ({ target }) => { | ||||
|   const contentEl = target.parentNode.parentNode.querySelector('.e-content'); | ||||
| 
 | ||||
|   if (contentEl.style.display === 'block') { | ||||
|     contentEl.style.display = 'none'; | ||||
|     target.parentNode.style.marginBottom = 0; | ||||
|   } else { | ||||
|     contentEl.style.display = 'block'; | ||||
|     target.parentNode.style.marginBottom = null; | ||||
|   } | ||||
| 
 | ||||
|   return false; | ||||
| }); | ||||
							
								
								
									
										43
									
								
								app/javascript/core/settings.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										43
									
								
								app/javascript/core/settings.js
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,43 @@ | |||
| //  This file will be loaded on settings pages, regardless of theme.
 | ||||
| 
 | ||||
| const { length } = require('stringz'); | ||||
| const { delegate } = require('rails-ujs'); | ||||
| 
 | ||||
| import { processBio } from 'flavours/glitch/util/bio_metadata'; | ||||
| 
 | ||||
| delegate(document, '.account_display_name', 'input', ({ target }) => { | ||||
|   const nameCounter = document.querySelector('.name-counter'); | ||||
| 
 | ||||
|   if (nameCounter) { | ||||
|     nameCounter.textContent = 30 - length(target.value); | ||||
|   } | ||||
| }); | ||||
| 
 | ||||
| delegate(document, '.account_note', 'input', ({ target }) => { | ||||
|   const noteCounter = document.querySelector('.note-counter'); | ||||
| 
 | ||||
|   if (noteCounter) { | ||||
|     const noteWithoutMetadata = processBio(target.value).text; | ||||
|     noteCounter.textContent = 500 - length(noteWithoutMetadata); | ||||
|   } | ||||
| }); | ||||
| 
 | ||||
| delegate(document, '#account_avatar', 'change', ({ target }) => { | ||||
|   const avatar = document.querySelector('.card.compact .avatar img'); | ||||
|   const [file] = target.files || []; | ||||
|   const url = file ? URL.createObjectURL(file) : avatar.dataset.originalSrc; | ||||
| 
 | ||||
|   avatar.src = url; | ||||
| }); | ||||
| 
 | ||||
| delegate(document, '#account_header', 'change', ({ target }) => { | ||||
|   const header = document.querySelector('.card.compact'); | ||||
|   const [file] = target.files || []; | ||||
|   const url = file ? URL.createObjectURL(file) : header.dataset.originalSrc; | ||||
| 
 | ||||
|   header.style.backgroundImage = `url(${url})`; | ||||
| }); | ||||
| 
 | ||||
| delegate(document, '#user_setting_flavour, #user_setting_skin', 'change', ({ target }) => { | ||||
|   target.form.submit(); | ||||
| }); | ||||
							
								
								
									
										16
									
								
								app/javascript/core/theme.yml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										16
									
								
								app/javascript/core/theme.yml
									
									
									
									
									
										Normal file
									
								
							|  | @ -0,0 +1,16 @@ | |||
| #  These packs will be loaded on every appropriate page, regardless of | ||||
| #  theme. | ||||
| pack: | ||||
|   about: | ||||
|   admin: admin.js | ||||
|   auth: | ||||
|   common: | ||||
|     filename: common.js | ||||
|     stylesheet: true | ||||
|   embed: embed.js | ||||
|   error: | ||||
|   home: | ||||
|   modal: | ||||
|   public: public.js | ||||
|   settings: settings.js | ||||
|   share: | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const ACCOUNT_FETCH_REQUEST = 'ACCOUNT_FETCH_REQUEST'; | ||||
| export const ACCOUNT_FETCH_SUCCESS = 'ACCOUNT_FETCH_SUCCESS'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| import { fetchRelationships } from './accounts'; | ||||
| 
 | ||||
| export const BLOCKS_FETCH_REQUEST = 'BLOCKS_FETCH_REQUEST'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const STATUS_CARD_FETCH_REQUEST = 'STATUS_CARD_FETCH_REQUEST'; | ||||
| export const STATUS_CARD_FETCH_SUCCESS = 'STATUS_CARD_FETCH_SUCCESS'; | ||||
|  | @ -1,6 +1,6 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| import { throttle } from 'lodash'; | ||||
| import { search as emojiSearch } from 'themes/glitch/util/emoji/emoji_mart_search_light'; | ||||
| import { search as emojiSearch } from 'flavours/glitch/util/emoji/emoji_mart_search_light'; | ||||
| import { useEmoji } from './emojis'; | ||||
| 
 | ||||
| import { | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const DOMAIN_BLOCK_REQUEST = 'DOMAIN_BLOCK_REQUEST'; | ||||
| export const DOMAIN_BLOCK_SUCCESS = 'DOMAIN_BLOCK_SUCCESS'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const FAVOURITED_STATUSES_FETCH_REQUEST = 'FAVOURITED_STATUSES_FETCH_REQUEST'; | ||||
| export const FAVOURITED_STATUSES_FETCH_SUCCESS = 'FAVOURITED_STATUSES_FETCH_SUCCESS'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const REBLOG_REQUEST = 'REBLOG_REQUEST'; | ||||
| export const REBLOG_SUCCESS = 'REBLOG_SUCCESS'; | ||||
|  | @ -1,6 +1,6 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| import { fetchRelationships } from './accounts'; | ||||
| import { openModal } from 'themes/glitch/actions/modal'; | ||||
| import { openModal } from 'flavours/glitch/actions/modal'; | ||||
| 
 | ||||
| export const MUTES_FETCH_REQUEST = 'MUTES_FETCH_REQUEST'; | ||||
| export const MUTES_FETCH_SUCCESS = 'MUTES_FETCH_SUCCESS'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| import { List as ImmutableList } from 'immutable'; | ||||
| import IntlMessageFormat from 'intl-messageformat'; | ||||
| import { fetchRelationships } from './accounts'; | ||||
|  | @ -1,10 +1,10 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const PINNED_STATUSES_FETCH_REQUEST = 'PINNED_STATUSES_FETCH_REQUEST'; | ||||
| export const PINNED_STATUSES_FETCH_SUCCESS = 'PINNED_STATUSES_FETCH_SUCCESS'; | ||||
| export const PINNED_STATUSES_FETCH_FAIL = 'PINNED_STATUSES_FETCH_FAIL'; | ||||
| 
 | ||||
| import { me } from 'themes/glitch/util/initial_state'; | ||||
| import { me } from 'flavours/glitch/util/initial_state'; | ||||
| 
 | ||||
| export function fetchPinnedStatuses() { | ||||
|   return (dispatch, getState) => { | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| import { openModal, closeModal } from './modal'; | ||||
| 
 | ||||
| export const REPORT_INIT   = 'REPORT_INIT'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| export const SEARCH_CHANGE = 'SEARCH_CHANGE'; | ||||
| export const SEARCH_CLEAR  = 'SEARCH_CLEAR'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api from 'themes/glitch/util/api'; | ||||
| import api from 'flavours/glitch/util/api'; | ||||
| 
 | ||||
| import { deleteFromTimelines } from './timelines'; | ||||
| import { fetchStatusCard } from './cards'; | ||||
|  | @ -1,4 +1,4 @@ | |||
| import { connectStream } from 'themes/glitch/util/stream'; | ||||
| import { connectStream } from 'flavours/glitch/util/stream'; | ||||
| import { | ||||
|   updateTimeline, | ||||
|   deleteFromTimelines, | ||||
|  | @ -1,4 +1,4 @@ | |||
| import api, { getLinks } from 'themes/glitch/util/api'; | ||||
| import api, { getLinks } from 'flavours/glitch/util/api'; | ||||
| import { Map as ImmutableMap, List as ImmutableList } from 'immutable'; | ||||
| 
 | ||||
| export const TIMELINE_UPDATE  = 'TIMELINE_UPDATE'; | ||||
|  | @ -7,7 +7,7 @@ import Permalink from './permalink'; | |||
| import IconButton from './icon_button'; | ||||
| import { defineMessages, injectIntl } from 'react-intl'; | ||||
| import ImmutablePureComponent from 'react-immutable-pure-component'; | ||||
| import { me } from 'themes/glitch/util/initial_state'; | ||||
| import { me } from 'flavours/glitch/util/initial_state'; | ||||
| 
 | ||||
| const messages = defineMessages({ | ||||
|   follow: { id: 'account.follow', defaultMessage: 'Follow' }, | ||||
|  | @ -1,6 +1,6 @@ | |||
| import React from 'react'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import unicodeMapping from 'themes/glitch/util/emoji/emoji_unicode_mapping_light'; | ||||
| import unicodeMapping from 'flavours/glitch/util/emoji/emoji_unicode_mapping_light'; | ||||
| 
 | ||||
| const assetHost = process.env.CDN_HOST || ''; | ||||
| 
 | ||||
|  | @ -1,9 +1,9 @@ | |||
| import React from 'react'; | ||||
| import AutosuggestAccountContainer from 'themes/glitch/features/compose/containers/autosuggest_account_container'; | ||||
| import AutosuggestAccountContainer from 'flavours/glitch/features/compose/containers/autosuggest_account_container'; | ||||
| import AutosuggestEmoji from './autosuggest_emoji'; | ||||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import { isRtl } from 'themes/glitch/util/rtl'; | ||||
| import { isRtl } from 'flavours/glitch/util/rtl'; | ||||
| import ImmutablePureComponent from 'react-immutable-pure-component'; | ||||
| import Textarea from 'react-textarea-autosize'; | ||||
| import classNames from 'classnames'; | ||||
|  | @ -1,5 +1,5 @@ | |||
| import React from 'react'; | ||||
| import Motion from 'themes/glitch/util/optional_motion'; | ||||
| import Motion from 'flavours/glitch/util/optional_motion'; | ||||
| import spring from 'react-motion/lib/spring'; | ||||
| import PropTypes from 'prop-types'; | ||||
| 
 | ||||
|  | @ -1,7 +1,7 @@ | |||
| import React from 'react'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import detectPassiveEvents from 'detect-passive-events'; | ||||
| import { scrollTop } from 'themes/glitch/util/scroll'; | ||||
| import { scrollTop } from 'flavours/glitch/util/scroll'; | ||||
| 
 | ||||
| export default class Column extends React.PureComponent { | ||||
| 
 | ||||
|  | @ -4,8 +4,7 @@ import classNames from 'classnames'; | |||
| import { defineMessages, FormattedMessage, injectIntl } from 'react-intl'; | ||||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| 
 | ||||
| // Glitch imports
 | ||||
| import NotificationPurgeButtonsContainer from 'themes/glitch/containers/notification_purge_buttons_container'; | ||||
| import NotificationPurgeButtonsContainer from 'flavours/glitch/containers/notification_purge_buttons_container'; | ||||
| 
 | ||||
| const messages = defineMessages({ | ||||
|   show: { id: 'column_header.show_settings', defaultMessage: 'Show settings' }, | ||||
|  | @ -3,7 +3,7 @@ import PropTypes from 'prop-types'; | |||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| import IconButton from './icon_button'; | ||||
| import Overlay from 'react-overlays/lib/Overlay'; | ||||
| import Motion from 'themes/glitch/util/optional_motion'; | ||||
| import Motion from 'flavours/glitch/util/optional_motion'; | ||||
| import spring from 'react-motion/lib/spring'; | ||||
| import detectPassiveEvents from 'detect-passive-events'; | ||||
| 
 | ||||
|  | @ -1,5 +1,5 @@ | |||
| import React from 'react'; | ||||
| import Motion from 'themes/glitch/util/optional_motion'; | ||||
| import Motion from 'flavours/glitch/util/optional_motion'; | ||||
| import spring from 'react-motion/lib/spring'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import classNames from 'classnames'; | ||||
|  | @ -1,7 +1,7 @@ | |||
| import React from 'react'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import scheduleIdleTask from 'themes/glitch/util/schedule_idle_task'; | ||||
| import getRectFromEntry from 'themes/glitch/util/get_rect_from_entry'; | ||||
| import scheduleIdleTask from 'flavours/glitch/util/schedule_idle_task'; | ||||
| import getRectFromEntry from 'flavours/glitch/util/get_rect_from_entry'; | ||||
| import { is } from 'immutable'; | ||||
| 
 | ||||
| // Diff these props in the "rendered" state
 | ||||
|  | @ -4,9 +4,9 @@ import PropTypes from 'prop-types'; | |||
| import { is } from 'immutable'; | ||||
| import IconButton from './icon_button'; | ||||
| import { defineMessages, injectIntl, FormattedMessage } from 'react-intl'; | ||||
| import { isIOS } from 'themes/glitch/util/is_mobile'; | ||||
| import { isIOS } from 'flavours/glitch/util/is_mobile'; | ||||
| import classNames from 'classnames'; | ||||
| import { autoPlayGif } from 'themes/glitch/util/initial_state'; | ||||
| import { autoPlayGif } from 'flavours/glitch/util/initial_state'; | ||||
| 
 | ||||
| const messages = defineMessages({ | ||||
|   toggle_visible: { id: 'media_gallery.toggle_visible', defaultMessage: 'Toggle visibility' }, | ||||
|  | @ -1,13 +1,13 @@ | |||
| import React, { PureComponent } from 'react'; | ||||
| import { ScrollContainer } from 'react-router-scroll-4'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import IntersectionObserverArticleContainer from 'themes/glitch/containers/intersection_observer_article_container'; | ||||
| import IntersectionObserverArticleContainer from 'flavours/glitch/containers/intersection_observer_article_container'; | ||||
| import LoadMore from './load_more'; | ||||
| import IntersectionObserverWrapper from 'themes/glitch/util/intersection_observer_wrapper'; | ||||
| import IntersectionObserverWrapper from 'flavours/glitch/util/intersection_observer_wrapper'; | ||||
| import { throttle } from 'lodash'; | ||||
| import { List as ImmutableList } from 'immutable'; | ||||
| import classNames from 'classnames'; | ||||
| import { attachFullscreenListener, detachFullscreenListener, isFullscreen } from 'themes/glitch/util/fullscreen'; | ||||
| import { attachFullscreenListener, detachFullscreenListener, isFullscreen } from 'flavours/glitch/util/fullscreen'; | ||||
| 
 | ||||
| export default class ScrollableList extends PureComponent { | ||||
| 
 | ||||
|  | @ -6,9 +6,9 @@ import StatusHeader from './status_header'; | |||
| import StatusContent from './status_content'; | ||||
| import StatusActionBar from './status_action_bar'; | ||||
| import ImmutablePureComponent from 'react-immutable-pure-component'; | ||||
| import { MediaGallery, Video } from 'themes/glitch/util/async-components'; | ||||
| import { MediaGallery, Video } from 'flavours/glitch/util/async-components'; | ||||
| import { HotKeys } from 'react-hotkeys'; | ||||
| import NotificationOverlayContainer from 'themes/glitch/features/notifications/containers/overlay_container'; | ||||
| import NotificationOverlayContainer from 'flavours/glitch/features/notifications/containers/overlay_container'; | ||||
| import classNames from 'classnames'; | ||||
| 
 | ||||
| // We use the component (and not the container) since we do not want
 | ||||
|  | @ -1,14 +1,11 @@ | |||
| //  THIS FILE EXISTS FOR UPSTREAM COMPATIBILITY & SHOULDN'T BE USED !!
 | ||||
| //  SEE INSTEAD : glitch/components/status/action_bar
 | ||||
| 
 | ||||
| import React from 'react'; | ||||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import IconButton from './icon_button'; | ||||
| import DropdownMenuContainer from 'themes/glitch/containers/dropdown_menu_container'; | ||||
| import DropdownMenuContainer from 'flavours/glitch/containers/dropdown_menu_container'; | ||||
| import { defineMessages, injectIntl } from 'react-intl'; | ||||
| import ImmutablePureComponent from 'react-immutable-pure-component'; | ||||
| import { me } from 'themes/glitch/util/initial_state'; | ||||
| import { me } from 'flavours/glitch/util/initial_state'; | ||||
| import RelativeTimestamp from './relative_timestamp'; | ||||
| 
 | ||||
| const messages = defineMessages({ | ||||
|  | @ -1,7 +1,7 @@ | |||
| import React from 'react'; | ||||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import { isRtl } from 'themes/glitch/util/rtl'; | ||||
| import { isRtl } from 'flavours/glitch/util/rtl'; | ||||
| import { FormattedMessage } from 'react-intl'; | ||||
| import Permalink from './permalink'; | ||||
| import classnames from 'classnames'; | ||||
|  | @ -1,7 +1,7 @@ | |||
| import React from 'react'; | ||||
| import ImmutablePropTypes from 'react-immutable-proptypes'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import StatusContainer from 'themes/glitch/containers/status_container'; | ||||
| import StatusContainer from 'flavours/glitch/containers/status_container'; | ||||
| import ImmutablePureComponent from 'react-immutable-pure-component'; | ||||
| import ScrollableList from './scrollable_list'; | ||||
| 
 | ||||
|  | @ -1,8 +1,8 @@ | |||
| import React from 'react'; | ||||
| import { connect } from 'react-redux'; | ||||
| import { defineMessages, injectIntl, FormattedMessage } from 'react-intl'; | ||||
| import { makeGetAccount } from 'themes/glitch/selectors'; | ||||
| import Account from 'themes/glitch/components/account'; | ||||
| import { makeGetAccount } from 'flavours/glitch/selectors'; | ||||
| import Account from 'flavours/glitch/components/account'; | ||||
| import { | ||||
|   followAccount, | ||||
|   unfollowAccount, | ||||
|  | @ -10,10 +10,10 @@ import { | |||
|   unblockAccount, | ||||
|   muteAccount, | ||||
|   unmuteAccount, | ||||
| } from 'themes/glitch/actions/accounts'; | ||||
| import { openModal } from 'themes/glitch/actions/modal'; | ||||
| import { initMuteModal } from 'themes/glitch/actions/mutes'; | ||||
| import { unfollowModal } from 'themes/glitch/util/initial_state'; | ||||
| } from 'flavours/glitch/actions/accounts'; | ||||
| import { openModal } from 'flavours/glitch/actions/modal'; | ||||
| import { initMuteModal } from 'flavours/glitch/actions/mutes'; | ||||
| import { unfollowModal } from 'flavours/glitch/util/initial_state'; | ||||
| 
 | ||||
| const messages = defineMessages({ | ||||
|   unfollowConfirm: { id: 'confirmations.unfollow.confirm', defaultMessage: 'Unfollow' }, | ||||
|  | @ -1,6 +1,6 @@ | |||
| import React from 'react'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import Card from 'themes/glitch/features/status/components/card'; | ||||
| import Card from 'flavours/glitch/features/status/components/card'; | ||||
| import { fromJS } from 'immutable'; | ||||
| 
 | ||||
| export default class CardContainer extends React.PureComponent { | ||||
|  | @ -1,12 +1,12 @@ | |||
| import React from 'react'; | ||||
| import { Provider } from 'react-redux'; | ||||
| import PropTypes from 'prop-types'; | ||||
| import configureStore from 'themes/glitch/store/configureStore'; | ||||
| import { hydrateStore } from 'themes/glitch/actions/store'; | ||||
| import configureStore from 'flavours/glitch/store/configureStore'; | ||||
| import { hydrateStore } from 'flavours/glitch/actions/store'; | ||||
| import { IntlProvider, addLocaleData } from 'react-intl'; | ||||
| import { getLocale } from 'mastodon/locales'; | ||||
| import Compose from 'themes/glitch/features/standalone/compose'; | ||||
| import initialState from 'themes/glitch/util/initial_state'; | ||||
| import Compose from 'flavours/glitch/features/standalone/compose'; | ||||
| import initialState from 'flavours/glitch/util/initial_state'; | ||||
| 
 | ||||
| const { localeData, messages } = getLocale(); | ||||
| addLocaleData(localeData); | ||||
|  | @ -1,7 +1,7 @@ | |||
| import { openModal, closeModal } from 'themes/glitch/actions/modal'; | ||||
| import { openModal, closeModal } from 'flavours/glitch/actions/modal'; | ||||
| import { connect } from 'react-redux'; | ||||
| import DropdownMenu from 'themes/glitch/components/dropdown_menu'; | ||||
| import { isUserTouching } from 'themes/glitch/util/is_mobile'; | ||||
| import DropdownMenu from 'flavours/glitch/components/dropdown_menu'; | ||||
| import { isUserTouching } from 'flavours/glitch/util/is_mobile'; | ||||
| 
 | ||||
| const mapStateToProps = state => ({ | ||||
|   isModalOpen: state.get('modal').modalType === 'ACTIONS', | ||||
|  | @ -1,6 +1,6 @@ | |||
| import { connect } from 'react-redux'; | ||||
| import IntersectionObserverArticle from 'themes/glitch/components/intersection_observer_article'; | ||||
| import { setHeight } from 'themes/glitch/actions/height_cache'; | ||||
| import IntersectionObserverArticle from 'flavours/glitch/components/intersection_observer_article'; | ||||
| import { setHeight } from 'flavours/glitch/actions/height_cache'; | ||||
| 
 | ||||
| const makeMapStateToProps = (state, props) => ({ | ||||
|   cachedHeight: state.getIn(['height_cache', props.saveHeightKey, props.id]), | ||||
Some files were not shown because too many files have changed in this diff Show more
		Loading…
	
		Reference in a new issue