From 9f29ffc8c36c1555e0e0eb01efa1f2305a06c735 Mon Sep 17 00:00:00 2001 From: albert Date: Fri, 12 Mar 2010 12:32:31 -0500 Subject: [PATCH] work on post views --- app/controllers/sessions_controller.rb | 10 +- app/logical/anonymous_user.rb | 4 + app/logical/post_set.rb | 4 + app/models/user.rb | 10 +- app/presenters/post_set_presenter.rb | 36 +++ app/views/layouts/default.html.erb | 13 +- app/views/posts/index.html.erb | 97 +++++++ app/views/sessions/new.html.erb | 12 +- app/views/users/edit.html.erb | 67 +++++ app/views/users/show.html.erb | 9 +- config/routes.rb | 2 +- public/index.html | 278 -------------------- public/javascripts/posts/index.js | 17 -- public/javascripts/{ => src}/application.js | 6 +- public/javascripts/src/cookie.js | 58 ++++ public/javascripts/src/posts/index.js | 168 ++++++++++++ public/javascripts/{ => src}/rails.js | 0 script/compile_javascripts | 12 + 18 files changed, 486 insertions(+), 317 deletions(-) create mode 100644 app/presenters/post_set_presenter.rb delete mode 100644 public/index.html delete mode 100644 public/javascripts/posts/index.js rename public/javascripts/{ => src}/application.js (56%) create mode 100644 public/javascripts/src/cookie.js create mode 100644 public/javascripts/src/posts/index.js rename public/javascripts/{ => src}/rails.js (100%) create mode 100644 script/compile_javascripts diff --git a/app/controllers/sessions_controller.rb b/app/controllers/sessions_controller.rb index 8081c879b..13c6e987e 100644 --- a/app/controllers/sessions_controller.rb +++ b/app/controllers/sessions_controller.rb @@ -1,6 +1,4 @@ class SessionsController < ApplicationController - before_filter :member_only, :only => [:destroy] - def new @user = User.new end @@ -9,14 +7,14 @@ class SessionsController < ApplicationController if User.authenticate(params[:name], params[:password]) @user = User.find_by_name(params[:name]) session[:user_id] = @user.id - redirect_to(params[:url] || posts_path, :notice => "You have logged in") + redirect_to(params[:url] || posts_path, :notice => "You are now logged in.") else - render :action => "edit", :flash => "Password was incorrect" + redirect_to(new_session_path, :notice => "Password was incorrect.") end end def destroy - session[:user_id] = nil - redirect_to(posts_path, :notice => "You have logged out") + session.delete(:user_id) + redirect_to(posts_path, :notice => "You are now logged out.") end end diff --git a/app/logical/anonymous_user.rb b/app/logical/anonymous_user.rb index 63d16ea0d..d60ab45bf 100644 --- a/app/logical/anonymous_user.rb +++ b/app/logical/anonymous_user.rb @@ -96,6 +96,10 @@ class AnonymousUser false end + def blacklisted_tags + "" + end + %w(banned privileged contributor janitor moderator admin).each do |name, value| normalized_name = name.downcase.gsub(/ /, "_") diff --git a/app/logical/post_set.rb b/app/logical/post_set.rb index b525a88eb..5a92bb53f 100644 --- a/app/logical/post_set.rb +++ b/app/logical/post_set.rb @@ -102,4 +102,8 @@ class PostSet def to_json posts.to_json end + + def presenter + @presnter ||= PostSetPresenter.new(self) + end end diff --git a/app/models/user.rb b/app/models/user.rb index 427db4d3e..55c1ebda8 100644 --- a/app/models/user.rb +++ b/app/models/user.rb @@ -3,13 +3,13 @@ require 'digest/sha1' class User < ActiveRecord::Base class Error < Exception ; end - attr_accessor :password - attr_accessible :password, :password_confirmation, :password_hash, :email, :last_logged_in_at, :last_forum_read_at, :has_mail, :receive_email_notifications, :comment_threshold, :always_resize_images, :favorite_tags, :blacklisted_tags, :name + attr_accessor :password, :old_password + attr_accessible :password, :old_password, :password_confirmation, :password_hash, :email, :last_logged_in_at, :last_forum_read_at, :has_mail, :receive_email_notifications, :comment_threshold, :always_resize_images, :favorite_tags, :blacklisted_tags, :name validates_length_of :name, :within => 2..20, :on => :create validates_format_of :name, :with => /\A[^\s;,]+\Z/, :on => :create, :message => "cannot have whitespace, commas, or semicolons" validates_uniqueness_of :name, :case_sensitive => false, :on => :create validates_uniqueness_of :email, :case_sensitive => false, :on => :create, :if => lambda {|rec| !rec.email.blank?} - validates_length_of :password, :minimum => 5, :if => lambda {|rec| rec.new_record? || rec.password} + validates_length_of :password, :minimum => 5, :if => lambda {|rec| rec.new_record? || !rec.password.blank?} validates_inclusion_of :default_image_size, :in => %w(medium large original) validates_confirmation_of :password validates_presence_of :email, :if => lambda {|rec| rec.new_record? && Danbooru.config.enable_email_verification?} @@ -176,6 +176,10 @@ class User < ActiveRecord::Base include EmailVerificationMethods include BlacklistMethods include ForumMethods + + def initialize_default_image_size + self.default_image_size = "Medium" + end def can_update?(object, foreign_key = :user_id) is_moderator? || is_admin? || object.__send__(foreign_key) == id diff --git a/app/presenters/post_set_presenter.rb b/app/presenters/post_set_presenter.rb new file mode 100644 index 000000000..b04c6b9b8 --- /dev/null +++ b/app/presenters/post_set_presenter.rb @@ -0,0 +1,36 @@ +class PostSetPresenter + attr_accessor :post_set + + def initialize(post_set) + @post_set = post_set + end + + def posts + post_set.posts + end + + def tag_list_html + "" + end + + def wiki_html + "" + end + + def pagination_html + end + + def post_previews_html + html = "" + + posts.each do |post| + html << %{
} + html << %{} + html << %{} + html << %{
} + end + + html + end +end diff --git a/app/views/layouts/default.html.erb b/app/views/layouts/default.html.erb index 23ac4a8e7..165b18ea3 100644 --- a/app/views/layouts/default.html.erb +++ b/app/views/layouts/default.html.erb @@ -4,16 +4,21 @@ <%= yield(:page_title) || Danbooru.config.app_name %> + <%= csrf_meta_tag %> + <% unless @current_user.blacklisted_tags.blank? %> + + <% end %> <%= auto_discovery_link_tag :atom, posts_path(:format => "atom", :tags => params[:tags]) %> <%= stylesheet_link_tag "default" %> <%= javascript_include_tag "http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js" %> + <%= javascript_include_tag "rails" %> <%= Danbooru.config.custom_html_header_content %> <%= yield :html_header_content %> @@ -61,9 +66,9 @@ <% end %> -
+
<%= yield :layout %> -
+ <%= yield :page_footer_content %> diff --git a/app/views/posts/index.html.erb b/app/views/posts/index.html.erb index e69de29bb..45ddf0c5a 100644 --- a/app/views/posts/index.html.erb +++ b/app/views/posts/index.html.erb @@ -0,0 +1,97 @@ +<% unless @post_set.suggestions.blank? %> +
+ Maybe you meant: <%= @post_set.suggestions.map {|x| link_to(x, posts_path(:tags => x), :class => "tag-type-#{Tag.type_name(x)}" )}.to_sentence(:last_word_connector => ", or ", :two_words_connector => " or ") %> +
+<% end %> + + + +
+

Posts

+ <%= @post_set.presenter.post_previews_html %> +
+ +
+ <%= @post_set.presenter.pagination_html %> +
+ +<% content_for(:page_title) do %> + /<%= @post_set.tags %> +<% end %> + +<% content_for(:page_header) do %> + / <%= @post_set.tags %> +<% end %> + +<% content_for(:secondary_nav_links) do %> + +
  • Listing
  • +
  • Upload
  • +
  • Popular
  • +
  • Favorites
  • +
  • Subscriptions
  • +
  • Changes
  • +
  • Approvals
  • +
  • Moderate
  • +
  • Help
  • +
    +<% end %> diff --git a/app/views/sessions/new.html.erb b/app/views/sessions/new.html.erb index 3a0e24c9d..a10eadbae 100644 --- a/app/views/sessions/new.html.erb +++ b/app/views/sessions/new.html.erb @@ -19,10 +19,18 @@ + +<% content_for(:page_title) do %> +login +<% end %> + +<% content_for(:page_header) do %> + / login +<% end %> diff --git a/app/views/users/edit.html.erb b/app/views/users/edit.html.erb index d3c95f1d5..ae8ec74a3 100644 --- a/app/views/users/edit.html.erb +++ b/app/views/users/edit.html.erb @@ -1,3 +1,70 @@ +<% form_for @user do |f| %> +
    + Basic + +

    + <%= f.label :email %> + <%= f.text_field :email %> +

    + +

    + <%= f.label :receive_email_notifications, "Email notifications" %> + <%= f.check_box :receive_email_notifications %> +

    + +

    + <%= f.label :comment_threshold %> + <%= f.text_field :comment_threshold, :size => 2 %> +

    + +

    + <%= f.label :always_resize_images %> + <%= f.check_box :always_resize_images %> +

    + +

    + <%= f.label :default_image_size %> + <%= f.select :default_image_size, %w(Medium Large Original) %> +

    + +

    + <%= f.label :favorite_tags %> + <%= f.text_area :favorite_tags, :rows => 5 %> +

    + +

    + <%= f.label :blacklisted_tags %> + <%= f.text_area :blacklisted_tags, :rows => 5 %> +

    +
    + +
    + SpecialFor security purposes, changing the following settings requires you to re-enter your password. You can leave the new password field blank to keep your current one.

    + +

    + <%= f.label :name %> + <%= f.text_field :name %> +

    + +

    + <%= f.label :password, "New password" %> + <%= f.text_field :password %> +

    + +

    + <%= f.label :old_password %> + <%= f.text_field :old_password %> +

    +
    + + <%= submit_tag "Submit" %> +<% end %> + +<% content_for(:page_title) do %> + /<%= @user.name %>/Settings +<% end %> + <% content_for(:page_header) do %> / <%= @user.name %> / Settings <% end %> diff --git a/app/views/users/show.html.erb b/app/views/users/show.html.erb index 0239a8047..3632ad0bd 100644 --- a/app/views/users/show.html.erb +++ b/app/views/users/show.html.erb @@ -1,11 +1,14 @@ -

    <%= @user.name %>

    - +<% content_for(:page_title) do %> + users/<%= @user.name %> +<% end %> + <% content_for(:page_header) do %> / <%= @user.name %> -<% end %> \ No newline at end of file +<% end %> diff --git a/config/routes.rb b/config/routes.rb index 61ae49505..cb853117b 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -56,5 +56,5 @@ Danbooru::Application.routes.draw do |map| match "/user_maintenance/login_reminder" => "user_maintenance#login_reminder", :as => "login_reminder_info" match "/user_maintenance/reset_password" => "user_maintenance#reset_password", :as => "reset_password_info" - root :to => "post#index" + root :to => "posts#index" end diff --git a/public/index.html b/public/index.html deleted file mode 100644 index ef916f9c5..000000000 --- a/public/index.html +++ /dev/null @@ -1,278 +0,0 @@ - - - - Ruby on Rails: Welcome aboard - - - - - - -
    - - -
    - - - - -
    -

    Getting started

    -

    Here’s how to get rolling:

    - -
      -
    1. -

      Use rails generate to create your models and controllers

      -

      To see all available options, run it without parameters.

      -
    2. - -
    3. -

      Set up a default route and remove or rename this file

      -

      Routes are set up in config/routes.rb.

      -
    4. - -
    5. -

      Create your database

      -

      Run rake db:migrate to create your database. If you're not using SQLite (the default), edit config/database.yml with your username and password.

      -
    6. -
    -
    -
    - - -
    - - diff --git a/public/javascripts/posts/index.js b/public/javascripts/posts/index.js deleted file mode 100644 index 23bc2d7ac..000000000 --- a/public/javascripts/posts/index.js +++ /dev/null @@ -1,17 +0,0 @@ -function submit_quick_edit(e) { - e.stopPropagation(); - $("#quick-edit").hide(); - $.post("/posts.js", $("#quick-edit form").serialize()); -} - -$(document).ready(function() { - $("#quick-edit form").submit(submit_quick_edit); - $("#post_tag_string").keydown(function(e) { - if (e.keyCode != 13) - return; - submit_quick_edit(e); - e.stopPropagation(); - }) - $("#mode-box select").click() - PostModeMenu.init(); -}); diff --git a/public/javascripts/application.js b/public/javascripts/src/application.js similarity index 56% rename from public/javascripts/application.js rename to public/javascripts/src/application.js index 6b04d00f9..586e0eb69 100644 --- a/public/javascripts/application.js +++ b/public/javascripts/src/application.js @@ -1,8 +1,8 @@ -// Post.init_blacklisted(); -// Cookie.setup(); +Cookie.setup(); + $(document).ready(function() { $("#hide-upgrade-account-link").click(function() { $("#upgrade-account").hide(); - // Cookie.put('hide-upgrade-account', '1', 7); + Cookie.put('hide-upgrade-account', '1', 7); }); }); diff --git a/public/javascripts/src/cookie.js b/public/javascripts/src/cookie.js new file mode 100644 index 000000000..4b254f6f8 --- /dev/null +++ b/public/javascripts/src/cookie.js @@ -0,0 +1,58 @@ +Cookie = { + put: function(name, value, days) { + if (days == null) { + days = 365; + } + + var date = new Date(); + date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000)); + var expires = "; expires=" + date.toGMTString(); + document.cookie = name + "=" + encodeURIComponent(value) + expires + "; path=/"; + }, + + raw_get: function(name) { + var nameEq = name + "="; + var ca = document.cookie.split(";"); + + for (var i = 0; i < ca.length; ++i) { + var c = ca[i]; + + while (c.charAt(0) == " ") { + c = c.substring(1, c.length); + } + + if (c.indexOf(nameEq) == 0) { + return c.substring(nameEq.length, c.length); + } + } + + return ""; + }, + + get: function(name) { + return this.unescape(this.raw_get(name)); + }, + + remove: function(name) { + Cookie.put(name, "", -1); + }, + + unescape: function(val) { + return decodeURIComponent(val.replace(/\+/g, " ")); + }, + + setup: function() { + if (location.href.match(/^\/(comment|pool|note|post)/) && this.get("tos") != "1") { + // Setting location.pathname in Safari doesn't work, so manually extract the domain. + var domain = location.href.match(/^(http:\/\/[^\/]+)/)[0]; + location.href = domain + "/static/terms_of_service?url=" + location.href; + return; + } + + if (this.get("hide-upgrade-account") != "1") { + if ($("upgrade-account")) { + $("upgrade-account").show(); + } + } + } +} diff --git a/public/javascripts/src/posts/index.js b/public/javascripts/src/posts/index.js new file mode 100644 index 000000000..74c0d1834 --- /dev/null +++ b/public/javascripts/src/posts/index.js @@ -0,0 +1,168 @@ +PostModeMenu = { + init: function() { + this.original_background_color = $(document.body).css("background-color") + + if (Cookie.get("mode") == "") { + Cookie.put("mode", "view"); + $("#mode-box select").val("view"); + } else { + $("#mode-box select").val(Cookie.get("mode")); + } + + this.change(); + }, + + change: function() { + var s = $("#mode-box select").val(); + Cookie.put("mode", s, 7); + + if (s == "view") { + $(document.body).css({"background-color": this.original_background_color}); + } else if (s == "edit") { + $(document.body).css({"background-color": "#3A3"}); + } else if (s == "add-fav") { + $(document.body).css({"background-color": "#FFA"}); + } else if (s == "remove-fav") { + $(document.body).css({"background-color": "#FFA"}); + } else if (s == "rating-q") { + $(document.body).css({"background-color": "#AAA"}); + } else if (s == "rating-s") { + $(document.body).css({"background-color": "#6F6"}); + } else if (s == "rating-e") { + $(document.body).css({"background-color": "#F66"}); + } else if (s == "vote-down") { + $(document.body).css({"background-color": "#FAA"}); + } else if (s == "vote-up") { + $(document.body).css({"background-color": "#AFA"}); + } else if (s == "lock-rating") { + $(document.body).css({"background-color": "#AA3"}); + } else if (s == "lock-note") { + $(document.body).css({"background-color": "#3AA"}); + } else if (s == "approve") { + $(document.body).css({"background-color": "#26A"}); + } else if (s == "unapprove") { + $(document.body).css({"background-color": "#F66"}); + } else if (s == "add-to-pool") { + $(document.body).css({"background-color": "#26A"}); + } else if (s == "apply-tag-script") { + $(document.body).css({"background-color": "#A3A"}); + } else if (s == "edit-tag-script") { + $(document.body).css({"background-color": "#FFF"}); + + var script = Cookie.get("tag-script"); + script = prompt("Enter a tag script", script); + + if (script) { + Cookie.put("tag-script", script); + $("#mode-box select").val("apply-tag-script"); + } else { + $("#mode-box select").val("view"); + } + + this.change(); + } else { + $(document.body).css({"background-color": "#AFA"}); + } + }, + + click: function(post_id) { + var s = $("#mode-box select").val(); + + if (s.value == "view") { + return true; + } else if (s.value == "add-fav") { + Favorite.create(post_id); + } else if (s.value == "remove-fav") { + Favorite.destroy(post_id); + } else if (s.value == "edit") { + // TODO + } else if (s.value == 'vote-down') { + PostVote.create("down", post_id); + } else if (s.value == 'vote-up') { + PostVote.create("up", post_id); + } else if (s.value == 'rating-q') { + Post.update(post_id, {"post[rating]": "questionable"}); + } else if (s.value == 'rating-s') { + Post.update(post_id, {"post[rating]": "safe"}); + } else if (s.value == 'rating-e') { + Post.update(post_id, {"post[rating]": "explicit"}); + } else if (s.value == 'lock-rating') { + Post.update(post_id, {"post[is_rating_locked]": "1"}); + } else if (s.value == 'lock-note') { + Post.update(post_id, {"post[is_note_locked]": "1"}); + } else if (s.value == 'unapprove') { + Unapproval.create(post_id); + } else if (s.value == "approve") { + Post.update(post_id, {"post[is_pending]": "0"}); + } else if (s.value == 'add-to-pool') { + Pool.add_post(post_id, 0); + } else if (s.value == "apply-tag-script") { + var tag_script = Cookie.get("tag-script"); + TagScript.run(post_id, tag_script); + } + + return false + } +} + +TagScript = { + parse: function(script) { + return script.match(/\[.+?\]|\S+/g); + }, + + test: function(tags, predicate) { + var split_pred = predicate.match(/\S+/g); + var is_true = true; + + split_pred.each(function(x) { + if (x[0] == "-") { + if (tags.include(x.substr(1, 100))) { + is_true = false + throw $break + } + } else { + if (!tags.include(x)) { + is_true = false + throw $break + } + } + }) + + return is_true + }, + + process: function(tags, command) { + if (command.match(/^\[if/)) { + var match = command.match(/\[if\s+(.+?)\s*,\s*(.+?)\]/) + if (TagScript.test(tags, match[1])) { + return TagScript.process(tags, match[2]) + } else { + return tags + } + } else if (command == "[reset]") { + return [] + } else if (command[0] == "-") { + return tags.reject(function(x) {return x == command.substr(1, 100)}) + } else { + tags.push(command) + return tags + } + }, + + run: function(post_id, tag_script) { + var commands = TagScript.parse(tag_script) + var post = Post.posts.get(post_id) + var old_tags = post.tags.join(" ") + + commands.each(function(x) { + post.tags = TagScript.process(post.tags, x) + }) + + Post.update(post_id, {"post[old_tags]": old_tags, "post[tags]": post.tags.join(" ")}) + } +} + +$(document).ready(function() { + $("#mode-box select").click(PostModeMenu.change) + PostModeMenu.init(); +}); diff --git a/public/javascripts/rails.js b/public/javascripts/src/rails.js similarity index 100% rename from public/javascripts/rails.js rename to public/javascripts/src/rails.js diff --git a/script/compile_javascripts b/script/compile_javascripts new file mode 100644 index 000000000..c624ce116 --- /dev/null +++ b/script/compile_javascripts @@ -0,0 +1,12 @@ +#!/usr/bin/env sh + +mkdir -p public/javascripts/compiled/posts + +# Create the base script that's used everywhere +cat public/javascripts/src/rails.js > public/javascripts/compiled/base.js +cat public/javascripts/src/cookie.js > public/javascripts/compiled/base.js +cat public/javascripts/src/application.js >> public/javascripts/compiled/base.js + +# Create post/index.js +cat public/javascripts/compiled/base.js > public/javascripts/compiled/posts/index.js +cat public/javascripts/src/posts/index.js >> public/javascripts/compiled/posts/index.js