From 2a278e0a2d7fbb0c46ba71b176c023a41fcd9f35 Mon Sep 17 00:00:00 2001 From: wanglinchun Date: Thu, 3 Apr 2014 22:38:18 +0800 Subject: [PATCH] all --- app/controllers/contests_controller.rb | 428 ++++++++++++++++++ app/helpers/contests_helper.rb | 158 +++++++ app/models/contest.rb | 117 +++++ app/models/contesting_project.rb | 51 +++ app/models/join_in_competition.rb | 10 + app/views/contests/_application_list.html.erb | 15 + app/views/contests/_contest_list.html.erb | 49 ++ app/views/contests/_form_contest.html.erb | 36 ++ app/views/contests/_history.html.erb | 53 +++ app/views/contests/_list_projects.html.erb | 102 +++++ app/views/contests/_new.html.erb | 53 +++ app/views/contests/_new_join.html.erb | 57 +++ app/views/contests/_pre_show.html.erb | 13 + app/views/contests/_project_list.html.erb | 15 + app/views/contests/_set_join.js.erb | 8 + app/views/contests/add.js.erb | 4 + app/views/contests/back.js.erb | 2 + app/views/contests/create.js.erb | 4 + app/views/contests/destroy.js.erb | 2 + app/views/contests/index.html.erb | 38 ++ app/views/contests/more.js.erb | 2 + app/views/contests/new.js.erb | 5 + app/views/contests/new_contest.html.erb | 10 + app/views/contests/new_join.js.erb | 3 + app/views/contests/set_reward.js.erb | 31 ++ app/views/contests/settings.html.erb | 30 ++ app/views/contests/show_application.html.erb | 67 +++ app/views/contests/show_contest.html.erb | 34 ++ app/views/contests/show_contest_user.html.erb | 30 ++ app/views/contests/show_participator.html.erb | 71 +++ app/views/contests/show_project.html.erb | 99 ++++ app/views/layouts/base_newcontest.html.erb | 264 +++++++++++ db/migrate/20140327071420_create_contests.rb | 15 + ...140327073052_create_contesting_projects.rb | 12 + ...ge_created_at_of_contests_to_created_on.rb | 11 + ...21611_add_reward_to_contesting_projects.rb | 5 + ...40402023357_create_join_in_competitions.rb | 10 + 37 files changed, 1914 insertions(+) create mode 100644 app/controllers/contests_controller.rb create mode 100644 app/helpers/contests_helper.rb create mode 100644 app/models/contest.rb create mode 100644 app/models/contesting_project.rb create mode 100644 app/models/join_in_competition.rb create mode 100644 app/views/contests/_application_list.html.erb create mode 100644 app/views/contests/_contest_list.html.erb create mode 100644 app/views/contests/_form_contest.html.erb create mode 100644 app/views/contests/_history.html.erb create mode 100644 app/views/contests/_list_projects.html.erb create mode 100644 app/views/contests/_new.html.erb create mode 100644 app/views/contests/_new_join.html.erb create mode 100644 app/views/contests/_pre_show.html.erb create mode 100644 app/views/contests/_project_list.html.erb create mode 100644 app/views/contests/_set_join.js.erb create mode 100644 app/views/contests/add.js.erb create mode 100644 app/views/contests/back.js.erb create mode 100644 app/views/contests/create.js.erb create mode 100644 app/views/contests/destroy.js.erb create mode 100644 app/views/contests/index.html.erb create mode 100644 app/views/contests/more.js.erb create mode 100644 app/views/contests/new.js.erb create mode 100644 app/views/contests/new_contest.html.erb create mode 100644 app/views/contests/new_join.js.erb create mode 100644 app/views/contests/set_reward.js.erb create mode 100644 app/views/contests/settings.html.erb create mode 100644 app/views/contests/show_application.html.erb create mode 100644 app/views/contests/show_contest.html.erb create mode 100644 app/views/contests/show_contest_user.html.erb create mode 100644 app/views/contests/show_participator.html.erb create mode 100644 app/views/contests/show_project.html.erb create mode 100644 app/views/layouts/base_newcontest.html.erb create mode 100644 db/migrate/20140327071420_create_contests.rb create mode 100644 db/migrate/20140327073052_create_contesting_projects.rb create mode 100644 db/migrate/20140327082704_change_created_at_of_contests_to_created_on.rb create mode 100644 db/migrate/20140401121611_add_reward_to_contesting_projects.rb create mode 100644 db/migrate/20140402023357_create_join_in_competitions.rb diff --git a/app/controllers/contests_controller.rb b/app/controllers/contests_controller.rb new file mode 100644 index 000000000..39e9a2053 --- /dev/null +++ b/app/controllers/contests_controller.rb @@ -0,0 +1,428 @@ +# fq +# class BidsController < ApplicationController +class ContestsController < ApplicationController + menu_item :respond + menu_item :project, :only => :show_project + menu_item :application, :only => :show_application + before_filter :find_contest, :only => [:show_contest, :show_project, :show_application, :create,:destroy,:more,:back,:add,:new,:show_results, :set_reward, + :show_contest_project, :show_contest_user, :join_in_contest, :unjoin_in_contest, :new_join,:show_participator, :settings] + + # added by fq + before_filter :require_login, :only => [:join_in_contest, :unjoin_in_contest] + # end + before_filter :require_login,:only => [:set_reward, :destroy, :add, :new, ] + + helper :watchers + helper :attachments + include AttachmentsHelper + include ApplicationHelper + helper :projects + helper :words + + + def index + # @contests = Contest.visible + # @contests ||= [] + @offset, @limit = api_offset_and_limit({:limit => 10}) + @contests = Contest.visible + @contests = @contests.like(params[:name]) if params[:name].present? + @contest_count = @contests.count + @contest_pages = Paginator.new @contest_count, @limit, params['page'] + + @offset ||= @contest_pages.reverse_offset + if params[:contest_sort_type].present? + case params[:contest_sort_type] + when '0' + unless @offset == 0 + @contests = @contests.offset(@offset).limit(@limit).all.reverse + else + limit = @contest_count % @limit + limit = @limit if limit == 0 + @contests = @contests.offset(@offset).limit(limit).all.reverse + end + @s_state = 0 + when '1' + unless @offset == 0 + @contests = @contests.reorder('contests.commit').offset(@offset).limit(@limit).all.reverse + else + limit = @contest_count % @limit + limit = @limit if limit == 0 + @contests = @contests.reorder('contests.commit').offset(@offset).limit(limit).all.reverse + end + @s_state = 1 + when '2' + unless @offset == 0 + @contests = @contests.offset(@offset).limit(@limit).all.reverse + else + limit = @contest_count % @limit + limit = @limit if limit == 0 + @contests = @contests.offset(@offset).limit(@limit).all.reverse + end + @s_state = 0 + end + else + unless @offset == 0 + @contests = @contests.reorder('contests.commit').offset(@offset).limit(@limit).all.reverse + else + limit = @contest_count % @limit + limit = @limit if limit == 0 + @contests = @contests.reorder('contests.commit').offset(@offset).limit(limit).all.reverse + end + @s_state = 1 + end + end + + def show_contest + @user = @contest.author + @jours = @contest.journals_for_messages.order('created_on DESC') + @limit = 10 + @feedback_count = @jours.count + @feedback_pages = Paginator.new @feedback_count, @limit, params['page'] + @offset ||= @feedback_pages.offset + @jour = @jours[@offset, @limit] + @state = false + + respond_to do |format| + layout_file = 'base_newcontest' + format.html { + render :layout => layout_file + } + format.api + end + end + + def join_in_contest + if params[:contest_password] == @contest.password + JoinInCompetition.create(:user_id => User.current.id, :competition_id => @contest.id) + @state = 0 + else + @state = 1 + end + + respond_to do |format| + format.js { render :partial => 'set_join', :locals => {:user => User.current, :object_id => params[:id]} } + end + end + + def unjoin_in_contest + + joined = JoinInCompetition.where('competition_id = ? and user_id = ?', @contest.id, User.current.id) + + joined.each do |join| + join.delete + end + + respond_to do |format| + format.js { render :partial => 'set_join', :locals => {:user => User.current, :object_id => params[:id]} } + end + end + + def new_join + + + end + + def show_participator + render :layout => 'base_newcontest' + + end + + + def settings + if @contest.author.id == User.current.id + @contest = Contest.find(params[:id]) + render :layout => 'base_newcontest' + else + render_403 :message => :notice_not_contest_setting_authorized + end + end + + def show_contest_project + contests = Contest.where('parent_id = ?', @contest.id) + @projects = [] + for contest in contests + @projects += contest.contesting_projects + end + + respond_to do |format| + format.html { + render :layout => 'base_newcontest' + } + format.api + + end + end + + def show_contest_user + contests = Contest.find(:all) + @users = [] + for contest in contests + for project in contest.projects + @users += project.users + end + end + + respond_to do |format| + format.html { + render :layout => 'base_newcontest' + } + format.api + + end + end + #显示参赛的项目 + def show_project + @membership = User.current.memberships.all(:conditions => Project.visible_condition(User.current)) + @option = [] + @membership.each do |membership| + unless(membership.project.project_type==1) + membership.member_roles.each{|role| + if(role.role_id == 3) + @option << membership.project + end + } + end + end + @user = @contest.author + @contesting_project = @contest.contesting_projects.all + if params[:student_id].present? + @temp = [] + @contesting_project.each do |pro| + if pro.project && pro.project.project_status + if /#{params[:student_id]}/ =~ pro.user.user_extensions.student_id + @temp << pro + end + end + @temp + end + @contesting_project = @temp + else + + @temp = [] + @contesting_project.each do |pro| + if pro.project && pro.project.project_status + @temp << pro + end + @temp + end + if @temp.size > 0 + @contesting_project = @temp.sort {|a,b| b.project.project_status.grade <=> a.project.project_status.grade} + end + end + respond_to do |format| + format.html { + render :layout => 'base_newcontest' + } + format.api + end + end + ############ + ##显示参赛的应用 + def show_application + respond_to do |format| + format.html { + render :layout => 'base_newcontest' + } + format.api + end + end + + ###添加应标项目 + def add + project = Project.find(params[:contest]) + contest_message = params[:contest_for_save][:contest_message] + if ContestingProject.where("project_id = ? and contest_id = ?", project.id, @contest.id).size == 0 + if ContestingProject.cerate_contesting(@contest.id, project.id, contest_message) + flash.now[:notice] = l(:label_bidding_contest_succeed) + end + else + flash.now[:error] = l(:label_bidding_fail) + end + + @contesting_project = @contest.contesting_projects + + respond_to do |format| + + format.html { redirect_to :back } + format.js + end + end + + ## 新建留言 + def create + + if params[:contest_message][:message].size>0 + if params[:reference_content] + message = params[:contest_message][:message] + "\n" + params[:reference_content] + else + message = params[:contest_message][:message] + end + refer_user_id = params[:contest_message][:reference_user_id].to_i + @contest.add_jour(User.current, message, refer_user_id) + end + @user = @contest.author + @jours = @contest.journals_for_messages.where('m_parent_id IS NULL').order('created_on DESC') + @limit = 10 + @feedback_count = @jours.count + @feedback_pages = Paginator.new @feedback_count, @limit, params['page'] + @offset ||= @feedback_pages.offset + @jour = @jours[@offset, @limit] + @contest.set_commit(@feedback_count) + + respond_to do |format| + format.js + end + + end + + ##删除留言 + def destroy + @user = @contest.author + if User.current.admin? || User.current.id == @user.id + JournalsForMessage.delete_message(params[:object_id]) + end + @jours = @contest.journals_for_messages.reverse + @limit = 10 + @feedback_count = @jours.count + @feedback_pages = Paginator.new @feedback_count, @limit, params['page'] + @offset ||= @feedback_pages.offset + @jour = @jours[@offset, @limit] + + @contest.set_commit(@feedback_count) + respond_to do |format| + format.js + end + end + + ##引用留言 + def new + @jour = JournalsForMessage.find(params[:journal_id]) if params[:journal_id] + if @jour + user = @jour.user + text = @jour.notes + else + user = @contest.author + text = @contest.description + end + text = text.to_s.strip.gsub(%r{
((.|\s)*?)
}m, '[...]') + @content = "> #{ll(User.current.language, :text_user_wrote, user)}\n> " + @content << text.gsub(/(\r?\n|\r\n?)/, "\n> ") + "\n\n" + @id = user.id + rescue ActiveRecord::RecordNotFound + render_404 + end + + ##新建竞赛 + def new_contest + @contest = Contest.new + @contest.safe_attributes = params[:contest] + end + + ##提交创建的竞赛 + def create_contest + @contest = Contest.new + @contest.name = params[:contest][:name] + @contest.description = params[:contest][:description] + @contest.budget = params[:contest][:budget] + @contest.deadline = params[:contest][:deadline] + @contest.password = params[:contest][:password] + @contest.author_id = User.current.id + @contest.commit = 0 + if @contest.save + unless @contest.watched_by?(User.current) + if @contest.add_watcher(User.current) + flash[:notice] = l(:label_contesting_created_succeed) + end + end + redirect_to show_contest_contest_path(@contest) + else + @contest.safe_attributes = params[:contest] + render :action => 'new_contest' + end + end + + ##更新竞赛配置信息 + def update_contest + @contest = Contest.find(params[:id]) + @contest.name = params[:contest][:name] + @contest.description = params[:contest][:description] + + @contest.budget = params[:contest][:budget] + @contest.deadline = params[:contest][:deadline] + @contest.password = params[:contest][:password] + @contest.author_id = User.current.id + @contest.commit = 0 + if @contest.save + unless @contest.watched_by?(User.current) + if @contest.add_watcher(User.current) + flash[:notice] = l(:label_contesting_updated_succeed) + end + end + redirect_to show_contest_contest_path(@contest) + + else + @contest.safe_attributes = params[:contest] + render :action => 'new_contest' + end + end + + def more + @jour = @contest.journals_for_messages + @jour.each_with_index {|j,i| j.indice = i+1} + @state = true + + respond_to do |format| + format.html { redirect_to :back } + format.js + #format.api { render_api_ok } + end + end + + def back + @jour = @contest.journals_for_messages + @jour.each_with_index {|j,i| j.indice = i+1} + @state = false + + respond_to do |format| + format.html { redirect_to :back } + format.js + #format.api { render_api_ok } + end + end + + def set_reward + @b_p = nil + @contesting_project_id = nil + + if params[:set_reward][:reward]&&((User.current.id==@contest.author_id)||User.current.admin) + # @contest_id = params[:id] + @contesting_project_id = params[:set_reward][:b_id] #[:b_id]??? + @b_p = ContestingProject.find_by_id(@contesting_project_id) + + # 把字段存进表中 + @b_p.update_reward(params[:set_reward][:reward].to_s) + end + + respond_to do |format| + format.js + end + end + + + def manage + + end + + private + + def find_contest + if params[:id] + @contest = Contest.find(params[:id]) + @user = @contest.author + end + rescue + render_404 + end + +end + diff --git a/app/helpers/contests_helper.rb b/app/helpers/contests_helper.rb new file mode 100644 index 000000000..e13641b1d --- /dev/null +++ b/app/helpers/contests_helper.rb @@ -0,0 +1,158 @@ +#enconding:utf-8 +# fq +module ContestsHelper + + def render_notes(contest, journal, options={}) + content = '' + removable = User.current == journal.user || User.current == contest.author + links = [] + if !journal.notes.blank? + links << link_to(image_tag('comment.png'), + {:controller => 'contests', :action => 'new', :id => contest, :journal_id => journal}, + :remote => true, + :method => 'post', + :title => l(:button_quote)) if options[:reply_links] + if removable + url = {:controller => 'contests', + :action => 'destroy', + :object_id => journal, + :id => contest} + links << ' ' + links << link_to(image_tag('delete.png'), url, + :remote => true, :method => 'delete', :class => "delete", :title => l(:button_delete)) + end + end + content << content_tag('div', links.join(' ').html_safe, :class => 'contextual') unless links.empty? + content << textilizable(journal.notes) + css_classes = "wiki" + content_tag('div', content.html_safe, :id => "journal-#{journal.id}-notes", :class => css_classes) + end + + def link_to_in_place_notes_editor(text, field_id, url, options={}) + onclick = "$.ajax({url: '#{url_for(url)}', type: 'get'}); return false;" + link_to text, '#', options.merge(:onclick => onclick) + end + + # this method is used to get all projects that tagged one tag + # added by william + def get_contests_by_tag(tag_name) + Contest.tagged_with(tag_name).order('updated_on desc') + end + + #added by huang + def sort_contest_enterprise(state, project_type) + content = ''.html_safe + case state + when 0 + content << content_tag('li', link_to(l(:label_sort_by_active), calls_path(:contest_sort_type => '1', :project_type => project_type))) + content << content_tag('li', link_to(l(:label_sort_by_time), calls_path(:contest_sort_type => '0', :project_type => project_type), :class=>"selected"), :class=>"selected") + + when 1 + content << content_tag('li', link_to(l(:label_sort_by_active), calls_path(:contest_sort_type => '1', :project_type => project_type), :class=>"selected"), :class=>"selected") + content << content_tag('li', link_to(l(:label_sort_by_time), calls_path(:contest_sort_type => '0', :project_type => project_type))) + end + content = content_tag('ul', content) + content_tag('div', content, :class => "tabs_enterprise") + end + #end + + # def sort_bid(state, project_type) + # content = ''.html_safe + # case state + # when 0 + # content << content_tag('li', link_to(l(:label_sort_by_active), calls_path(:bid_sort_type => '1', :project_type => project_type))) + # content << content_tag('li', link_to(l(:label_sort_by_time), calls_path(:bid_sort_type => '0', :project_type => project_type), :class=>"selected"), :class=>"selected") +# + # when 1 + # content << content_tag('li', link_to(l(:label_sort_by_active), calls_path(:bid_sort_type => '1', :project_type => project_type), :class=>"selected"), :class=>"selected") + # content << content_tag('li', link_to(l(:label_sort_by_time), calls_path(:bid_sort_type => '0', :project_type => project_type))) + # end + # content = content_tag('ul', content) + # content_tag('div', content, :class => "tabs") + # end + + #huang + def sort_contest(state) + content = ''.html_safe + case state + when 0 + content << content_tag('li', link_to(l(:label_sort_by_active), contest_path(:contest_sort_type => '1'))) + content << content_tag('li', link_to(l(:label_sort_by_time), contest_path(:contest_sort_type => '0'), :class=>"selected"), :class=>"selected") + + when 1 + content << content_tag('li', link_to(l(:label_sort_by_active), contest_path(:contest_sort_type => '1'), :class=>"selected"), :class=>"selected") + content << content_tag('li', link_to(l(:label_sort_by_time), contest_path(:contest_sort_type => '0'))) + end + content = content_tag('ul', content) + content_tag('div', content, :class => "tabs") + end + #end + + # def course_options_for_select(courses) + # # + # html = '' + # courses.each do |course| + # html << "" + # end + # html.html_safe + # end + + + # used to get the reward and handle the value which can be used to display in views + # added by william + def get_prize(c_project) + c_project.get_reward + end + + def count_contest_project + contests = Contest.find(:id) + @projects = [] + for contest in contests + @projects += contest.contesting_projects + end + @projects.count + end + + def count_contest_user + contests = Contest.find(:id) + @users = [] + for contest in contests + for project in contest.projects + @users += project.users + end + end + @users.count + end + + def im_watching_student_id? contest + people = [] + people << contest.author + # case bid.reward_type # 天煞的bid分了三用途,里面各种hasmany还不定能用! + # when 1 + # when 2 + # bid.join_in_contests.each do |jic| + # people << jic.user + # end + # when 3 + # people += bid.courses.first.users.to_a + # else + # raise 'bids_helper: unknow bid type' # 出了错看这里!不知道的抛异常,省的找不到出错的地方! + # end + + contest.join_in_contests.each do |jic| + people << jic.user + end + people.include?(User.current) + end + + def select_option_helper option + tmp = Hash.new + option.each do |project| + tmp[project.name] = project.identifier + end + tmp + end + +end \ No newline at end of file diff --git a/app/models/contest.rb b/app/models/contest.rb new file mode 100644 index 000000000..a4427d24c --- /dev/null +++ b/app/models/contest.rb @@ -0,0 +1,117 @@ +class Contest < ActiveRecord::Base + attr_accessible :author_id, :budget, :commit, :deadline, :description, :name, :password + include Redmine::SafeAttributes + + belongs_to :author, :class_name => 'User', :foreign_key => :author_id + has_many :contesting_projects, :dependent => :destroy + has_many :projects, :through => :contesting_projects + has_many :projects_member, :class_name => 'User', :through => :projects + has_many :journals_for_messages, :as => :jour, :dependent => :destroy + has_many :acts, :class_name => 'Activity', :as => :act, :dependent => :destroy + has_many :join_in_competitions, foreign_key: 'competition_id', :dependent => :destroy + has_many :join_in_contests, class_name: 'JoinInCompetition', foreign_key: 'competition_id', :dependent => :destroy + + + + acts_as_attachable + + NAME_LENGTH_LIMIT = 60 + DESCRIPTION_LENGTH_LIMIT = 250 + + validates_length_of :name, :maximum => NAME_LENGTH_LIMIT + validates_length_of :description, :maximum => DESCRIPTION_LENGTH_LIMIT + validates_presence_of :author_id, :name, :deadline + validates_format_of :deadline, :with => /^[\d]{4}[-][\d]{1,2}[-][\d]{1,2}$/ + validates_format_of :budget, :with => /^(\d+)$|^(\d+).([0-9]{2})|^(\d+).([0-9]{1})$/ + validate :validate_user + after_create :act_as_activity + + scope :visible, lambda {|*args| + nil + } + + scope :like, lambda {|arg| + if arg.blank? + where(nil) + else + pattern = "%#{arg.to_s.strip.downcase}%" + where("LOWER(id) LIKE :p OR LOWER(name) LIKE :p OR LOWER(description) LIKE :p", :p => pattern) + end + } + + acts_as_watchable + acts_as_taggable + + acts_as_event :title => Proc.new {|o| "#{l(:label_requirement)} ##{o.id}: #{o.name}" }, + :description => :description, + :author => :author, + :url => Proc.new {|o| {:controller => 'contests', :action => 'show_contest', :id => o.id}} + + acts_as_activity_provider :find_options => {:include => [:projects, :author]}, + :author_key => :author_id + + safe_attributes 'name', + 'description', + 'budget', + 'deadline', + 'password' + + + def add_jour(user, notes, reference_user_id = 0, options = {}) + if options.count == 0 + self.journals_for_messages << JournalsForMessage.new(:user_id => user.id, :notes => notes, :reply_id => reference_user_id) + else + jfm = self.journals_for_messages.build(options) + jfm.save + jfm + end + end + + def self.creat_contests(budget, deadline, name, description=nil) + self.create(:author_id => User.current.id, :budget => budget, + :deadline => deadline, :name => name, :description => description, :commit => 0) + end + + def update_contests(budget, deadline, name, description=nil) + if(User.current.id == self.author_id) + self.name = name + self.budget = budget + self.deadline = deadline + self.description = description + self.save + end + end + + def delete_contests + unless self.nil? + if User.current.id == self.author_id + self.destroy + end + end + end + + def set_commit(commit) + self.update_attribute(:commit, commit) + end + + private + + def validate_user + errors.add :author_id, :invalid if author.nil? || !author.active? + end + + + def act_as_activity + self.acts << Activity.new(:user_id => self.author_id) + end + + def validate_contest_manager(user_id) + unless user_id.nil? + if self.author_id == user_id + return true + else + return false + end + end + end +end diff --git a/app/models/contesting_project.rb b/app/models/contesting_project.rb new file mode 100644 index 000000000..773c04c68 --- /dev/null +++ b/app/models/contesting_project.rb @@ -0,0 +1,51 @@ +class ContestingProject < ActiveRecord::Base + attr_accessible :contest_id, :description, :project_id, :user_id, :reward + + belongs_to :contest + belongs_to :project + belongs_to :user + + DESCRIPTION_LENGTH_LIMIT = 500 + + validates_length_of :description, :maximum => DESCRIPTION_LENGTH_LIMIT + validates_presence_of :user_id, :contest_id, :project_id + validate :validate_user + validate :validate_contest + validate :validate_project + validates_uniqueness_of :contest_id, :scope => :project_id + + def self.cerate_contesting(contest_id, project_id, description = nil) + self.create(:user_id => User.current.id, :contest_id => contest_id, + :project_id => project_id, :description => description) + end + + def update_reward(which) + self.update_attribute(:reward,which) + end + + def get_reward + self.reward + end + + def cancel_contesting + unless self.nil? + if User.current.id == self.user_id + self.destroy + end + end + end + + private + + def validate_user + errors.add :user_id, :invalid if user.nil? || !user.active? + end + + def validate_contest + errors.add :contest_id, :invalid if contest.nil? + end + + def validate_project + errors.add :project_id, :invalid if project.nil? + end +end diff --git a/app/models/join_in_competition.rb b/app/models/join_in_competition.rb new file mode 100644 index 000000000..707dccf07 --- /dev/null +++ b/app/models/join_in_competition.rb @@ -0,0 +1,10 @@ +# 新竞赛参加关系表 +class JoinInCompetition < ActiveRecord::Base + attr_accessible :competition_id, :user_id + belongs_to :user, :class_name => "User", :foreign_key => :user_id + belongs_to :competition, :class_name => "Contest", :foreign_key => :competition_id + + validates :user_id, presence: true + validates :competition_id, presence: true + +end diff --git a/app/views/contests/_application_list.html.erb b/app/views/contests/_application_list.html.erb new file mode 100644 index 000000000..081a9f4de --- /dev/null +++ b/app/views/contests/_application_list.html.erb @@ -0,0 +1,15 @@ + +<%= render_flash_messages %> + + + + <% if User.current.logged? %> + + <% end %> +
<%= l(:label_bidding_project) %> +
+ <%= toggle_link l(:button_contesting_as_project), 'put-bid-form' %> +
+
+ +<%#= render :partial=> "list_projects" %> diff --git a/app/views/contests/_contest_list.html.erb b/app/views/contests/_contest_list.html.erb new file mode 100644 index 000000000..cdc390410 --- /dev/null +++ b/app/views/contests/_contest_list.html.erb @@ -0,0 +1,49 @@ + +<% contests.each do |contest|%> + + + + + +
<%= link_to(image_tag(url_to_avatar(contest.author), :class => 'avatar'), user_path(contest.author), :class => "avatar") %> + + + + + + + + + + + +
<%= link_to(contest.author, user_path(contest.author), :class => 'bid_user') %>:  <%= link_to(contest.name, show_contest_contest_path(contest), :class => 'bid_path') %>
+ + + + + + + + + +
+ <%= l(:label_contests_reward_method) %><%= contest.budget%> +
<%= l(:label_x_biding_project, :count => contest.contesting_projects.count) %>(<%= link_to contest.contesting_projects.count %>) + <%= l(:label_x_bids_responses, :count => contest.commit) %>(<%= link_to contest.commit, respond_path(contest) %>) + <%= l(:label_x_followers, :count => contest.watcher_users.count) %>(<%= link_to contest.watcher_users.count, respond_path(contest) %>) +
<%= l :label_create_time %>: <%= format_time contest.created_on %>
+
+ + + + +
<%= contest.description%>
+
+<% end %> + + diff --git a/app/views/contests/_form_contest.html.erb b/app/views/contests/_form_contest.html.erb new file mode 100644 index 000000000..5dc824d28 --- /dev/null +++ b/app/views/contests/_form_contest.html.erb @@ -0,0 +1,36 @@ + + +<%= error_messages_for 'contest' %> + +

<%= l(:label_bids_form_contest_new_description) %>

+

<%= f.text_field :name, :required => true, :size => 60, :style => "width:490px;", :maxlength => Contest::NAME_LENGTH_LIMIT, :placeholder => "#{l(:label_contest_name)}" %>

+ +

<%= f.text_area :description, :rows => 8, :class => 'wiki-edit', :style => "font-size:small;width:490px;margin-left:10px;", :maxlength => Contest::DESCRIPTION_LENGTH_LIMIT, :placeholder => "#{l(:label_contest_description)}" %>

+ +

<%= f.text_field :password, :size => 60, :style => "width:488px;margin-left: 10px;" %>

+ +

+ <%= f.text_field :budget, :required => true, :size => 60, :style => "width:350px;", :placeholder => l(:label_bids_reward_what) %> + + +

+ +

<%= f.text_field :deadline, :required => true, :size => 60, :style => "width:150px;", :placeholder => "#{l(:label_deadline)}" %><%= calendar_for('contest_deadline')%>

diff --git a/app/views/contests/_history.html.erb b/app/views/contests/_history.html.erb new file mode 100644 index 000000000..6be572c65 --- /dev/null +++ b/app/views/contests/_history.html.erb @@ -0,0 +1,53 @@ +<% reply_allow = JournalsForMessage.create_by_user? User.current %> +<% tip1 = l(:label_user_response) %> +

<%=tip1%>

+ +
+ <%= render :partial => 'new', :locals => {:contest => @contest, :sta => @state} %> +
+ + +<% if journals.size >0 %> + +<% end %> diff --git a/app/views/contests/_list_projects.html.erb b/app/views/contests/_list_projects.html.erb new file mode 100644 index 000000000..6a778819d --- /dev/null +++ b/app/views/contests/_list_projects.html.erb @@ -0,0 +1,102 @@ + +<% contesting_project.each do |c_project|%> + <% if c_project.project %> + + + + +
+ + + + + + + +
+
+ <%= image_tag(url_to_avatar(c_project.project), :class => 'avatar3') %> + +
+ + + + + + + + + + + + + + + + + +
+ + <%= link_to(c_project.project.name, project_path(c_project.project)) %> + + <%= l(:label_joined_contest)%> + + + + <%= l(:label_system_grade) %>:<%= (c_project.project.project_status.nil? ? 0.0 : c_project.project.project_status.grade) unless (c_project.project.project_status.nil? && c_project.project.nil?) %> + <% if get_prize(c_project).nil? or get_prize(c_project) == "" %> + <% if @contest.deadline < Date.today %> + <%= l(:label_noawards)%> + <% end %> + <% else %> + + <% case get_prize(c_project) %> + <% when '-1' %> + <%= image_tag("/images/bid/special_reward.png")%> + <% when '0' %> + <%= image_tag("/images/bid/first_reward.png")%> + <% when '1' %> + <%= image_tag("/images/bid/second_reward.png")%> + <% when '2' %> + <%= image_tag("/images/bid/third_reward.png")%> + <% when '3' %> + <%= image_tag("/images/bid/forth_reward.png")%> + <% when '4' %> + <%= image_tag("/images/bid/fifth_reward.png")%> + <% when '5' %> + <%= image_tag("/images/bid/qualified.png")%> + <% end %> + <% end %> + + +
<%= c_project.project.description %>
+ <%= format_time c_project.created_at%> +
+
+
+ + + + + + + + +
+ + <%= l(:label_contest_user) %> + <% unless c_project.user.nil? %> + <%= c_project.user.lastname %><%= c_project.user.firstname %> + <% end %> + + +
+ <%= l(:label_contest_reason) %> + <%= c_project.description %> +
+
+
+
+ <% end %> +<% end %> + diff --git a/app/views/contests/_new.html.erb b/app/views/contests/_new.html.erb new file mode 100644 index 000000000..2462d3fb1 --- /dev/null +++ b/app/views/contests/_new.html.erb @@ -0,0 +1,53 @@ + + + +<%= form_for('contest_message', + :remote => true, :method => :post, + :url => {:controller => 'contests', + :action => 'create', + :id => contest, + :sta => sta} + ) do |f|%> + +
+ <%= render :partial => 'pre_show', :locals => {:content => @content} %> +
+ + <% if User.current.logged? %> + + + + +
<%= f.text_area 'message', :rows => 3, :cols => 65, :placeholder => l(:label_my_respond), :style => "resize: none;", :class => 'noline'%>
+ + <%= f.text_field :reference_user_id, :style=>"display:none"%> + + + + + + +
<%= submit_tag l(:button_leave_meassge), :name => nil , :class => "contest_btn", :onmouseout => "this.style.backgroundPosition = 'left top'", :onmouseover => "this.style.backgroundPosition = 'left -31px'"%> + <%= submit_tag l(:button_clear), :name => nil, :onclick => "clearMessage('contest_message_message');", :type => 'button', :class => "bid_btn", :onmouseout => "this.style.backgroundPosition = 'left top'", :onmouseover => "this.style.backgroundPosition = 'left -31px'" %>
+ + <% else %> +
+ <%= l(:label_user_login_tips) %> + <%= link_to l(:label_user_login_new), signin_path %> +
+ <% end %> +<% end %> diff --git a/app/views/contests/_new_join.html.erb b/app/views/contests/_new_join.html.erb new file mode 100644 index 000000000..c764690de --- /dev/null +++ b/app/views/contests/_new_join.html.erb @@ -0,0 +1,57 @@ + + + +

请输入竞赛密码

+ +<%= form_tag( join_in_contest_contests_path(id: contest.id), + :remote => true, + :method => :post, + :id => 'new-watcher-form') do %> + + + + + <%= text_field_tag 'contest_password', nil, :size => 45 %> + +

+ <%= submit_tag l(:label_new_join), :name => nil, :class => "contest_btn", :onclick => "hideModal(this);" %> + <%= submit_tag l(:button_cancel), :name => nil, :class => "contest_btn", :onclick => "hideModal(this);", :type => 'button' %> + +

+
+<% end %> diff --git a/app/views/contests/_pre_show.html.erb b/app/views/contests/_pre_show.html.erb new file mode 100644 index 000000000..fef1f16e4 --- /dev/null +++ b/app/views/contests/_pre_show.html.erb @@ -0,0 +1,13 @@ + +<% unless content.nil?%> + + + + + + + +
<%= textilizable content %>
<%= hidden_field_tag 'reference_content', params[:reference_content], :value => content%>
+<% end %> + + diff --git a/app/views/contests/_project_list.html.erb b/app/views/contests/_project_list.html.erb new file mode 100644 index 000000000..325e87105 --- /dev/null +++ b/app/views/contests/_project_list.html.erb @@ -0,0 +1,15 @@ + +<%= render_flash_messages %> + + + + <% if User.current.logged? %> + + <% end %> +
<%= l(:label_bidding_project) %>(<%= contesting_project.count%>) +
+ <%= toggle_link l(:button_contesting_as_project), 'put-bid-form' %> +
+
+ +<%= render :partial=> "list_projects",:locals => {:contesting_project => contesting_project,:contest => @contest }%> diff --git a/app/views/contests/_set_join.js.erb b/app/views/contests/_set_join.js.erb new file mode 100644 index 000000000..346e1d846 --- /dev/null +++ b/app/views/contests/_set_join.js.erb @@ -0,0 +1,8 @@ +$("#<%=object_id%>").replaceWith('<%= escape_javascript join_in_competition(@contest, user) %>'); +<% if @state %> + <% if @state == 0 %> + alert("加入成功") + <% else %> + alert("密码错误") + <% end %> +<% end %> \ No newline at end of file diff --git a/app/views/contests/add.js.erb b/app/views/contests/add.js.erb new file mode 100644 index 000000000..9c696d8aa --- /dev/null +++ b/app/views/contests/add.js.erb @@ -0,0 +1,4 @@ +$('#contesting_project_list').html('<%= escape_javascript(render(:partial => 'project_list', :locals => {:contesting_project => @contesting_project})) %>'); +$("#project_id").val("请选择项目"); +$("#contest_message").val( "<%= l(:label_bid_reason) %>" ); +$("#put-bid-form").hide(); \ No newline at end of file diff --git a/app/views/contests/back.js.erb b/app/views/contests/back.js.erb new file mode 100644 index 000000000..d806c1481 --- /dev/null +++ b/app/views/contests/back.js.erb @@ -0,0 +1,2 @@ +$('#history').html('<%= escape_javascript(render(:partial => 'history', :locals => {:contest => @contest, :journals => @jour, :state => @state})) %>'); +$('#contest_message_reference_user_id').val(""); \ No newline at end of file diff --git a/app/views/contests/create.js.erb b/app/views/contests/create.js.erb new file mode 100644 index 000000000..9246d939c --- /dev/null +++ b/app/views/contests/create.js.erb @@ -0,0 +1,4 @@ +$('#history').html('<%= escape_javascript(render(:partial => 'contests/history', :locals => {:contest => @contest, :journals => @jour, :state => true})) %>'); +$('#pre_show').html('<%= escape_javascript(render(:partial => 'pre_show', :locals => {:content => nil})) %>'); +$('#contest_message_message').val(""); +$('#contest_message_reference_user_id').val(""); diff --git a/app/views/contests/destroy.js.erb b/app/views/contests/destroy.js.erb new file mode 100644 index 000000000..a2f0fb2da --- /dev/null +++ b/app/views/contests/destroy.js.erb @@ -0,0 +1,2 @@ +$('#history').html('<%= escape_javascript(render(:partial => 'history', :locals => {:contest => @contest, :journals => @jour, :state => false})) %>'); +$('#contest_message_reference_user_id').val(""); \ No newline at end of file diff --git a/app/views/contests/index.html.erb b/app/views/contests/index.html.erb new file mode 100644 index 000000000..3a7bde1e5 --- /dev/null +++ b/app/views/contests/index.html.erb @@ -0,0 +1,38 @@ +
+ <%= form_tag({:controller => 'contests', :action => 'index'}, :method => :get) do %> + + + + + + + + + + + +
<%= l(:label_contest_innovate) %><%= l(:label_user_location) %> : + <% if User.current.logged? %> + <% unless User.current.user_extensions.identity == 1 %> + <%= link_to(l(:label_newtype_contest), {:controller => 'contests', :action => 'new_contest'}, :class => 'icon icon-add') %> + <% end %> + <% end %> + + +
<%= link_to request.host()+"/contests", :controller => 'contests', :action => 'index' %> <%=link_to l(:field_homepage), home_path %> > <%=link_to l(:label_contest_innovate), :controller => 'contests', :action => 'index' %>
+ <% end %> +
+<% if @contests.size > 0%> +<%= sort_contest(@s_state)%> +
+ <%= render :partial => 'contest_list', :locals => {:contests => @contests, :contest_pages => @contest_pages} %> +
+<% else %> + <%= render :partial => "layouts/no_content"%> +<% end %> + +<% html_title l(:label_contest_list)%> diff --git a/app/views/contests/more.js.erb b/app/views/contests/more.js.erb new file mode 100644 index 000000000..d806c1481 --- /dev/null +++ b/app/views/contests/more.js.erb @@ -0,0 +1,2 @@ +$('#history').html('<%= escape_javascript(render(:partial => 'history', :locals => {:contest => @contest, :journals => @jour, :state => @state})) %>'); +$('#contest_message_reference_user_id').val(""); \ No newline at end of file diff --git a/app/views/contests/new.js.erb b/app/views/contests/new.js.erb new file mode 100644 index 000000000..a251b3d69 --- /dev/null +++ b/app/views/contests/new.js.erb @@ -0,0 +1,5 @@ +$('#pre_show').html('<%= escape_javascript(render(:partial => 'pre_show', :locals => {:content => @content})) %>'); +$('#contest_message_reference_user_id').val("<%= @id%>"); +showAndScrollTo("pre_show", "contest_message_reference_user_id"); + + diff --git a/app/views/contests/new_contest.html.erb b/app/views/contests/new_contest.html.erb new file mode 100644 index 000000000..7366b4203 --- /dev/null +++ b/app/views/contests/new_contest.html.erb @@ -0,0 +1,10 @@ + +

<%=l(:label_newtype_contest)%>

+ +<%= labelled_form_for @contest, :url => {:controller => 'contests', :action => 'create_contest'}, method: :post do |f| %> +
+ <%= render :partial => 'form_contest', :locals => { :f => f } %> + <%= submit_tag l(:button_create) %> + <%= javascript_tag "$('#bid_name').focus();" %> + <% end %> +
\ No newline at end of file diff --git a/app/views/contests/new_join.js.erb b/app/views/contests/new_join.js.erb new file mode 100644 index 000000000..5ec9356d7 --- /dev/null +++ b/app/views/contests/new_join.js.erb @@ -0,0 +1,3 @@ +$('#ajax-modal').html('<%= escape_javascript(render :partial => 'contests/new_join', :locals => {:contest => @contest}) %>'); +showModal('ajax-modal', '400px'); +$('#ajax-modal').addClass('new-watcher'); diff --git a/app/views/contests/set_reward.js.erb b/app/views/contests/set_reward.js.erb new file mode 100644 index 000000000..d6d8c4f9f --- /dev/null +++ b/app/views/contests/set_reward.js.erb @@ -0,0 +1,31 @@ +$('#reward_result_<%= @contesting_project_id %>').html('<%= j( + +if get_prize(@b_p).nil? or get_prize(@b_p) == "" + if @contest.deadline < Date.today + puts '未评奖' + end +else + + case get_prize(@b_p) + when '-1' + image_tag("/images/bid/special_reward.png") + when '1' + when '0' + image_tag("/images/bid/first_reward.png") + when '1' + image_tag("/images/bid/second_reward.png") + when '2' + image_tag("/images/bid/third_reward.png") + when '3' + image_tag("/images/bid/forth_reward.png") + when '4' + image_tag("/images/bid/fifth_reward.png") + when '5' + image_tag("/images/bid/qualified.png") + end + +end +) +%>') + +$('#<%= @contesting_project_id %>').hide() diff --git a/app/views/contests/settings.html.erb b/app/views/contests/settings.html.erb new file mode 100644 index 000000000..def1c7f5d --- /dev/null +++ b/app/views/contests/settings.html.erb @@ -0,0 +1,30 @@ + +

<%=l(:label_settings)%>

+ +<%= error_messages_for 'contest' %> + +<%= labelled_form_for @contest, :url => update_contest_contest_path(@contest) do |f| %> +
+ <%= render :partial => 'form_contest', :locals => { :f => f } %> +
+ <%= submit_tag l(:button_create) %> + <%= javascript_tag "$('#bid_name').focus();" %> +<% end %> \ No newline at end of file diff --git a/app/views/contests/show_application.html.erb b/app/views/contests/show_application.html.erb new file mode 100644 index 000000000..da06a7cb0 --- /dev/null +++ b/app/views/contests/show_application.html.erb @@ -0,0 +1,67 @@ + + + + + + <% if User.current.logged? %> + + + + <% end %> +
+ <%= render :partial => 'application_list' %> +
+ diff --git a/app/views/contests/show_contest.html.erb b/app/views/contests/show_contest.html.erb new file mode 100644 index 000000000..9ce40bfcb --- /dev/null +++ b/app/views/contests/show_contest.html.erb @@ -0,0 +1,34 @@ +<% reply_allow = JournalsForMessage.create_by_user? User.current %> +
+ <%= image_tag(url_to_avatar(@contest.author), :class => "avatar")%> + +

<%= link_to(@contest.author.lastname+@contest.author.firstname, user_path(@contest.author))%>:<%= @contest.name %>

+

+ <%= l(:label_bids_reward_method) %><%= @contest.budget%> +

+
+ <%= @contest.description %> + +
+ + <%= render :partial => "/praise_tread/praise_tread", + :locals => {:obj => @contest,:show_flag => true,:user_id =>User.current.id}%> + +
+
+ +
+ +
+ <%= render :partial => 'history', :locals => { :contest => @contest, :journals => @jour, :state => false} %> +
+ + + diff --git a/app/views/contests/show_contest_user.html.erb b/app/views/contests/show_contest_user.html.erb new file mode 100644 index 000000000..43eb896ad --- /dev/null +++ b/app/views/contests/show_contest_user.html.erb @@ -0,0 +1,30 @@ +
+ <% for user in @contest.watcher_users %> + +<% end %> +
\ No newline at end of file diff --git a/app/views/contests/show_participator.html.erb b/app/views/contests/show_participator.html.erb new file mode 100644 index 000000000..da51aef3a --- /dev/null +++ b/app/views/contests/show_participator.html.erb @@ -0,0 +1,71 @@ + +

<%=link_to l(:label_x_join_in_contest, :count => @contest.join_in_contests.count)+"("+@contest.join_in_contests(@user.id).count.to_s+")", :controller=>"contests", :action=>"show_participator"%>

+
+ <% for temp in @contest.join_in_contests %> + <% user = temp.user %> + + <% end %> +
\ No newline at end of file diff --git a/app/views/contests/show_project.html.erb b/app/views/contests/show_project.html.erb new file mode 100644 index 000000000..f43d5048e --- /dev/null +++ b/app/views/contests/show_project.html.erb @@ -0,0 +1,99 @@ + + + + + + <% if User.current.logged? %> + + + + <% end %> +
+ <%= render :partial => 'project_list', :locals => {:contesting_project => @contesting_project,:contest => @contest} %> +
+ diff --git a/app/views/layouts/base_newcontest.html.erb b/app/views/layouts/base_newcontest.html.erb new file mode 100644 index 000000000..1b3a99966 --- /dev/null +++ b/app/views/layouts/base_newcontest.html.erb @@ -0,0 +1,264 @@ +<% @nav_dispaly_contest_label = 1 %> + + + + + <%= h html_title %> + + + <%= csrf_meta_tag %> + <%= favicon %> + <%= stylesheet_link_tag 'jquery/jquery-ui-1.9.2', 'application', :media => 'all' %> + <%= stylesheet_link_tag 'rtl', :media => 'all' if l(:direction) == 'rtl' %> + <%= javascript_heads %> + <%= heads_for_theme %> + <%= call_hook :view_layouts_base_html_head %> + + <%= yield :header_tags -%> + + +
+
+
+ <%=render :partial => 'layouts/base_header'%> +
+ +
+ + + + + + + + + + +
创新竞赛社区<%= l(:label_user_location) %> : + +
<%=link_to request.host()+"/contests", :controller=>'contests', :action=>'index' %><%=link_to l(:field_homepage), home_path %> > + <%=link_to l(:label_contest_innovate), :controller=>'contests', :action=>'index' %> > + <%= link_to @contest.name, show_contest_contest_path %> +
+
+ + + +
+ <% if display_main_menu?(@contest) %> +
+ <%= render_menu :contest_menu %> +
+ <% end %> + + <%= yield %> + <%= call_hook :view_layouts_base_content %> +
+
+ <%=render :partial => 'layouts/base_footer'%> +
+
+
+ + + + +
+ <%= call_hook :view_layouts_base_body_bottom %> + + diff --git a/db/migrate/20140327071420_create_contests.rb b/db/migrate/20140327071420_create_contests.rb new file mode 100644 index 000000000..0ec04a6c5 --- /dev/null +++ b/db/migrate/20140327071420_create_contests.rb @@ -0,0 +1,15 @@ +class CreateContests < ActiveRecord::Migration + def change + create_table :contests do |t| + t.string :name + t.integer :budget + t.integer :author_id + t.date :deadline + t.string :description + t.integer :commit + t.string :password + + t.timestamps + end + end +end diff --git a/db/migrate/20140327073052_create_contesting_projects.rb b/db/migrate/20140327073052_create_contesting_projects.rb new file mode 100644 index 000000000..b9dc336b2 --- /dev/null +++ b/db/migrate/20140327073052_create_contesting_projects.rb @@ -0,0 +1,12 @@ +class CreateContestingProjects < ActiveRecord::Migration + def change + create_table :contesting_projects do |t| + t.integer :project_id + t.string :contest_id + t.integer :user_id + t.string :description + + t.timestamps + end + end +end diff --git a/db/migrate/20140327082704_change_created_at_of_contests_to_created_on.rb b/db/migrate/20140327082704_change_created_at_of_contests_to_created_on.rb new file mode 100644 index 000000000..32d52d35a --- /dev/null +++ b/db/migrate/20140327082704_change_created_at_of_contests_to_created_on.rb @@ -0,0 +1,11 @@ +class ChangeCreatedAtOfContestsToCreatedOn < ActiveRecord::Migration + def self.up + rename_column :contests, :created_at, :created_on + rename_column :contests, :updated_at, :updated_on + end + + def self.down + rename_column :contests, :created_on, :created_at + rename_column :contests, :updated_on, :updated_at + end +end diff --git a/db/migrate/20140401121611_add_reward_to_contesting_projects.rb b/db/migrate/20140401121611_add_reward_to_contesting_projects.rb new file mode 100644 index 000000000..8ac71c94b --- /dev/null +++ b/db/migrate/20140401121611_add_reward_to_contesting_projects.rb @@ -0,0 +1,5 @@ +class AddRewardToContestingProjects < ActiveRecord::Migration + def change + add_column :contesting_projects, :reward, :string + end +end diff --git a/db/migrate/20140402023357_create_join_in_competitions.rb b/db/migrate/20140402023357_create_join_in_competitions.rb new file mode 100644 index 000000000..b7fba87f1 --- /dev/null +++ b/db/migrate/20140402023357_create_join_in_competitions.rb @@ -0,0 +1,10 @@ +class CreateJoinInCompetitions < ActiveRecord::Migration + def change + create_table :join_in_competitions do |t| + t.integer :user_id + t.integer :competition_id + + t.timestamps + end + end +end