diff --git a/app/assets/javascripts/content_types.js b/app/assets/javascripts/content_types.js new file mode 100644 index 000000000..83fd6f2bc --- /dev/null +++ b/app/assets/javascripts/content_types.js @@ -0,0 +1,24 @@ +$(document).ready(function() { + $('.js-enable-content-type').click(function () { + var content_type = $(this).data('content-type'); + var related_card = $(this).children('.card').first(); + var is_currently_active = related_card.hasClass('active'); + var ie_badge = $(this).find('.enabled-badge'); + + $.post('/customization/toggle_content_type', { + content_type: content_type, + active: is_currently_active ? 'off' : 'on' + }); + + if (is_currently_active) { + related_card.removeClass('active'); + ie_badge.attr('data-badge-caption', 'hidden'); + } else { + related_card.addClass('active'); + ie_badge.attr('data-badge-caption', 'active'); + } + + // Return false so we don't jump to the top of the page on link click + return false; + }); +}); diff --git a/app/assets/javascripts/navbar.js b/app/assets/javascripts/navbar.js new file mode 100644 index 000000000..d773dd76c --- /dev/null +++ b/app/assets/javascripts/navbar.js @@ -0,0 +1,5 @@ +// $(document).ready(function () { +// $('.tab-link').click(function() { +// document.location = $(this).attr('href'); +// }); +// }); diff --git a/app/assets/javascripts/navbar.js.coffee b/app/assets/javascripts/navbar.js.coffee deleted file mode 100644 index 1c2ac0229..000000000 --- a/app/assets/javascripts/navbar.js.coffee +++ /dev/null @@ -1 +0,0 @@ -$( -> $(".button-collapse").sidenav() ) diff --git a/app/assets/stylesheets/autosave.scss b/app/assets/stylesheets/autosave.scss new file mode 100644 index 000000000..9d855135d --- /dev/null +++ b/app/assets/stylesheets/autosave.scss @@ -0,0 +1,17 @@ +.autosave-bar { + position: fixed; + bottom: 0; + left: 0; + width: 100%; + + margin: 0; + padding: 4px 0; + + text-align: center; + background: white; + border-top: 2px solid lightgrey; + + i { + font-size: 15px; + } +} diff --git a/app/assets/stylesheets/btn-group.scss b/app/assets/stylesheets/btn-group.scss new file mode 100644 index 000000000..3d4d159b8 --- /dev/null +++ b/app/assets/stylesheets/btn-group.scss @@ -0,0 +1,44 @@ +.btn-group { + position: relative; + display: -ms-inline-flexbox; + display: inline-flex; +} + +.btn-group.card { + margin: 0; +} + +.btn-group>.btn:first-child:not(:last-child) { + border-top-right-radius: 0; + border-bottom-right-radius: 0; +} + +.btn-group>.btn:not(:first-child):not(:last-child) { + border-radius: 0; + border-left: 1px solid lightgrey; +} + +.btn-group>.btn:last-child:not(:first-child), +.btn-group>.dropdown-toggle:not(:first-child) { + border-top-left-radius: 0; + border-bottom-left-radius: 0; + border-left: 1px solid lightgrey; +} + +.btn-group>.btn-inactive { + background-color: #607d8b; +} + +.btn-group>.btn { + -webkit-box-shadow: 0 0px 0px 0 rgba(0, 0, 0, 0), 0 0px 0px 0px rgba(0, 0, 0, 0), 0 0px 0px 0 rgba(0, 0, 0, 0); + box-shadow: 0 0px 0px 0 rgba(0, 0, 0, 0), 0 0px 0px 0px rgba(0, 0, 0, 0), 0 0px 0px 0 rgba(0, 0, 0, 0); +} + +.btn-group>.btn-inactive:hover { + background-color: #728F9D; +} + +.btn-group>.btn:hover { + -webkit-box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.14), 0 3px 1px -2px rgba(0, 0, 0, 0.12), 0 1px 5px 0 rgba(0, 0, 0, 0.2); + box-shadow: 0 2px 2px 0 rgba(0, 0, 0, 0.14), 0 3px 1px -2px rgba(0, 0, 0, 0.12), 0 1px 5px 0 rgba(0, 0, 0, 0.2); +} diff --git a/app/assets/stylesheets/content.css.scss b/app/assets/stylesheets/content.css.scss index eae8fe329..94a4efa6c 100644 --- a/app/assets/stylesheets/content.css.scss +++ b/app/assets/stylesheets/content.css.scss @@ -14,15 +14,13 @@ p.long-form { margin-bottom: 16px; } -.card-action { - .green-text, .red-text { - i { - font-size: 90%; - } +.card-action.nice-icon-links { + i { + font-size: 90%; + } - a { - color: grey; - } + a { + color: grey; } } @@ -127,3 +125,10 @@ p.long-form { margin-bottom: 30px; } + +.parallax-header { + img { + -webkit-filter: blur(3px); /* Safari 6.0 - 9.0 */ + filter: blur(3px); + } +} diff --git a/app/assets/stylesheets/content_types.scss b/app/assets/stylesheets/content_types.scss new file mode 100644 index 000000000..a5460d313 --- /dev/null +++ b/app/assets/stylesheets/content_types.scss @@ -0,0 +1,27 @@ +.js-enable-content-type .card:not(.active) { + -webkit-filter: grayscale(100%); /* Safari 6.0 - 9.0 */ + filter: grayscale(100%); + + .card-image > img { + -webkit-filter: blur(2px); /* Safari 6.0 - 9.0 */ + filter: blur(2px); + } +} + +.js-enable-content-type .card:not(.active):hover { + -webkit-filter: grayscale(75%); /* Safari 6.0 - 9.0 */ + filter: grayscale(75%); + + .card-image > img { + -webkit-filter: blur(0px); /* Safari 6.0 - 9.0 */ + filter: blur(0px); + } +} + +.js-enable-content-type .enabled-badge { + float: right; + position: relative; + top: -51px; + right: 7px; + z-index: 3; +} diff --git a/app/assets/stylesheets/dashboard.css.scss b/app/assets/stylesheets/dashboard.css.scss index 45e89e246..ca5fba42a 100644 --- a/app/assets/stylesheets/dashboard.css.scss +++ b/app/assets/stylesheets/dashboard.css.scss @@ -2,4 +2,4 @@ .card-image { max-height: 200px; } -} \ No newline at end of file +} diff --git a/app/assets/stylesheets/editor.css.scss b/app/assets/stylesheets/editor.css.scss index 58eddcee1..ff1df25d5 100644 --- a/app/assets/stylesheets/editor.css.scss +++ b/app/assets/stylesheets/editor.css.scss @@ -2,13 +2,41 @@ min-height: 400px; border: 1px solid #dedede; padding: 5px 0; + margin-bottom: 600px; + + color: black; p { margin-top: 0; } + + /* PAGES */ + background: white; + padding: 30px; + border-bottom: 1px solid grey; } /* Materialize hacks */ b, strong { font-weight: bolder !important; } + +.document-name-bar { + .input-field.inline { + margin-bottom: 0; + } + + .row { + margin-bottom: 0; + } + + margin-bottom: 40px; +} + +.smart-sidebar { + opacity: 0.4; + + &:hover { + opacity: 1.0; + } +} diff --git a/app/assets/stylesheets/footer.css b/app/assets/stylesheets/footer.css index c94ab5177..f953277f2 100644 --- a/app/assets/stylesheets/footer.css +++ b/app/assets/stylesheets/footer.css @@ -7,3 +7,7 @@ body { main { flex: 1 0 auto; } + +.stealth-page-footer { + padding-bottom: 20px; +} diff --git a/app/assets/stylesheets/materialize-overrides.scss b/app/assets/stylesheets/materialize-overrides.scss index 51e747006..68591a935 100644 --- a/app/assets/stylesheets/materialize-overrides.scss +++ b/app/assets/stylesheets/materialize-overrides.scss @@ -6,13 +6,17 @@ @media only screen and (min-width: 1024px) { .fixed-card-content { - height: 8em; + height: 8em; } } @media only screen and (max-width: 1024px) { .fixed-card-content { - height: 10em; + height: 10em; } -} \ No newline at end of file +} + +body { + background: #f4f4f4; +} diff --git a/app/assets/stylesheets/navbar.css b/app/assets/stylesheets/navbar.css index 36fbfc047..c5a21229c 100644 --- a/app/assets/stylesheets/navbar.css +++ b/app/assets/stylesheets/navbar.css @@ -1,13 +1,34 @@ .dropdown-content { - min-width: 300px !important; + min-width: 400px !important; } -.navbar-fixed { - margin-bottom: 15px; - z-index: 1000 !important; +@media only screen and (min-width: 993px) { + body.has-fixed-sidenav { + padding-left: 300px !important; + } + + nav.navbar.logged-in { + width: calc(100% - 300px); + } +} + +@media only screen and (max-width: 993px) { + body.has-fixed-sidenav { + padding-left: 0 !important; + } +} + +@media only screen and (min-width: 601px) { + nav, nav .nav-wrapper i, nav a.sidenav-trigger, nav a.sidenav-trigger i { + height: 64px; + line-height: 64px; + } } -.universe-filter-active { - background: purple; - height: 100%; +nav.navbar { + z-index: 10; + transition: box-shadow .3s, background-color .3s; + padding: 0 20px; + background-color: #fff; + color: rgba(0,0,0,0.87); } diff --git a/app/assets/stylesheets/sidenav.css.scss b/app/assets/stylesheets/sidenav.css.scss index bcad62d25..cff23eaf5 100644 --- a/app/assets/stylesheets/sidenav.css.scss +++ b/app/assets/stylesheets/sidenav.css.scss @@ -1,14 +1,43 @@ .sidenav { - padding-top: 64px; + li { + display: block; + } + + .logo-container { + padding: 0 16px; + height: 64px; + line-height: 64px; + font-size: 24px; + border-bottom: 1px solid rgba(0,0,0,0.2); + box-sizing: content-box; + + i.material-icons.right { + position: relative; + top: 8px; + left: 26px; + } + } - .header { - background: #10B6FF; - color: white; - margin: 0; - text-align: center; + .collapsible .collapsible-header { + text-transform: uppercase; + height: 64px; + line-height: 64px; + + .material-icons.left { + margin-top: 8px; + } + } + + .collapsible .collapsible-header .chevron { + float: right; + height: 24px; + width: 24px; + line-height: 24px; + margin: 20px 0 0 0; + transition: transform .2s; + } - font-size: 12px; - height: 20px; - line-height: 20px; + .collapsible>.active .collapsible-header .chevron { + transform: rotate(-90deg); } } diff --git a/app/assets/stylesheets/thredded-overrides.scss b/app/assets/stylesheets/thredded-overrides.scss index 8d0099ed5..1ed5bc352 100644 --- a/app/assets/stylesheets/thredded-overrides.scss +++ b/app/assets/stylesheets/thredded-overrides.scss @@ -1,5 +1,81 @@ @import "thredded"; +#thredded--container { + #q /* search input */ { + height: 37px; + padding-left: 16px; + } + + .thredded--user-navigation { + height: 64px; + } + + .thredded--currently-online { + right: 100px; + } + + .thredded--new-topic-form { + background: white; + padding: 10px; + padding-bottom: 0; + border: 1px solid lightgrey; + + margin-bottom: 20px; + } + + .thredded--topics--topic { + background: white; + padding: 4px 26px; + border: 1px solid lightgrey; + + margin-bottom: 0.7rem; + } + + .thredded--topics--posts-count { + left: -1rem; + top: 2px; + } + + .thredded--topics--follow-icon { + right: 0.2rem; + top: 6px; + } + + .thredded--pagination { + background: white; + padding: 0 0 10px 0; + } + + .thredded--topic .thredded--post { + background: white; + padding: 10px; + + margin-bottom: 20px; + border-bottom: 1px solid lightgrey; + } + + @media (min-width: 47.12501rem) { + .thredded--post--avatar { + top: 0; + } + } + + .thredded--messageboard { + background: white; + border-bottom: 1px solid lightgrey; + margin: 2px; + } +} + +.thredded--main-header { + nav { + background: white; + padding: 0 10px; + + margin-bottom: 100px; + } +} + .thredded--main-container { // The padding and max-width are handled by the app's container. min-width: 80%; diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index 7faf7a369..1a31a429b 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -48,7 +48,9 @@ def cache_most_used_page_information current_user.user_content_type_activators.pluck(:content_type) ) - @current_user_content = current_user.content(content_types: @activated_content_types) + # We always want to cache Universes, even if they aren't explicitly turned on. + @current_user_content = current_user.content(content_types: @activated_content_types + ['Universe']) + @current_user_content['Document'] = current_user.documents end def cache_forums_unread_counts diff --git a/app/controllers/content_controller.rb b/app/controllers/content_controller.rb index 83d1659f6..fe1c409b6 100644 --- a/app/controllers/content_controller.rb +++ b/app/controllers/content_controller.rb @@ -8,6 +8,13 @@ class ContentController < ApplicationController before_action :populate_linkable_content_for_each_content_type, only: [:new, :edit] + before_action :set_attributes_content_type, only: [:attributes] + + before_action :set_navbar_color + before_action :set_general_navbar_actions, except: [:deleted, :show, :changelog] + before_action :set_specific_navbar_actions, only: [:show, :changelog] + before_action :set_sidenav_expansion + def index @content_type_class = content_type_from_controller(self.class) pluralized_content_name = @content_type_class.name.downcase.pluralize @@ -44,6 +51,18 @@ def show return redirect_to(root_path, notice: "You don't have permission to view that content.") if @content.nil? @serialized_content = ContentSerializer.new(@content) + if user_signed_in? + @navbar_actions << { + label: @serialized_content.name, + href: main_app.polymorphic_path(@content) + } + + @navbar_actions << { + label: 'Changelog', + href: send("changelog_#{content_type.name.downcase}_path", @content) + } + end + return redirect_to(root_path) if @content.user.nil? # deleted user's content return if ENV.key?('CONTENT_BLACKLIST') && ENV['CONTENT_BLACKLIST'].split(',').include?(@content.user.try(:email)) @@ -81,7 +100,7 @@ def new # todo this is a good spot to audit to disable and see if create permissions are ok also unless (current_user || User.new).can_create?(content_type_from_controller(self.class)) - return redirect_back(fallback_location: root_path) + return redirect_to(subscription_path, notice: "#{@content.class.name.pluralize} require a Premium subscription to create.") end respond_to do |format| @@ -143,7 +162,7 @@ def create upload_files params['image_uploads'], content_type.name, @content.id end - successful_response(content_creation_redirect_url, t(:create_success, model_name: humanized_model_name)) + successful_response(content_creation_redirect_url, t(:create_success, model_name: @content.try(:name).presence || humanized_model_name)) else failed_response('new', :unprocessable_entity, "Unable to save page. Error code: " + @content.errors.map(&:messages).to_sentence) end @@ -189,12 +208,32 @@ def update end if update_success - successful_response(@content, t(:update_success, model_name: humanized_model_name)) + successful_response(@content, t(:update_success, model_name: @content.try(:name).presence || humanized_model_name)) else failed_response('edit', :unprocessable_entity, "Unable to save page. Error code: " + @content.errors.map(&:messages).to_sentence) end end + def changelog + content_type = content_type_from_controller(self.class) + return redirect_to root_path unless valid_content_types.map(&:name).include?(content_type.name) + @content = content_type.find_by(id: params[:id]) + return redirect_to(root_path, notice: "You don't have permission to view that content.") if @content.nil? + @serialized_content = ContentSerializer.new(@content) + + if user_signed_in? + @navbar_actions << { + label: @serialized_content.name, + href: main_app.polymorphic_path(@content) + } + + @navbar_actions << { + label: 'Changelog', + href: send("changelog_#{content_type.name.downcase}_path", @content) + } + end + end + def upload_files image_uploads_list, content_type, content_id image_uploads_list.each do |image_data| image_size_kb = File.size(image_data.tempfile.path) / 1000.0 @@ -237,9 +276,10 @@ def destroy 'content_type': content_type.name }) if Rails.env.production? + cached_page_name = @content.try(:name) @content.destroy - successful_response(content_deletion_redirect_url, t(:delete_success, model_name: humanized_model_name)) + successful_response(content_deletion_redirect_url, t(:delete_success, model_name: cached_page_name.presence || humanized_model_name)) end # List all recently-deleted content @@ -249,15 +289,12 @@ def deleted @content_pages[content_type] = content_type.constantize.with_deleted.where('deleted_at > ?', 24.hours.ago).where(user_id: current_user.id) end @content_pages["Document"] = current_user.documents.with_deleted.where('deleted_at > ?', 24.hours.ago) + + # Override controller + @sidenav_expansion = 'my account' end def attributes - @content_type = params[:content_type] - # todo make this a before_action load_content_type - unless valid_content_types.map { |c| c.name.downcase }.include?(@content_type) - raise "Invalid content type on attributes customization page: #{@content_type}" - end - @content_type_class = @content_type.titleize.constantize end private @@ -368,4 +405,73 @@ def failed_response(action, status, notice=nil) def humanized_model_name content_type_from_controller(self.class).model_name.human end + + def set_attributes_content_type + @content_type = params[:content_type] + # todo make this a before_action load_content_type + unless valid_content_types.map { |c| c.name.downcase }.include?(@content_type) + raise "Invalid content type on attributes customization page: #{@content_type}" + end + @content_type_class = @content_type.titleize.constantize + end + + def set_navbar_color + content_type = @content_type_class || content_type_from_controller(self.class) + @navbar_color = content_type.try(:hex_color) || '#2196F3' + end + + # For index, new, edit + def set_general_navbar_actions + content_type = @content_type_class || content_type_from_controller(self.class) + @navbar_actions = [] + + if @current_user_content + @navbar_actions << { + label: "Your #{view_context.pluralize @current_user_content.fetch(content_type.name, []).count, content_type.name.downcase}", + href: main_app.polymorphic_path(content_type) + } + end + + @navbar_actions << { + label: "New #{content_type.name.downcase}", + href: main_app.new_polymorphic_path(content_type) + } + + discussions_link = ForumsLinkbuilderService.worldbuilding_url(content_type) + if discussions_link.present? + @navbar_actions << { + label: 'Discussions', + href: discussions_link + } + end + + @navbar_actions << { + label: 'Customize template', + href: main_app.attribute_customization_path(content_type.name.downcase) + } + end + + # For showing a specific piece of content + def set_specific_navbar_actions + content_type = @content_type_class || content_type_from_controller(self.class) + @navbar_actions = [] + + if user_signed_in? + if @current_user_content + @navbar_actions << { + label: "Your #{view_context.pluralize @current_user_content.fetch(content_type.name, []).count, content_type.name.downcase}", + href: main_app.polymorphic_path(content_type) + } + end + # + # @navbar_actions << { + # label: "New #{content_type.name.downcase}", + # href: main_app.new_polymorphic_path(content_type) + # } + end + end + + def set_sidenav_expansion + @sidenav_expansion = 'worldbuilding' + end end diff --git a/app/controllers/customization_controller.rb b/app/controllers/customization_controller.rb index 4ff12effa..9eb40a121 100644 --- a/app/controllers/customization_controller.rb +++ b/app/controllers/customization_controller.rb @@ -7,6 +7,7 @@ def content_types @all_content_types = Rails.application.config.content_types[:all] @premium_content_types = Rails.application.config.content_types[:premium] @my_activators = current_user.user_content_type_activators.pluck(:content_type) + @sidenav_expansion = 'worldbuilding' end def toggle_content_type diff --git a/app/controllers/documents_controller.rb b/app/controllers/documents_controller.rb index 5f0b71bf3..665fb7801 100644 --- a/app/controllers/documents_controller.rb +++ b/app/controllers/documents_controller.rb @@ -1,13 +1,26 @@ class DocumentsController < ApplicationController before_action :authenticate_user! + before_action :set_sidenav_expansion + before_action :set_navbar_color + before_action :set_navbar_actions, except: [:edit] + before_action :set_footer_visibility, only: [:edit] + def index @documents = current_user.documents.order('updated_at desc') end def show - document = Document.find_by(id: params[:id], user_id: current_user.id) - redirect_to edit_document_path(document) + @document = Document.find_by(id: params[:id], user_id: current_user.id) + + unless @document.present? || @document.viewable_by?(current_user || User.new) + redirect_to(root_path, notice: "That document either doesn't exist or you don't have permission to view it.") + end + + @navbar_actions.unshift({ + label: (@document.name || 'Untitled document'), + href: document_path(@document) + }) end def edit @@ -46,10 +59,39 @@ def destroy if current_user.can_delete?(document) document.destroy - redirect_back(fallback_location: documents_path, notice: "The document was successfully deleted.") + redirect_to(documents_path, notice: "The document was successfully deleted.") else - redirect_back(fallback_location: root_path, notice: "You don't have permission to do that!") + redirect_to(root_path, notice: "You don't have permission to do that!") + end + end + + def set_sidenav_expansion + @sidenav_expansion = 'writing' + end + + def set_navbar_color + content_type = content_type_from_controller(self.class) + @navbar_color = content_type.hex_color + end + + def set_navbar_actions + @navbar_actions = [] + + if @current_user_content['Document'].present? + @navbar_actions << { + label: "Your #{@current_user_content['Document'].count} Document#{'s' unless @navbar_actions == 1}", + href: documents_path + } end + + @navbar_actions << { + label: "New Document", + href: edit_document_path(:new) + } + end + + def set_footer_visibility + @show_footer = false end private diff --git a/app/controllers/export_controller.rb b/app/controllers/export_controller.rb index 82333a413..de3a3f171 100644 --- a/app/controllers/export_controller.rb +++ b/app/controllers/export_controller.rb @@ -3,6 +3,8 @@ class ExportController < ApplicationController before_action :whitelist_pluralized_model, only: [:csv] def index + @sidenav_expansion = 'my account' + Mixpanel::Tracker.new(Rails.application.config.mixpanel_token).track(current_user.id, 'viewed export page', { 'content count': current_user.content_count }) if Rails.env.production? @@ -27,13 +29,13 @@ def outline def notebook_json report_to_mixpanel 'json', 'notebook' - json_dump = current_user.content.map { |category, content| {"#{category}": fill_relations(category.constantize, content)} }.to_json + json_dump = current_user.content.except('Document').map { |category, content| {"#{category}": fill_relations(category.constantize, content)} }.to_json send_data json_dump, filename: "notebook-#{Date.today}.json" end def notebook_xml report_to_mixpanel 'xml', 'notebook' - xml_dump = current_user.content.map { |category, content| {"#{category}": fill_relations(category.constantize, content)}}.to_xml + xml_dump = current_user.content.except('Document').map { |category, content| {"#{category}": fill_relations(category.constantize, content)}}.to_xml send_data xml_dump, filename: "notebook-#{Date.today}.xml" end @@ -118,7 +120,7 @@ def fill_relations(ar_class, ar_relation) end def content_to_outline - content_types = current_user.content.keys + content_types = current_user.content.except('Document').keys text = "" content_types.each do |content_type| diff --git a/app/controllers/main_controller.rb b/app/controllers/main_controller.rb index c5dab7d51..5413f4d26 100644 --- a/app/controllers/main_controller.rb +++ b/app/controllers/main_controller.rb @@ -28,9 +28,13 @@ def dashboard def prompts return redirect_to(new_user_session_path) unless user_signed_in? + @sidenav_expansion = 'writing' + @navbar_color = '#FF9800' + set_random_content # for question end + # deprecated path just kept around for bookmarks for a while def notes return redirect_to(new_user_session_path) unless user_signed_in? redirect_to edit_document_path(current_user.documents.first) @@ -68,6 +72,7 @@ def for_roleplayers def for_designers end + # deprecated path todo cleanup def for_friends @subscriber_count = User.where(selected_billing_plan_id: [3, 4]).count @drawing_date = 'June 15, 2017 12:00pm'.to_date @@ -81,6 +86,10 @@ def for_friends def feature_voting end + def privacyinfo + @sidenav_expansion = 'help' + end + private def set_random_content @@ -90,18 +99,23 @@ def set_random_content # when we want to enable prompts for contributing universes we can remove the user: # selector here, but we will need to verify the user has permission to see the universe # when we do that, or else prompts could open leak - @content = content_type.constantize.where(user: current_user, id: @universe_scope.id).sample + @content = content_type.constantize.where(user: current_user, id: @universe_scope.id).includes(:user) else - @content = content_type.constantize.where(user: current_user).sample + @content = content_type.constantize.where(user: current_user).includes(:user) end else if @universe_scope.present? - @content = content_type.constantize.where(user: current_user, universe: @universe_scope).sample + @content = content_type.constantize.where(user: current_user, universe: @universe_scope).includes(:user) else - @content = content_type.constantize.where(user: current_user).sample + @content = content_type.constantize.where(user: current_user).includes(:user) end end + unless @content.klass.name == Universe.name + @content = @content.includes(:universe) + end + + @content = @content.sample return if @content.present? end end diff --git a/app/controllers/registrations_controller.rb b/app/controllers/registrations_controller.rb index 9465625c9..7051c3a79 100644 --- a/app/controllers/registrations_controller.rb +++ b/app/controllers/registrations_controller.rb @@ -1,6 +1,9 @@ class RegistrationsController < Devise::RegistrationsController after_action :add_account, only: [:create] + before_action :set_navbar_actions, only: [:edit] + before_action :set_navbar_color, only: [:edit] + def new super if params[:referral] @@ -8,6 +11,10 @@ def new end end + def edit + @sidenav_expansion = 'my account' + end + private def sign_up_params @@ -15,13 +22,24 @@ def sign_up_params end def account_update_params - params.require(:user).permit(:name, :email, :username, :password, :password_confirmation, :email_updates, :fluid_preference) + params.require(:user).permit( + :name, :email, :username, :password, :password_confirmation, :email_updates, :fluid_preference, + :bio, :favorite_genre, :favorite_author, :interests, :age, :location, :gender + ) end def update_resource(resource, params) resource.update_without_password(params) end + def set_navbar_color + @navbar_color = '#000000' + end + + def set_navbar_actions + @navbar_actions = [] + end + protected def add_account diff --git a/app/controllers/users_controller.rb b/app/controllers/users_controller.rb index da35d7efd..94379ecf1 100644 --- a/app/controllers/users_controller.rb +++ b/app/controllers/users_controller.rb @@ -4,6 +4,8 @@ def index end def show + @sidenav_expansion = 'my account' + @user = User.find_by(id: params[:id]) return redirect_to(root_path, notice: 'That user does not exist.') if @user.nil? diff --git a/app/models/concerns/has_content.rb b/app/models/concerns/has_content.rb index 3aa8178b8..ff3991256 100644 --- a/app/models/concerns/has_content.rb +++ b/app/models/concerns/has_content.rb @@ -23,10 +23,12 @@ def content( content_types: Rails.application.config.content_types[:all].map(&:name), page_scoping: { user_id: self.id } ) + return {} if content_types.empty? + polymorphic_content_fields = [:id, :name, :page_type, :user_id, :created_at, :updated_at, :deleted_at, :privacy] where_conditions = page_scoping.map { |key, value| "#{key} = #{value}" }.join(' AND ') + ' AND deleted_at IS NULL' - sql = content_types.map do |page_type| + sql = content_types.uniq.map do |page_type| "SELECT #{polymorphic_content_fields.join(',')} FROM #{page_type.downcase.pluralize} WHERE #{where_conditions}" end.join(' UNION ALL ') + ' ORDER BY page_type, id' @@ -51,7 +53,7 @@ def content_list( polymorphic_content_fields = [:id, :name, :page_type, :user_id, :created_at, :updated_at, :deleted_at, :privacy] where_conditions = page_scoping.map { |key, value| "#{key} = #{value}" }.join(' AND ') + ' AND deleted_at IS NULL' - sql = content_types.map do |page_type| + sql = content_types.uniq.map do |page_type| "SELECT #{polymorphic_content_fields.join(',')} FROM #{page_type.downcase.pluralize} WHERE #{where_conditions}" end.join(' UNION ALL ') diff --git a/app/models/content_types/building.rb b/app/models/content_types/building.rb index d1d184c32..1fcebd18b 100644 --- a/app/models/content_types/building.rb +++ b/app/models/content_types/building.rb @@ -21,6 +21,10 @@ def self.color 'blue-grey' end + def self.hex_color + '#607D8B' + end + def self.icon 'business' end diff --git a/app/models/content_types/character.rb b/app/models/content_types/character.rb index b5ffcee8f..2b52df8b0 100644 --- a/app/models/content_types/character.rb +++ b/app/models/content_types/character.rb @@ -57,6 +57,10 @@ def self.color 'red' end + def self.hex_color + '#F44336' + end + def self.icon 'group' end diff --git a/app/models/content_types/condition.rb b/app/models/content_types/condition.rb index 08f464530..dd411ca87 100644 --- a/app/models/content_types/condition.rb +++ b/app/models/content_types/condition.rb @@ -21,6 +21,10 @@ def self.color 'text-darken-1 lime' end + def self.hex_color + '#CDDC39' + end + def self.icon 'bubble_chart' end diff --git a/app/models/content_types/country.rb b/app/models/content_types/country.rb index f43bd5047..e7926c344 100644 --- a/app/models/content_types/country.rb +++ b/app/models/content_types/country.rb @@ -40,6 +40,10 @@ def self.color 'lighten-2 text-lighten-2 brown' end + def self.hex_color + '#A1887F' + end + def self.icon 'explore' end diff --git a/app/models/content_types/creature.rb b/app/models/content_types/creature.rb index 9964eeb8a..9c4fede3e 100644 --- a/app/models/content_types/creature.rb +++ b/app/models/content_types/creature.rb @@ -41,6 +41,10 @@ def self.color 'brown' end + def self.hex_color + '#795548' + end + def self.icon 'pets' end diff --git a/app/models/content_types/deity.rb b/app/models/content_types/deity.rb index b046acceb..2080421a1 100644 --- a/app/models/content_types/deity.rb +++ b/app/models/content_types/deity.rb @@ -41,6 +41,10 @@ def self.color 'text-lighten-4 blue' end + def self.hex_color + '#BBDEFB' + end + def self.icon 'ac_unit' end diff --git a/app/models/content_types/flora.rb b/app/models/content_types/flora.rb index 8b639d6f7..f5818e401 100644 --- a/app/models/content_types/flora.rb +++ b/app/models/content_types/flora.rb @@ -36,6 +36,10 @@ def self.color 'text-lighten-3 lighten-3 teal' end + def self.hex_color + '#80CBC4' + end + def self.icon 'local_florist' end diff --git a/app/models/content_types/government.rb b/app/models/content_types/government.rb index 00bc36aaa..2675e2d1d 100644 --- a/app/models/content_types/government.rb +++ b/app/models/content_types/government.rb @@ -31,6 +31,10 @@ def self.color 'darken-2 green' end + def self.hex_color + '#388E3C' + end + def self.icon 'account_balance' end diff --git a/app/models/content_types/group.rb b/app/models/content_types/group.rb index 46dedefac..40a106c7f 100644 --- a/app/models/content_types/group.rb +++ b/app/models/content_types/group.rb @@ -44,6 +44,10 @@ def self.color 'cyan' end + def self.hex_color + '#00BCD4' + end + def self.icon 'wc' end diff --git a/app/models/content_types/item.rb b/app/models/content_types/item.rb index 502729f80..2f6390192 100644 --- a/app/models/content_types/item.rb +++ b/app/models/content_types/item.rb @@ -40,6 +40,10 @@ def self.color 'amber' end + def self.hex_color + '#FFC107' + end + def self.icon 'beach_access' end diff --git a/app/models/content_types/job.rb b/app/models/content_types/job.rb index 8e8aef8ff..d072c945c 100644 --- a/app/models/content_types/job.rb +++ b/app/models/content_types/job.rb @@ -21,6 +21,10 @@ def self.color 'text-lighten-1 brown' end + def self.hex_color + '#795548' + end + def self.icon 'work' end diff --git a/app/models/content_types/landmark.rb b/app/models/content_types/landmark.rb index 4dc49a7c2..7cf7f5096 100644 --- a/app/models/content_types/landmark.rb +++ b/app/models/content_types/landmark.rb @@ -36,6 +36,10 @@ def self.color 'text-lighten-1 lighten-1 orange' end + def self.hex_color + '#FFA726' + end + def self.icon 'location_on' end diff --git a/app/models/content_types/language.rb b/app/models/content_types/language.rb index e38ae1897..63ed53e27 100644 --- a/app/models/content_types/language.rb +++ b/app/models/content_types/language.rb @@ -28,6 +28,10 @@ def self.color 'blue' end + def self.hex_color + '#2196F3' + end + def self.icon 'forum' end diff --git a/app/models/content_types/location.rb b/app/models/content_types/location.rb index dc5ba3b0f..632db5170 100644 --- a/app/models/content_types/location.rb +++ b/app/models/content_types/location.rb @@ -51,6 +51,10 @@ def self.color 'green' end + def self.hex_color + '#4CAF50' + end + def self.content_name 'location' end diff --git a/app/models/content_types/magic.rb b/app/models/content_types/magic.rb index 8b0a8a3ed..8b12cc779 100644 --- a/app/models/content_types/magic.rb +++ b/app/models/content_types/magic.rb @@ -30,6 +30,10 @@ def self.color 'orange' end + def self.hex_color + '#FF9800' + end + def self.icon 'flash_on' end diff --git a/app/models/content_types/planet.rb b/app/models/content_types/planet.rb index 2233deb3d..423092dc2 100644 --- a/app/models/content_types/planet.rb +++ b/app/models/content_types/planet.rb @@ -37,6 +37,10 @@ def self.color 'text-lighten-2 blue' end + def self.hex_color + '#64B5F6' + end + def self.icon 'public' end diff --git a/app/models/content_types/race.rb b/app/models/content_types/race.rb index 6573c8c7a..a19f6570b 100644 --- a/app/models/content_types/race.rb +++ b/app/models/content_types/race.rb @@ -36,6 +36,10 @@ def self.color 'light-green' end + def self.hex_color + '#8BC34A' + end + def self.icon 'face' end diff --git a/app/models/content_types/religion.rb b/app/models/content_types/religion.rb index 84dfcc825..b43b1a5a5 100644 --- a/app/models/content_types/religion.rb +++ b/app/models/content_types/religion.rb @@ -40,7 +40,11 @@ def description end def self.color - 'yellow' + 'indigo' + end + + def self.hex_color + '#3f51b5' end def self.icon diff --git a/app/models/content_types/scene.rb b/app/models/content_types/scene.rb index 8b77821ce..e732eb77e 100644 --- a/app/models/content_types/scene.rb +++ b/app/models/content_types/scene.rb @@ -36,6 +36,10 @@ def self.color 'grey' end + def self.hex_color + '#9E9E9E' + end + def self.icon 'local_movies' end diff --git a/app/models/content_types/technology.rb b/app/models/content_types/technology.rb index ba095ce60..0e9762d25 100644 --- a/app/models/content_types/technology.rb +++ b/app/models/content_types/technology.rb @@ -35,6 +35,10 @@ def self.color 'text-darken-2 red' end + def self.hex_color + '#D32F2F' + end + def self.icon 'router' end diff --git a/app/models/content_types/town.rb b/app/models/content_types/town.rb index 1a41a6ead..da18715b8 100644 --- a/app/models/content_types/town.rb +++ b/app/models/content_types/town.rb @@ -39,6 +39,10 @@ def self.color 'text-lighten-3 lighten-3 purple' end + def self.hex_color + '#CE93D8' + end + def self.icon 'location_city' end diff --git a/app/models/content_types/tradition.rb b/app/models/content_types/tradition.rb index 01e30edd9..031e77f61 100644 --- a/app/models/content_types/tradition.rb +++ b/app/models/content_types/tradition.rb @@ -21,6 +21,10 @@ def self.color 'text-lighten-3 lighten-3 red' end + def self.hex_color + '#EF9A9A' + end + def self.icon 'today' end diff --git a/app/models/content_types/universe.rb b/app/models/content_types/universe.rb index 0bc312d22..bb70b71ae 100644 --- a/app/models/content_types/universe.rb +++ b/app/models/content_types/universe.rb @@ -70,6 +70,10 @@ def self.color 'purple' end + def self.hex_color + '#9C27B0' + end + def self.icon 'language' end diff --git a/app/models/content_types/vehicle.rb b/app/models/content_types/vehicle.rb index 02181fc47..c2f349660 100644 --- a/app/models/content_types/vehicle.rb +++ b/app/models/content_types/vehicle.rb @@ -21,6 +21,10 @@ def self.color 'text-lighten-2 green' end + def self.hex_color + '#81C784' + end + def self.icon 'drive_eta' end diff --git a/app/models/document.rb b/app/models/document.rb index c079356c6..893473bdd 100644 --- a/app/models/document.rb +++ b/app/models/document.rb @@ -10,6 +10,10 @@ def self.color 'teal' end + def self.hex_color + '#009688' + end + def self.icon 'description' end diff --git a/app/services/forums_linkbuilder_service.rb b/app/services/forums_linkbuilder_service.rb new file mode 100644 index 000000000..32ec8e7d5 --- /dev/null +++ b/app/services/forums_linkbuilder_service.rb @@ -0,0 +1,30 @@ +class ForumsLinkbuilderService < Service + def self.worldbuilding_url(page_type) + self.content_to_url_map.fetch(page_type.name.to_sym, nil) + end + + def self.content_to_url_map + { + 'Character': '/forum/characters-board', + 'Condition': '/forum/conditions', + 'Creature': '/forum/characters', # [sic] + 'Flora': '/forum/flora', + 'Government': '/forum/governments', + 'Item': '/forum/items', + 'Job': '/forum/jobs', + 'Landmark': '/forum/landmarks', + 'Language': '/forum/general-worldbuilding', # wtf did I do + 'Location': '/forum/locations', + 'Magic': '/forum/magic', + 'Planet': '/forum/planets', + 'Race': '/forum/races', + 'Religion': '/forum/religions', + 'Technology': '/forum/technology', + 'Tradition': '/forum/traditions' + } + end + + def self.is_discussions_page?(url) + return url.start_with?('/forum/') + end +end diff --git a/app/views/cards/serendipitous/_content_question.html.erb b/app/views/cards/serendipitous/_content_question.html.erb index e4052fd9c..f7e11d224 100644 --- a/app/views/cards/serendipitous/_content_question.html.erb +++ b/app/views/cards/serendipitous/_content_question.html.erb @@ -34,12 +34,14 @@ questionable_field_ids = fields_for_these_categories.pluck(:id) - attribute_fields_with_values attribute_field_to_question = AttributeField.find_by(id: questionable_field_ids.sample) end + + @serendipitous_asking_question = attribute_field_to_question.present? %> -<% if attribute_field_to_question.present? %> +<% if @serendipitous_asking_question %>
-
- <%= content.class.icon %> +
+ <%= content.class.icon %> <%= t( @@ -57,7 +59,7 @@
-
+
<%= form_for content do |f| %> <%= hidden_field(:override, :redirect_path, value: redirect_path) if defined?(redirect_path) %> @@ -86,8 +88,8 @@ } %>
- <%# render partial: 'content/display/quick_reference', locals: { content: content } %> -

+ <%= render partial: 'content/display/quick_reference', locals: { content: content } %> +

diff --git a/app/views/cards/ui/_alert.html.erb b/app/views/cards/ui/_alert.html.erb index 1f716871a..01324c879 100644 --- a/app/views/cards/ui/_alert.html.erb +++ b/app/views/cards/ui/_alert.html.erb @@ -1,7 +1,8 @@ <% if alert %> -
- - <%= alert.html_safe unless alert.blank? %> - -
+ <%= content_for :javascript do %> + M.toast({ + html: "<%= alert.gsub('"', '\"').html_safe %>", + classes: 'rounded' + }) + <% end %> <% end %> diff --git a/app/views/cards/ui/_notice.html.erb b/app/views/cards/ui/_notice.html.erb index efb3392ef..da6c047e5 100644 --- a/app/views/cards/ui/_notice.html.erb +++ b/app/views/cards/ui/_notice.html.erb @@ -1,7 +1,8 @@ <% if notice %> -
- - <%= notice.html_safe unless notice.blank? %> - -
-<% end %> \ No newline at end of file + <%= content_for :javascript do %> + M.toast({ + html: "<%= notice.gsub('"', '\"').html_safe %>", + classes: 'rounded' + }) + <% end %> +<% end %> diff --git a/app/views/content/attributes.html.erb b/app/views/content/attributes.html.erb index 1b7c16946..3b98c3ee6 100644 --- a/app/views/content/attributes.html.erb +++ b/app/views/content/attributes.html.erb @@ -1,24 +1,8 @@ -
-
    -
  • - <%= image_tag "card-headers/#{@content_type.pluralize}.jpg" %> -
    -

    <%= @content_type.titleize.pluralize %>

    -
    <%= t("content_oneliners.#{@content_type}") %>
    -
    -
  • -
-
- +<%= content_for :full_width_page_header do %> + <%= render partial: 'content/components/parallax_header', locals: { content_type: @content_type_class.name, content_class: @content_type_class } %> +<% end %> -
    +
    • <%= @content_type_class.icon %> diff --git a/app/views/content/cards/_in_universe_content_list.html.erb b/app/views/content/cards/_in_universe_content_list.html.erb index 4188ae358..214858ecc 100644 --- a/app/views/content/cards/_in_universe_content_list.html.erb +++ b/app/views/content/cards/_in_universe_content_list.html.erb @@ -17,18 +17,20 @@ else list_name_lookup_cache = {} end - - #raise list_name_lookup_cache.inspect %> -
      +
      <% images = ImageUpload.where(content_type: content_type_name, content_id: content_list.pluck(:id)) %> - <% if rand(3) < 2 && images.any? %> - <%= image_tag images.sample.src(:large), class: 'activator', style: 'height: 265px' %> - <% else %> - <%= image_tag "card-headers/#{content_type_pluralized}.jpg", class: 'activator', style: 'height: 265px' %> - <% end %> + <% + category_image = if rand(3) < 2 && images.any? + images.sample.src(:large) + else + asset_path("card-headers/#{content_type_pluralized}.jpg") + end + %> +
      +
      <% if defined?(card_title) && !card_title.blank? %> <%= card_title %> @@ -37,10 +39,11 @@ <% end %> <% if user_signed_in? %> - <%= link_to new_polymorphic_path(content_type), class: "btn-floating btn-large halfway-fab waves-effect waves-light #{content_type_class.color} tooltipped", + <%= link_to new_polymorphic_path(content_type), class: "btn-floating btn-large halfway-fab waves-effect waves-light #{content_type_class.color} tooltipped #{'grey' unless current_user.can_create?(content_type_class)}", data: { position: 'bottom', - tooltip: "Create a #{content_type.to_s}", + tooltip: current_user.can_create?(content_type_class) ? "Create a#{'n' if %w(a e i o u).include?(content_type.to_s[0])} #{content_type.to_s}" + : "#{content_type.to_s.pluralize.titleize} require a Premium subscription to create.", enterDelay: 50 } do %> add diff --git a/app/views/content/cards/_mobile_links.html.erb b/app/views/content/cards/_mobile_links.html.erb deleted file mode 100644 index e7007dbbe..000000000 --- a/app/views/content/cards/_mobile_links.html.erb +++ /dev/null @@ -1,28 +0,0 @@ -
      -
      - - - forum - - Visit the forums - - -

      - There have been <%= Thredded::Topic.where('created_at > ?', DateTime.current - 1.week).count %> new threads created in the past week on the forums. - Share your characters, talk about worlbuilding, find a collaborator or two, or just, well, chat! There's threads for everyone. -


      - -
      - <%= link_to main_app.thredded_path, class: 'btn white black-text' do %> - View discussions - <% if @unread_threads > 0 || @unread_private_messages > 0 %> - - <%= @unread_threads %><%= "/#{@unread_private_messages}" if @unread_private_messages > 0 %> - - <% end %> - <% end %> -
      -
      - -
      -
      diff --git a/app/views/content/changelog.html.erb b/app/views/content/changelog.html.erb new file mode 100644 index 000000000..7e5665e38 --- /dev/null +++ b/app/views/content/changelog.html.erb @@ -0,0 +1 @@ +<%= render partial: 'content/display/changelog', locals: { content: @serialized_content } %> diff --git a/app/views/content/components/_list_filter_bar.html.erb b/app/views/content/components/_list_filter_bar.html.erb new file mode 100644 index 000000000..8953900f2 --- /dev/null +++ b/app/views/content/components/_list_filter_bar.html.erb @@ -0,0 +1,82 @@ + diff --git a/app/views/content/components/_parallax_header.html.erb b/app/views/content/components/_parallax_header.html.erb new file mode 100644 index 000000000..781735fe2 --- /dev/null +++ b/app/views/content/components/_parallax_header.html.erb @@ -0,0 +1,21 @@ +
      +
        +
      • + <%= image_tag "card-headers/#{content_type.downcase.pluralize}.jpg" %> +
        +

        + <%= content_class.icon %> + <%= content_type.titleize.pluralize %> +

        +
        <%= t("content_oneliners.#{content_type.downcase}") %>
        +
        +
      • +
      +
      + +<%= content_for :javascript do %> + $('.slider').slider({ + height: 200, + indicators: false + }); +<% end %> diff --git a/app/views/content/deleted.html.erb b/app/views/content/deleted.html.erb index acfcca5d5..fcd7bd29b 100644 --- a/app/views/content/deleted.html.erb +++ b/app/views/content/deleted.html.erb @@ -1,90 +1,116 @@ -

      Your recently-deleted pages

      -

      - Pages can be "un-deleted" for up to 24 hours after deletion. - After this time, they are permanently deleted and cannot be recovered. - Use this page if you've accidentally deleted a page and need to recover it. -

      +
      -<% showed_any_content = false %> +
      +
      +
      +

      + Pages can be "un-deleted" for up to 24 hours after deletion. + After this time, they are permanently deleted and cannot be recovered. + Use this page if you've accidentally deleted a page and need to recover it. +

      +
      +
      +
      -<% @content_pages.each do |content_type_name, content_list| %> - <% next unless content_list.any? %> - <% showed_any_content = true %> -

      <%= content_type_name.pluralize %>

      +
      + <% showed_any_content = false %> - <% - content_type = content_type_name.constantize - category_ids_for_this_content_type = AttributeCategory.where(entity_type: content_type_name.downcase, user_id: current_user).pluck(:id) - name_field = AttributeField.find_by(field_type: 'name', attribute_category_id: category_ids_for_this_content_type) + <% @content_pages.each do |content_type_name, content_list| %> + <% next unless content_list.any? %> + <% showed_any_content = true %> - content_ids = content_list.pluck(:id) - if name_field - list_name_lookup_cache = Hash[ - name_field.attribute_values.where( - entity_type: content_type_name - ).pluck(:entity_id, :value) - ] - else - list_name_lookup_cache = {} - end - %> + <% + content_type = content_type_name.constantize + category_ids_for_this_content_type = AttributeCategory.where(entity_type: content_type_name.downcase, user_id: current_user).pluck(:id) + name_field = AttributeField.find_by(field_type: 'name', attribute_category_id: category_ids_for_this_content_type) -
        - <% content_list.each do |content| %> -
      • - <%= link_to content do %> - <%= content.class.icon %> - <% end %> - - <%= (content.respond_to?(:label) ? content.label : list_name_lookup_cache[content.id].presence || content.name) %> - - <% universe_field_value = content.universe_field_value %> - <% if universe_field_value.present? %> - <%= Universe.icon %> - <%# todo remove this hack %> - <% - if universe_field_value.is_a?(Integer) - universe_field_value = Universe.find_by(id: universe_field_value, user: content.user) - end - %> - <% if universe_field_value %> - <%= link_to universe_field_value.try(:name), universe_field_value %> - <% end %> - <% end %> - - <% if user_signed_in? && ( - (content.universe_field_value.present? && universe_field_value.try(:user) != current_user) || - (content.is_a?(Universe) && content.user != current_user) - ) - %> - - <% end %> - -

        - " style="font-size: 80%"> - delete - deleted <%= time_ago_in_words content.deleted_at %> ago - - " style="font-size: 80%"> - alarm - recoverable for the next <%= distance_of_time_in_words(DateTime.current, content.deleted_at + 24.hours) %> - -

        - - <%= form_for content do |f| %> - <%= f.hidden_field :deleted_at, value: nil %> - <%= f.submit 'Restore this page (undelete)', class: 'white btn black-text' %> - <% end %> - -
      • + content_ids = content_list.pluck(:id) + if name_field + list_name_lookup_cache = Hash[ + name_field.attribute_values.where( + entity_type: content_type_name + ).pluck(:entity_id, :value) + ] + else + list_name_lookup_cache = {} + end + %> + +
        +
        +

        + <%= content_type_name.pluralize %> +

        +
        +
        +
        +
        +
          + <% content_list.each do |content| %> +
        • + <%= link_to content do %> + <%= content.class.icon %> + <% end %> + + <%= (content.respond_to?(:label) ? content.label : list_name_lookup_cache[content.id].presence || content.name) %> + + <% universe_field_value = content.universe_field_value %> + <% if universe_field_value.present? %> + <%= Universe.icon %> + <%# todo remove this hack %> + <% + if universe_field_value.is_a?(Integer) + universe_field_value = Universe.find_by(id: universe_field_value, user: content.user) + end + %> + <% if universe_field_value %> + <%= link_to universe_field_value.try(:name), universe_field_value %> + <% end %> + <% end %> + + <% if user_signed_in? && ( + (content.universe_field_value.present? && universe_field_value.try(:user) != current_user) || + (content.is_a?(Universe) && content.user != current_user) + ) + %> + + <% end %> + +

          + " style="font-size: 80%"> + delete + deleted <%= time_ago_in_words content.deleted_at %> ago + + " style="font-size: 80%"> + alarm + recoverable for the next <%= distance_of_time_in_words(DateTime.current, content.deleted_at + 24.hours) %> + +

          + + <%= form_for content do |f| %> + <%= f.hidden_field :deleted_at, value: nil %> + <%= f.submit 'Recover', class: 'white btn black-text' %> + <% end %> + +
        • + <% end %> + +
        +
        +
        +
        +
        + + <% end %> + + <% if !showed_any_content %> +

        + Looks like you haven't deleted any pages in the past 24 hours. If you do, they will show up here for a limited time. +

        <% end %> -
      -<% end %> -<% if !showed_any_content %> -

      - Looks like you haven't deleted any pages in the past 24 hours. If you do, they will show up here for a limited time. -

      -<% end %> + +
      +
      diff --git a/app/views/content/display/_category_panel.html.erb b/app/views/content/display/_category_panel.html.erb index cd9e93a9d..803697fc7 100644 --- a/app/views/content/display/_category_panel.html.erb +++ b/app/views/content/display/_category_panel.html.erb @@ -1,6 +1,5 @@
      _panel" class="row panel"> <%= render partial: 'content/form/images/gallery', locals: { content: content } if category[:name] == 'gallery' %> - <%= render partial: 'content/display/changelog', locals: { content: content } if category[:name] == 'changelog' %> <%= render partial: 'content/display/contributors', locals: { content: content } if category[:name] == 'contributors' %> <% category[:fields].select { |field| !field[:hidden] }.each do |serialized_field| %> diff --git a/app/views/content/display/_changelog.html.erb b/app/views/content/display/_changelog.html.erb index 3834f3ba1..7e1492393 100644 --- a/app/views/content/display/_changelog.html.erb +++ b/app/views/content/display/_changelog.html.erb @@ -8,7 +8,7 @@ <%# todo full-page changelog with all events %>
      -
      Changelog for <%= content.name %>
      +
      Recent changes for <%= content.name %>
      • @@ -65,9 +65,19 @@ <%= (change_event.user == current_user) ? 'You' : link_to(change_event.user.name, change_event.user) %> <%= change_event.action %> - <%= key.titleize %> - <%= old_value.truncate(380) %> - <%= new_value.truncate(380) %> + <%= key.titleize %> + + <%= simple_format ContentFormatterService.show( + text: old_value.truncate(380), + viewing_user: current_user + ) %> + + + <%= simple_format ContentFormatterService.show( + text: new_value.truncate(380), + viewing_user: current_user + ) %> + <%= time_ago_in_words change_event.created_at %> ago <% end %> diff --git a/app/views/content/display/_quick_reference.html.erb b/app/views/content/display/_quick_reference.html.erb index 4ed8a472f..d6e628c88 100644 --- a/app/views/content/display/_quick_reference.html.erb +++ b/app/views/content/display/_quick_reference.html.erb @@ -1,7 +1,6 @@ <%# Usage: render partial: 'content/display/quick_reference', locals: { content: @content } %> -<%# - TODO: this needs optimized. Last count it was doing 55 SQL queries, so it has been temporarily - disabled (not called from dashboard.html.erb). +<% + serialized_content = ContentSerializer.new(content) %>

        @@ -15,43 +14,35 @@ <% end %> <% end %>

        -
        <%= content.description %>
        -<% all_categories = content.class.attribute_categories(current_user) %> -<% found_attributes = 0 %> -<% attributes_to_find = 5 %> - - - <% all_categories.each do |category| %> - <% break if found_attributes >= attributes_to_find %> - <% category.attribute_fields.each do |attribute_field| %> - <% break if found_attributes >= attributes_to_find %> - - <% next unless attribute_field.name.present? %> - <% next if attribute_field.name.end_with? '_id' %> - <% next if attribute_field.name == 'privacy' %> - <% next if ['name', 'description'].include?(attribute_field.name) %> - - <% next unless content.respond_to? attribute_field.name %> - <% next unless content.send(attribute_field.name).present? %> - <% next if content.send(attribute_field.name).is_a?(ActiveRecord::Associations::CollectionProxy) %> - - <% found_attributes += 1 %> - - - - - <% end %> - <% end %> - <% if found_attributes < attributes_to_find %> - - - +
          + <% serialized_content.data[:categories].each do |category| %> + <% next if ['changelog'].include?(category[:name]) %> + <% next unless category[:fields].any? { |field| field[:value].present? } %> +
        • +
          + <%= category[:icon] %> + <%= category[:label] %> +
          +
          + +
        -
        - <%= attribute_field.label %> -
        -
        <%= content.send(attribute_field.name) %>
        - More information will automatically appear here as you add it to <%= content.name %>. -
        + <% category[:fields].each do |field| %> + <% next unless field[:value].present? %> + + + + + <% end %> +
        <%= field[:label] %> + <% if field[:type] == 'universe' %> + <%= link_to serialized_content.data[:universe][:name], universe_path(field[:value]) %> + <% else %> + <%= field[:value] %> + <% end %> +
        + +
      +
    • <% end %> - +
    diff --git a/app/views/content/display/_sidelinks.html.erb b/app/views/content/display/_sidelinks.html.erb index eb2fee27d..343263d74 100644 --- a/app/views/content/display/_sidelinks.html.erb +++ b/app/views/content/display/_sidelinks.html.erb @@ -30,13 +30,8 @@ %> <% categories.each do |category| %> <% - # Don't show changelog tab on create/edit form - next if (creating || editing) && category[:name] == 'changelog' - if creating || editing # Show everything on create/edit forms - elsif category[:name] == 'changelog' - # Show changelog on show page elsif category[:name] == 'contributors' # Show contributors on show page if there are any to show next if raw_model.contributors.empty? diff --git a/app/views/content/form/_panel.html.erb b/app/views/content/form/_panel.html.erb index 16e128eb9..b3fcad8fe 100644 --- a/app/views/content/form/_panel.html.erb +++ b/app/views/content/form/_panel.html.erb @@ -3,7 +3,6 @@ raw_model = content.is_a?(ContentSerializer) ? content.raw_model : content %> -
    _panel" class="row panel" style="display: none"> <% if category[:name] == 'gallery' %> <%= render partial: 'content/form/gallery/panel', locals: { f: f, content: content } %> @@ -64,7 +63,7 @@ select_tag "#{raw_model.class.name.downcase}[custom_attribute_values][][value]", options_for_select( @universe_dropdown_options.compact, - content.universe.try(:id) + content.is_a?(ContentSerializer) ? content.universe.try(:id) : @universe_scope.try(:id) ), include_blank: current_user.on_premium_plan? || raw_model.is_a?(Character) || raw_model.is_a?(Location) || raw_model.is_a?(Item) %> diff --git a/app/views/content/index.html.erb b/app/views/content/index.html.erb index db53b99ae..a9bad32a8 100644 --- a/app/views/content/index.html.erb +++ b/app/views/content/index.html.erb @@ -2,33 +2,15 @@ content_type = @content_type_class.name.downcase %> -
    -
      -
    • - <%= image_tag "card-headers/#{content_type.pluralize}.jpg" %> -
      -

      <%= content_type.titleize.pluralize %>

      -
      <%= t("content_oneliners.#{content_type}") %>
      -
      -
    • -
    -
    - - +<%= content_for :full_width_page_header do %> + <%= render partial: 'content/components/parallax_header', locals: { content_type: content_type, content_class: @content_type_class } %> +<% end %> <% if @content.any? %> -

    - Your <%= pluralize(@content.count, content_type) %> - <%= render partial: 'content/list/actions', locals: { } %> -

    - <%= render partial: 'content/list/list', locals: { content_list: @content, content_type: @content_type_class, show_add_another_form: true } %> + <%= render partial: 'content/components/list_filter_bar', locals: { } %> +
    + <%= render partial: 'content/list/list', locals: { content_list: @content, content_type: @content_type_class, show_add_another_form: true } %> +
    <% elsif @content.empty? %> diff --git a/app/views/content/list/_actions.html.erb b/app/views/content/list/_actions.html.erb index 0ab81f1f3..487d6a9ef 100644 --- a/app/views/content/list/_actions.html.erb +++ b/app/views/content/list/_actions.html.erb @@ -1,13 +1,5 @@ -<%= render partial: 'content/list/create_button', locals: { } %> - -<% if @content.count > 0 %> - - <%= link_to attribute_customization_path(@content_type_class.name.downcase), - class: "btn white #{@content_type_class.color}-text tooltipped", - data: { position: "bottom", tooltip: "Customize categories and fields" } do %> - Customize this kind of page - <% end %> - +<%= link_to attribute_customization_path(@content_type_class.name.downcase), + class: "btn white #{@content_type_class.color}-text tooltipped", + data: { position: "bottom", tooltip: "Customize categories and fields" } do %> + Customize template <% end %> - -
    diff --git a/app/views/content/list/_list.html.erb b/app/views/content/list/_list.html.erb index 0ac06680a..465e3c990 100644 --- a/app/views/content/list/_list.html.erb +++ b/app/views/content/list/_list.html.erb @@ -53,11 +53,7 @@ data-position="bottom" data-delay="100" data-tooltip="You have been added as a contributor to this universe and its content."> <% end %> -

    - <%# content.description %> -

    - <% if user_signed_in? %> " style="font-size: 80%"> mode_edit diff --git a/app/views/customization/content_types.html.erb b/app/views/customization/content_types.html.erb index 1f0f8c611..76067b527 100644 --- a/app/views/customization/content_types.html.erb +++ b/app/views/customization/content_types.html.erb @@ -1,28 +1,41 @@

    -
      +
      • -
        settings Customize your notebook pages
        +
        settings Customize your notebook pages

        Below, you can turn on or off any page types in Notebook.ai. You won't lose any pages you've created in any of them even if you turn them off; you can always turn them back on again - and your lovely pages will be there. + and your lovely pages will still be there.

        - Simply click the switch next to any page type to turn it on or off. After you refresh any page, - you'll see only the page types you have turned on as links in your sidebar. + Simply click any page you'd like to turn on or off. Pages that are in black and white and blurred + are turned off (hidden), and pages that are clear and in color are turned on and ready to use!

        - You can also turn on premium-only content here (and are free to view, edit, and share your - existing premium content, even if you don't have an active subscription!), but you won't be - able to create additional premium content without a premium subscription, even if - you turn it on here. + Happy worldbuilding!

        +
        +
        + <%= image_tag 'tristan/small.png' %> +
        +
        +
        +
      • +
      • +
        help What pages are available to me on my current billing plan?
        +
        +
        +

        - Happy worldbuilding! + <% if current_user.on_premium_plan? %> + You're on a Premium plan! All pages are available to you! + <% else %> + You're on a free Starter plan. You can create unlimited Characters, Locations, and Items. You can also create up to 5 Universes. + <% end %>

        @@ -32,24 +45,24 @@
      • -
        help Having a problem turning pages on or off?
        +
        help Why can I turn on pages I don't have access to?
        -

        - - Some users are currently having difficulties turning pages on or off when using Internet Explorer - to view this page. - -

        -

        - If you are having difficulties while using Internet Explorer, you may wish to temporarily try another browser like - Google Chrome or Mozilla Firefox to turn pages on or off. Once the pages are configured to your liking, - the rest of the site should continue work in Internet Explorer just fine. -

        -

        - If you do not have another browser to customize your pages with, feel free to email me at - andrew@indentlabs.com and I'd be happy to turn everything - on for you manually. -

        +
        +
        +

        + You can turn on Premium-only content here to quickly access any existing pages you have of that type. For example, + if you created a dozen Creatures while on Premium, you'll always be able to turn on Creatures here and get back to + those pages. +

        +

        + As a reminder, you'll always have access to every page you've ever created, whether you're on Premium or not. They're + your pages! +

        +
        +
        + <%= image_tag 'tristan/small.png' %> +
        +
      @@ -57,81 +70,27 @@
    - <% @all_content_types.each.with_index do |content_type, i| %> - -
    -
    -
    - <%= image_tag "card-headers/#{content_type.name.downcase.pluralize}.jpg", height: 200, width: 300 %> - <% if Rails.application.config.content_types[:new].include?(content_type) %> - - - - <% end %> - - - <% if content_type.name == 'Universe' %> -
    - Always on -
    - <% else %> - <%= form_tag customization_toggle_content_type_path, method: :POST, remote: true do %> -
    - -
    - <% end %> - <% end %> - <% end %> +
    -
    +
    +
    <%= image_tag "card-headers/more.jpg", height: 200, width: 300 %> @@ -149,16 +108,14 @@ We're adding more page types soon so you can customize your digital notebook to match your world — not the other way around.

    -
    -

    - Have something in mind you're dying to plan in Notebook.ai? - <%= link_to 'https://docs.google.com/forms/d/1PFOaa97Cu3vrceUvcuFT6nyITaMwR-4wQSarUdVoPSg/edit' do %> - You can request new pages to be added with this form! - <% end %> -

    +
    + <%= link_to 'https://docs.google.com/forms/d/1PFOaa97Cu3vrceUvcuFT6nyITaMwR-4wQSarUdVoPSg/edit', target: '_new' do %> + Request a new page type + <% end %> +
    diff --git a/app/views/devise/passwords/new.html.erb b/app/views/devise/passwords/new.html.erb index be998ea86..09fe087cd 100644 --- a/app/views/devise/passwords/new.html.erb +++ b/app/views/devise/passwords/new.html.erb @@ -1,23 +1,25 @@ -

    Forgot your password?

    +
    +
    +
    +
    +

    Forgot your password?

    + <%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :post }) do |f| %> + <%= devise_error_messages! %> -
    -
    - <%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :post }) do |f| %> - <%= devise_error_messages! %> +
    + <%= f.label 'Enter the email associated with your account' %>
    + <%= f.email_field :email, autofocus: true %> +
    -
    - <%= f.label 'Enter the email associated with your account' %>
    - <%= f.email_field :email, autofocus: true %> +
    + <%= f.submit "Send me reset password instructions", class: 'btn blue' %> +
    +

    +
    + <%= render "devise/shared/links" %> +

    + <% end %>
    - -
    - <%= f.submit "Send me reset password instructions", class: 'btn' %> -
    -

    -
    - <%= render "devise/shared/links" %> -

    - <% end %> +
    - diff --git a/app/views/devise/registrations/edit.html.erb b/app/views/devise/registrations/edit.html.erb index 0bb149f4c..9b5387c29 100644 --- a/app/views/devise/registrations/edit.html.erb +++ b/app/views/devise/registrations/edit.html.erb @@ -1,31 +1,29 @@ -
    - <%= form_for(resource, as: resource_name, url: registration_path(resource_name), html: { method: :put }) do |f| %> - <%= devise_error_messages! %> +<%= form_for(resource, as: resource_name, url: registration_path(resource_name), html: { method: :put }) do |f| %> + <%= devise_error_messages! %> -
    - -
    - <%= render partial: 'devise/registrations/panes/information', locals: { f: f } %> -
    -
    - <%= render partial: 'devise/registrations/panes/preferences', locals: { f: f } %> -
    -
    - <%= render partial: 'devise/registrations/panes/more', locals: { f: f } %> -
    +
    + +
    + <%= render partial: 'devise/registrations/panes/information', locals: { f: f } %> +
    +
    + <%= render partial: 'devise/registrations/panes/preferences', locals: { f: f } %> +
    +
    + <%= render partial: 'devise/registrations/panes/more', locals: { f: f } %> +
    +
    -
    -
    - <%= f.submit "Save changes", class: 'btn blue' %> - <%= link_to "Cancel", :back, class: 'btn grey' %> -
    +
    +
    + <%= f.submit "Save changes", class: 'btn blue' %> + <%= link_to "Cancel", :back, class: 'btn grey' %>
    - <% end %> -
    +
    +<% end %> diff --git a/app/views/devise/registrations/new.html.erb b/app/views/devise/registrations/new.html.erb index 09deac819..bdfab494d 100644 --- a/app/views/devise/registrations/new.html.erb +++ b/app/views/devise/registrations/new.html.erb @@ -1,79 +1,84 @@ -

    Sign up for Notebook

    +
    +
    + <%= form_for(resource, as: resource_name, url: registration_path(resource_name)) do |f| %> + <%= devise_error_messages! %> -<%= form_for(resource, as: resource_name, url: registration_path(resource_name)) do |f| %> - <%= devise_error_messages! %> - -
    -
    +
    +
    +
    +

    Sign up for Notebook.ai

    +
    -
    - <%= f.label 'Your name' %>
    - <%= f.text_field :name, autofocus: true %> -
    +
    + <%= f.label 'Your name' %>
    + <%= f.text_field :name, autofocus: true %> +
    -
    - <%= f.label :email %> (This is the email you will log in with)
    - <%= f.email_field :email %> -
    +
    + <%= f.label :email %> (This is the email you will log in with)
    + <%= f.email_field :email %> +
    -
    - <%= f.label :password %> - <% if @minimum_password_length %> - (<%= @minimum_password_length %> characters minimum) - <% end %>
    - <%= f.password_field :password, autocomplete: "off" %> -
    +
    + <%= f.label :password %> + <% if @minimum_password_length %> + (<%= @minimum_password_length %> characters minimum) + <% end %>
    + <%= f.password_field :password, autocomplete: "off" %> +
    -
    - <%= f.label :password_confirmation %>
    - <%= f.password_field :password_confirmation, autocomplete: "off" %> -
    +
    + <%= f.label :password_confirmation %>
    + <%= f.password_field :password_confirmation, autocomplete: "off" %> +
    - + - <% - if params.key?('referral') || session.key?('referral') - referral_code = params['referral'] || session['referral'] - referrer = ReferralCode.where(code: referral_code).first - if referrer.present? - %> -
    -
    -
    - <%= f.label :referral_code %>
    - <%= f.text_field :referral_code, value: referral_code, readonly: true %> + <% + if params.key?('referral') || session.key?('referral') + referral_code = params['referral'] || session['referral'] + referrer = ReferralCode.where(code: referral_code).first + if referrer.present? + %> +
    +
    +
    + <%= f.label :referral_code %>
    + <%= f.text_field :referral_code, value: referral_code, readonly: true %> +
    +
    +
    + <%= f.label 'The following user will receive credit for referring you' %>
    + <%= f.text_field :referral_user, value: referrer.user.name.split('@').first, disabled: "disabled" %> +
    -
    -
    - <%= f.label 'The following user will receive credit for referring you' %>
    - <%= f.text_field :referral_user, value: referrer.user.name.split('@').first, disabled: "disabled" %> -
    -
    - <% - end - end - %> + <% + end + end + %> -
    - <%= f.label :email_updates do %> - <%= f.check_box :email_updates %> - We're always working to improve Notebook.ai. Please leave this box checked if you'd like to receive occasional updates about - what's new. - <% end %> -
    +
    + <%= f.label :email_updates do %> + <%= f.check_box :email_updates %> + We're always working to improve Notebook.ai. Please leave this box checked if you'd like to receive occasional updates about + what's new. + <% end %> +
    -
    - <%= f.submit "Sign up", class: 'btn blue' %> -

    -
    - <%= render "devise/shared/links" %> -

    +
    + <%= f.submit "Sign up", class: 'btn blue' %> +

    +
    + <%= render "devise/shared/links" %> +

    +
    +
    -
    + <% end %>
    -<% end %> +
    diff --git a/app/views/devise/registrations/panes/_information.html.erb b/app/views/devise/registrations/panes/_information.html.erb index 76fcd4e82..98dfc1a94 100644 --- a/app/views/devise/registrations/panes/_information.html.erb +++ b/app/views/devise/registrations/panes/_information.html.erb @@ -1,19 +1,97 @@ -
    -
    -

    Personal information

    -
    - <%= f.label 'Name (visible on your profile and forum posts)' %>
    - <%= f.text_field :name, autofocus: true %> +
    +
    +

    Public information

    +

    + This information is visible to other users. +

    +
    +
    +
    +
    +
    + <%= f.label 'Name (visible on your profile and forum posts)' %>
    + <%= f.text_field :name, autofocus: true %> +
    + +
    + <%= f.label 'Username (users can @mention you with your username on the forums)' %>
    + <%= f.text_field :username %> +
    +
    -
    - <%= f.label 'Email (always completely private)' %>
    - <%= f.email_field :email %> +
    +
    +
    + <%= f.text_area :bio, class: 'materialize-textarea with-character-counter', data: { length: 500 } %> + <%= f.label 'Bio' %>
    +
    + +
    + <%= f.text_field :favorite_genre, class: 'materialize-textarea' %> + <%= f.label 'Favorite genre' %>
    +
    + +
    + <%= f.text_field :favorite_author, class: 'materialize-textarea' %> + <%= f.label 'Favorite author' %>
    +
    + +
    + <%= f.text_field :interests, class: 'materialize-textarea' %> + <%= f.label 'Interests' %>
    +
    +
    +
    +
    -
    - <%= f.label 'Username (users can @mention you with your username on the forums)' %>
    - <%= f.text_field :username %> +
    +
    +

    Private information

    +

    + This information is only ever visible to you. +

    +

    + Notebook.ai will never share this information, but may also look at it to better understand its users. +

    +
    + +
    +
    +
    +
    + <%= f.label 'Email (always completely private)' %>
    + <%= f.email_field :email %> +
    +
    +
    + +
    +
    +
    + <%= f.text_field :age, class: 'materialize-textarea' %> + <%= f.label 'Age' %>
    +
    + +
    + <%= f.text_field :location, class: 'materialize-textarea' %> + <%= f.label 'Location' %>
    +
    + +
    + <%= f.text_field :gender, class: 'materialize-textarea' %> + <%= f.label 'Gender' %>
    +
    +
    +
    + +
    +
    + Last login + <%= time_ago_in_words current_user.current_sign_in_at %> ago + from IP <%= current_user.current_sign_in_ip %>. +
    @@ -22,17 +100,32 @@
    Currently waiting confirmation for: <%= resource.unconfirmed_email %>
    <% end %> -
    -
    -

    Changing your password

    -
    - <%= f.label :password %> (leave blank if you don't want to change it)
    - <%= f.password_field :password, autocomplete: "off" %> -
    +
    +
    +

    Password change

    +

    + Leave this blank unless you want to change your password. +

    +
    +
    +
    +
    +
    + <%= f.label 'New password' %>
    + <%= f.password_field :password, autocomplete: "off" %> +
    -
    - <%= f.label :password_confirmation %>
    - <%= f.password_field :password_confirmation, autocomplete: "off" %> +
    + <%= f.label 'New password (again)' %>
    + <%= f.password_field :password_confirmation, autocomplete: "off" %> +
    +
    + +<%= content_for :javascript do %> + $(document).ready(function() { + $('.with-character-counter').characterCounter(); + }); +<% end %> diff --git a/app/views/devise/sessions/new.html.erb b/app/views/devise/sessions/new.html.erb index 61f4c2c2d..00cb9cbf2 100644 --- a/app/views/devise/sessions/new.html.erb +++ b/app/views/devise/sessions/new.html.erb @@ -1,14 +1,11 @@ -
    - <%= image_tag 'logos/both-small.png', class: 'hide-on-small-only' %> - <%= image_tag 'logos/book-small.png', class: 'hide-on-med-and-up' %> -
    -
    + <%= image_tag 'logos/both-small.png', class: 'hide-on-small-only', style: 'width: 100%' %> + <%= image_tag 'logos/book-small.png', class: 'hide-on-med-and-up', style: 'width: 100%' %>
    <%= render 'devise/sessions/form' %>
    -
    \ No newline at end of file +
    diff --git a/app/views/documents/components/_autosave_bar.html.erb b/app/views/documents/components/_autosave_bar.html.erb new file mode 100644 index 000000000..2dd1f38c1 --- /dev/null +++ b/app/views/documents/components/_autosave_bar.html.erb @@ -0,0 +1,12 @@ +
    +
    +
    + + save + + This document will automatically save as you make changes. + + +
    +
    +
    diff --git a/app/views/documents/components/_document_name_bar.html.erb b/app/views/documents/components/_document_name_bar.html.erb new file mode 100644 index 000000000..0b7feca8d --- /dev/null +++ b/app/views/documents/components/_document_name_bar.html.erb @@ -0,0 +1,18 @@ +
    +
    +
    + <% if defined?(f) %> + Editing +
    + <%= + f.text_field :title, + placeholder: 'Untitled document', + value: document.try(:name) || 'Untitled document', + class: 'white-text', + style: 'font-size: 150%; border-bottom: 1px solid white;' + %> +
    + <% end %> +
    +
    +
    diff --git a/app/views/documents/components/_smart_sidebar.html.erb b/app/views/documents/components/_smart_sidebar.html.erb new file mode 100644 index 000000000..16a2cb8e1 --- /dev/null +++ b/app/views/documents/components/_smart_sidebar.html.erb @@ -0,0 +1,44 @@ +<% if current_user && @document.updatable_by?(current_user) %> +
    +
    + + This document + settings + +
      +
    • · Written by <%= link_to @document.user.name, @document.user %> + +
    • · Created <%= time_ago_in_words @document.created_at %> ago
    • +
    • · Last edited <%= time_ago_in_words @document.updated_at %> ago
    • +
    +

    + This card is only visible to you. +

    +
    +
    + + Settingsclose + +
      +
    • + <% if @document.persisted? && current_user.can_delete?(@document) %> + <%= link_to @document, + method: :delete, + class: 'small btn red white-text', + data: { + confirm: "Are you sure? This will permanently delete this entire document!" + } do + %> + Delete this document + <% end %> + <% end %> +
    • +
    +
    +
    +<% end %> diff --git a/app/views/documents/edit.html.erb b/app/views/documents/edit.html.erb index c42e9c45d..461397f8c 100644 --- a/app/views/documents/edit.html.erb +++ b/app/views/documents/edit.html.erb @@ -1,20 +1,24 @@ <%= form_for @document do |f| %> -
    -
    - save - - This document will automatically save as you make changes. - + <%= content_for :full_width_page_header do %> + <%= render partial: 'documents/components/document_name_bar', locals: { document: @document, f: f } %> + <%= render partial: 'documents/components/autosave_bar', locals: { document: @document } %> + +
    +
    +
    <%= @document.body.try(:html_safe) %>
    +
    +
    + <%= render partial: 'documents/components/smart_sidebar', locals: { document: @document } %> +
    - <%= f.text_field :title, placeholder: 'Untitled document', value: f.object.title.presence || 'Untitled document', style: 'font-size: 150%' %> -
    + <% end %> -
    <%= @document.body.try(:html_safe) %>
    save - This document will automatically save as you make changes. It will also expand as you write! + This document will automatically save as you make changes. + Highlight any text to bring up formatting options.
    <% end %> diff --git a/app/views/documents/index.html.erb b/app/views/documents/index.html.erb index 06313ef86..975dff70c 100644 --- a/app/views/documents/index.html.erb +++ b/app/views/documents/index.html.erb @@ -1,16 +1,6 @@ <% if @documents.any? %> -
    -
    -

    -
    - <%= link_to edit_document_path(:new), class: 'btn green white-text waves-effect waves-light', style: 'height: 45px' do %> - add New Document - <% end %> -
    - Your <%= current_user.documents.count %> documents -

    -
    -
    + <%= render partial: 'content/components/list_filter_bar', locals: { } %> +
    <% @documents.each.with_index do |document, i| %> <% if i % 3 == 0 %> @@ -33,19 +23,12 @@ ago

    -
    - <%= link_to edit_document_path(document), class: 'green-text' do %> +
    @@ -64,18 +47,21 @@ <% end %> <% if @documents.empty? %> -
    -

    You haven't created any documents yet!

    -

    - - <%= Document.icon %> - -

    -

    - You can create an unlimited number of documents with no limits on length. Enjoy! -

    - - <%= link_to "Create your first document", edit_document_path(:new), class: "btn #{Document.color}" %> - +
    +
    +
    +

    You haven't created any documents yet!

    +

    + + <%= Document.icon %> + +

    +

    + You can create an unlimited number of documents with no limits on length. Enjoy! +

    +
    + <%= link_to "Create your first document", edit_document_path(:new), class: "btn #{Document.color}" %> +
    +
    <% end %> diff --git a/app/views/documents/show.html.erb b/app/views/documents/show.html.erb new file mode 100644 index 000000000..e02ab48ef --- /dev/null +++ b/app/views/documents/show.html.erb @@ -0,0 +1,23 @@ +<%= content_for :full_width_page_header do %> + <%= render partial: 'documents/components/document_name_bar', locals: { document: @document } %> + <%= render partial: 'documents/components/autosave_bar', locals: { document: @document } %> + +
    +
    +
    <%= @document.body.try(:html_safe) || 'This document is blank.' %>
    +
    +
    + <%= render partial: 'documents/components/smart_sidebar', locals: { document: @document } %> + + <%= link_to edit_document_path(@document) do %> +
    +
    + + Edit this document + +
    +
    + <% end %> +
    +
    +<% end %> diff --git a/app/views/layouts/_footer.html.erb b/app/views/layouts/_footer.html.erb index 15c1fdc2e..e36f5d306 100644 --- a/app/views/layouts/_footer.html.erb +++ b/app/views/layouts/_footer.html.erb @@ -1,5 +1,4 @@ -