Revision 443:350acce374a2 app

View differences:

app/controllers/application_controller.rb
267 267
        uri = URI.parse(back_url)
268 268
        # do not redirect user to another host or to the login or register page
269 269
        if (uri.relative? || (uri.host == request.host)) && !uri.path.match(%r{/(login|account/register)})
270
          # soundsoftware: if back_url is the home page,
271
          # change it to My Page (#125)
272
          if (uri.path == home_path)
273
            uri.path = uri.path + "/my"
274
          end
270 275
          # soundsoftware: if login page is https but back_url http,
271 276
          # switch back_url to https to ensure cookie validity (#83)
272 277
          if (uri.scheme == "http") && (URI.parse(request.url).scheme == "https")
273 278
            uri.scheme = "https"
274
            back_url = uri.to_s
275 279
          end
280
          back_url = uri.to_s
276 281
          redirect_to(back_url)
277 282
          return
278 283
        end
app/controllers/attachments_controller.rb
16 16
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17 17

  
18 18
class AttachmentsController < ApplicationController
19

  
19 20
  before_filter :find_project
20 21
  before_filter :file_readable, :read_authorize, :except => :destroy
21 22
  before_filter :delete_authorize, :only => :destroy
23
  before_filter :active_authorize, :only => :toggle_active
22 24

  
23 25
  verify :method => :post, :only => :destroy
24 26

  
......
54 56
    redirect_to :controller => 'projects', :action => 'show', :id => @project
55 57
  end
56 58

  
59
  def toggle_active
60
    @attachment.active = !@attachment.active?
61
    @attachment.save!
62
    render :layout => false
63
  end
64

  
57 65
private
58 66
  def find_project
59 67
    @attachment = Attachment.find(params[:id])
......
77 85
    @attachment.deletable? ? true : deny_access
78 86
  end
79 87

  
88
  def active_authorize
89
    true
90
  end
91

  
80 92
  def detect_content_type(attachment)
81 93
    content_type = attachment.content_type
82 94
    if content_type.blank?
app/controllers/files_controller.rb
8 8
  include SortHelper
9 9

  
10 10
  def index
11
    sort_init 'filename', 'asc'
11
    sort_init 'active', 'desc'
12 12
    sort_update 'filename' => "#{Attachment.table_name}.filename",
13
		'active' => "#{Attachment.table_name}.active",
13 14
                'created_on' => "#{Attachment.table_name}.created_on",
14 15
                'size' => "#{Attachment.table_name}.filesize",
15 16
                'downloads' => "#{Attachment.table_name}.downloads"
......
33 34
    end
34 35
    redirect_to project_files_path(@project)
35 36
  end
37

  
36 38
end
app/controllers/members_controller.rb
28 28
      attrs = params[:member].dup
29 29
      if (user_ids = attrs.delete(:user_ids))
30 30
        user_ids.each do |user_id|
31
          members << Member.new(attrs.merge(:user_id => user_id))
31
          @new_member = Member.new(attrs.merge(:user_id => user_id))
32
          members << @new_member
33

  
34
          # send notification to member
35
          Mailer.deliver_added_to_project(@new_member, @project)
36

  
32 37
        end
33 38
      else
34
        members << Member.new(attrs)
39
        @new_member = Member.new(attrs)
40
        members << @new_member
41
        
42
        # send notification to member
43
        Mailer.deliver_added_to_project(@new_member, @project)
44
        
35 45
      end
46

  
36 47
      @project.members << members
48

  
37 49
    end
38 50
    respond_to do |format|
39 51
      if members.present? && members.all? {|m| m.valid? }
......
54 66
            errors = members.collect {|m|
55 67
              m.errors.full_messages
56 68
            }.flatten.uniq
57

  
58
            page.alert(l(:notice_failed_to_save_members, :errors => errors.join(', ')))
69
            
70
            # page.alert(l(:notice_failed_to_save_members, :errors => errors.join(', ')))
59 71
          }
60 72
        }
61 73
        
app/controllers/my_controller.rb
25 25
  BLOCKS = { 'issuesassignedtome' => :label_assigned_to_me_issues,
26 26
             'issuesreportedbyme' => :label_reported_issues,
27 27
             'issueswatched' => :label_watched_issues,
28
             'activitymyprojects' => :label_activity_my_recent,
28 29
             'news' => :label_news_latest,
30
             'tipoftheday' => :label_tipoftheday,
29 31
             'calendar' => :label_calendar,
30 32
             'documents' => :label_document_plural,
31 33
             'timelog' => :label_spent_time
32 34
           }.merge(Redmine::Views::MyPage::Block.additional_blocks).freeze
33 35

  
34
  DEFAULT_LAYOUT = {  'left' => ['issuesassignedtome'], 
35
                      'right' => ['issuesreportedbyme'] 
36
  DEFAULT_LAYOUT = {  'left' => ['tipoftheday', 'activitymyprojects'], 
37
                      'right' => ['issueswatched','calendar'] 
36 38
                   }.freeze
37 39

  
38 40
  verify :xhr => true,
app/controllers/projects_controller.rb
56 56
        @offset ||= @project_pages.current.offset
57 57
        @projects = Project.visible_roots.all(:offset => @offset, :limit => @limit, :order => sort_clause) 
58 58
        if User.current.logged?
59
          @user_projects = User.current.projects.sort_by(&:name)
59
          # seems sort_by gives us case-sensitive ordering, which we don't want
60
#          @user_projects = User.current.projects.sort_by(&:name)
61
          @user_projects = User.current.projects.all(:order => :name)
60 62
        end
61 63
        render :template => 'projects/index.rhtml', :layout => !request.xhr?
62 64
      }
......
215 217
  end
216 218

  
217 219
  verify :method => :post, :only => :modules, :render => {:nothing => true, :status => :method_not_allowed }
220
  
221
  def overview
222
    @project.has_welcome_page = params[:has_welcome_page]
223
    if @project.save
224
      flash[:notice] = l(:notice_successful_update)
225
    end
226
    redirect_to :action => 'settings', :id => @project, :tab => 'overview'
227
  end
228

  
218 229
  def modules
219 230
    @project.enabled_module_names = params[:enabled_module_names]
220 231
    flash[:notice] = l(:notice_successful_update)
app/controllers/repositories_controller.rb
36 36

  
37 37
  def edit
38 38
    @repository = @project.repository
39
    if !@repository && !params[:repository_scm].blank?
39

  
40
    if !@repository
41

  
42
      params[:repository_scm]='Mercurial'
43

  
40 44
      @repository = Repository.factory(params[:repository_scm])
41 45
      @repository.project = @project if @repository
42 46
    end
......
55 59
      @repository.merge_extra_info(p_extra)
56 60
      @repository.save
57 61
    end
62

  
58 63
    render(:update) do |page|
59 64
      page.replace_html "tab-content-repository",
60 65
                        :partial => 'projects/settings/repository'
app/controllers/sys_controller.rb
55 55
    render :nothing => true, :status => 404
56 56
  end
57 57

  
58
  def get_external_repo_url
59
    project = Project.find(params[:id])
60
    if project.repository
61
      repo = project.repository
62
      if repo.is_external?
63
        render :text => repo.external_url, :status => 200
64
      else
65
        render :nothing => true, :status => 200
66
      end
67
    end
68
  rescue ActiveRecord::RecordNotFound
69
    render :nothing => true, :status => 404
70
  end
71

  
72
  def clear_repository_cache
73
    project = Project.find(params[:id])
74
    if project.repository
75
      project.repository.clear_cache
76
    end
77
    render :nothing => true, :status => 200
78
  rescue ActiveRecord::RecordNotFound
79
    render :nothing => true, :status => 404
80
  end
81
  
58 82
  def set_embedded_active
59 83
    project = Project.find(params[:id])
60 84
    mods = project.enabled_modules
app/controllers/welcome_controller.rb
18 18
class WelcomeController < ApplicationController
19 19
  caches_action :robots
20 20

  
21
  include ProjectsHelper
22
  helper :projects
23

  
21 24
  def index
22
    @news = News.latest User.current
25
    @site_project = Project.find_by_identifier "soundsoftware-site"
26
    @site_news = []
27
    @site_news = News.latest_for @site_project if @site_project
23 28
    @projects = Project.latest User.current
24 29
    
25
    # tests if user is logged in to gfenerate the tips of the day list
30
    # tests if user is logged in to generate the tips of the day list
26 31
    if User.current.logged?
27 32
      @tipsoftheday = Setting.tipoftheday_text
28 33
    else
app/helpers/projects_helper.rb
23 23

  
24 24
  def project_settings_tabs
25 25
    tabs = [{:name => 'info', :action => :edit_project, :partial => 'projects/edit', :label => :label_information_plural},
26
            {:name => 'overview', :action => :edit_project, :partial => 'projects/settings/overview', :label => :label_welcome_page},
26 27
            {:name => 'modules', :action => :select_project_modules, :partial => 'projects/settings/modules', :label => :label_module_plural},
27 28
            {:name => 'members', :action => :manage_members, :partial => 'projects/settings/members', :label => :label_member_plural},
28 29
            {:name => 'versions', :action => :manage_versions, :partial => 'projects/settings/versions', :label => :label_version_plural},
......
49 50
    content_tag('select', options, :name => 'project[parent_id]', :id => 'project_parent_id')
50 51
  end
51 52

  
53
  def render_project_short_description(project)
54
    s = ''
55
    if (project.short_description)
56
      s << "<div class='description'>"
57
      s << textilizable(project.short_description, :project => project).gsub(/<[^>]+>/, '')
58
      s << "</div>"
59
    end
60
    s
61
  end
62
  
52 63
  # Renders a tree of projects as a nested set of unordered lists
53 64
  # The given collection may be a subset of the whole project tree
54 65
  # (eg. some intermediate nodes are private and can not be seen)
......
73 84
        classes = (ancestors.empty? ? 'root' : 'child')
74 85
        s << "<li class='#{classes}'><div class='#{classes}'>" +
75 86
               link_to_project(project, {}, :class => "project #{User.current.member_of?(project) ? 'my-project' : nil}")
76
        s << "<div class='wiki description'>#{textilizable(project.short_description, :project => project)}</div>" unless project.description.blank?
87
        s << render_project_short_description(project)
77 88
        s << "</div>\n"
78 89
        ancestors << project
79 90
      end
......
84 95
  end
85 96

  
86 97

  
98
  def render_my_project_in_hierarchy(project)
99
 
100
    s = ''
101

  
102
    if User.current.member_of?(project)
103

  
104
      # set the project environment to please macros.
105
      @project = project
106

  
107
      classes = (project.root? ? 'root' : 'child')
108
      
109
      s << "<li class='#{classes}'><div class='#{classes}'>" +
110
        link_to_project(project, {}, :class => "project my-project")
111
      if project.is_public?
112
        s << " <span class='public'>" << l("field_is_public") << "</span>"
113
      else
114
        s << " <span class='private'>" << l("field_is_private") << "</span>"
115
      end
116
      s << render_project_short_description(project)
117
      s << "</div>\n"
118

  
119
      cs = ''
120
      project.children.each do |child|
121
        cs << render_my_project_in_hierarchy(child)
122
      end
123

  
124
      if cs != ''
125
        s << "<ul class='projects'>\n" << cs << "</ul>\n";
126
      end
127

  
128
    end
129

  
130
    s
131

  
132
  end
133

  
87 134
  # Renders a tree of projects where the current user belongs
88 135
  # as a nested set of unordered lists
89 136
  # The given collection may be a subset of the whole project tree
90 137
  # (eg. some intermediate nodes are private and can not be seen)
91 138
  def render_my_project_hierarchy(projects)
139

  
92 140
    s = ''
93 141

  
94
    a = ''
142
    original_project = @project
95 143

  
96
    # Flag to tell if user has any projects
97
    t = FALSE
98
    
99
    if projects.any?
100
      ancestors = []
101
      original_project = @project
102
      projects.each do |project|
103
        # set the project environment to please macros.
104

  
105
        @project = project
106

  
107
        if User.current.member_of?(project):
108

  
109
          t = TRUE
110

  
111
          if (ancestors.empty? || project.is_descendant_of?(ancestors.last))
112
            s << "<ul class='projects #{ ancestors.empty? ? 'root' : nil}'>\n"
113
          else
114
            ancestors.pop
115
            s << "</li>"
116
            while (ancestors.any? && !project.is_descendant_of?(ancestors.last))
117
              ancestors.pop
118
              s << "</ul></li>\n"
119
            end
120
          end
121

  
122
          classes = (ancestors.empty? ? 'root' : 'child')
123
          s << "<li class='#{classes}'><div class='#{classes}'>" +
124
                 link_to_project(project, {}, :class => "project my-project")
125
          if project.is_public?
126
            s << " <span class='public'>" << l("field_is_public") << "</span>"
127
          else
128
            s << " <span class='private'>" << l("field_is_private") << "</span>"
129
          end
130
          s << "<div class='wiki description'>#{textilizable(project.short_description, :project => project)}</div>" unless project.description.blank?
131
          s << "</div>\n"
132
          ancestors << project
133
        end
134
       end
135
        s << ("</li></ul>\n" * ancestors.size)
136
        @project = original_project
144
    projects.each do |project|
145
      if project.root? || !projects.include?(project.parent)
146
        s << render_my_project_in_hierarchy(project)
147
      end
137 148
    end
138 149

  
139
    if t == TRUE
150
    @project = original_project
151

  
152
    if s != ''
153
      a = ''
140 154
      a << "<h2>"
141 155
      a <<  l("label_my_project_plural")
142 156
      a << "</h2>"
157
      a << "<ul class='projects root'>\n"
143 158
      a << s
144
    else
145
      a = s
159
      a << "</ul>\n"
160
      s = a
146 161
    end
162

  
163
    s
147 164
    
148
    a
149 165
  end
150 166

  
151 167
  # Renders a tree of projects that the current user does not belong
......
198 214
    s << " no_description" if project.description.blank?
199 215
    s << "'>" << link_to_project(project, {}, :class => "project #{User.current.member_of?(project) ? 'my-project' : nil}");
200 216
    s << "</div>"
201
    unless project.description.blank?
202
      s << "<div class='wiki description'>"
203
      s << textilizable(project.short_description, :project => project)
204
      s << "</div>"
205
    end
217
    s << render_project_short_description(project)
206 218
      
207 219
    s << "<td class='managers' align=top>"
208 220

  
......
230 242
    s << "</tr>"
231 243

  
232 244
    project.children.each do |child|
233
      s << render_project_in_table(child, oddeven, level + 1)
245
      if child.is_public? or User.current.member_of?(child)
246
        s << render_project_in_table(child, oddeven, level + 1)
247
      end
234 248
    end
235 249
    
236 250
    s
app/models/mailer.rb
32 32
    { :host => h, :protocol => Setting.protocol }
33 33
  end
34 34

  
35

  
36

  
37
  # Builds a tmail object used to email the specified user that he was added to a project
38
  #
39
  # Example:
40
  #   add_to_project(user) => tmail object
41
  #   Mailer.deliver_add_to_project(user) => sends an email to the registered user
42
  def added_to_project(member, project)
43

  
44
    user = User.find(member.user_id)
45

  
46
    set_language_if_valid user.language
47
    recipients user.mail
48
    subject l(:mail_subject_added_to_project, Setting.app_title)
49
    body :project_url => url_for(:controller => 'projects', :action => 'show', :id => project.id),
50
        :project_name => project.name
51
    render_multipart('added_to_project', body)
52
  end
53

  
54

  
55
  
35 56
  # Builds a tmail object used to email recipients of the added issue.
36 57
  #
37 58
  # Example:
......
458 479
    end
459 480
  end
460 481
end
482

  
483

  
484

  
485

  
app/models/news.rb
51 51
  def add_author_as_watcher
52 52
    Watcher.create(:watchable => self, :user => author)
53 53
  end
54

  
55
  # returns latest news for a specific project
56
  def self.latest_for(project, count = 5)
57
    find(:all, :limit => count, :conditions => [ "#{News.table_name}.project_id = #{project.id}", Project.allowed_to_condition(User.current, :view_news) ], :include => [ :author, :project ], :order => "#{News.table_name}.created_on DESC") 
58
  end
54 59
end
app/models/project.rb
468 468
  
469 469
  # Returns a short description of the projects (first lines)
470 470
  def short_description(length = 255)
471

  
472
    ## The short description is used in lists, e.g. Latest projects,
473
    ## My projects etc.  It should be no more than a line or two with
474
    ## no text formatting.
475

  
471 476
    ## Original Redmine code: this truncates to the CR that is more
472 477
    ## than "length" characters from the start.
473 478
    # description.gsub(/^(.{#{length}}[^\n\r]*).*$/m, '\1...').strip if description
474
    ## That's too much for us, and also we want to omit images and the
475
    ## like.  Truncate instead to the first CR that follows _any_
476
    ## non-blank text, and to the next word break beyond "length"
477
    ## characters if the result is still longer than that.
479

  
480
    ## That can leave too much text for us, and also we want to omit
481
    ## images and the like.  Truncate instead to the first CR that
482
    ## follows _any_ non-blank text, and to the next word break beyond
483
    ## "length" characters if the result is still longer than that.
484
    ##
478 485
    description.gsub(/![^\s]+!/, '').gsub(/^(\s*[^\n\r]*).*$/m, '\1').gsub(/^(.{#{length}}\b).*$/m, '\1 ...').strip if description
479 486
  end
480 487

  
app/models/repository.rb
268 268
    nil
269 269
  end
270 270

  
271
  def clear_cache
272
    clear_changesets
273
  end
274
    
271 275
  def self.scm_adapter_class
272 276
    nil
273 277
  end
app/models/repository/mercurial.rb
22 22
  has_many :changesets, :order => "#{Changeset.table_name}.id DESC", :foreign_key => 'repository_id'
23 23

  
24 24
  attr_protected :root_url
25
  validates_presence_of :url
25
  # validates_presence_of :url
26 26

  
27 27
  FETCH_AT_ONCE = 100  # number of changesets to fetch at once
28 28

  
app/views/activities/_recent.rhtml
1
<% events = @events_by_day %>
2
<% max = 5 %>
3
<% if (events.nil?) 
4
     activity = Redmine::Activity::Fetcher.new(User.current, :project => @project)
5
     
6
     if @project
7
        # Don't show news (duplicated with News box) or wiki edits (too
8
	# tedious) in project front page
9
        activity.scope = [ "changesets", "files", "issues", "documents" ]
10
     end
11
     
12
     events = activity.events(Date.today - 28, Date.today + 1)
13
     
14
     if defined? user
15
       events = events.select { |e| user.member_of? e.project }
16
     end
17
     
18
     events = events.first(max)
19

  
20
   end
21
%>
22

  
23
<div id="activity">
24

  
25
<% if @project.nil? %>
26
   <%= content_tag('h3', l(:label_activity_my_recent)) %>
27
   <div class="activity box">
28
<% end %>
29

  
30
<% if events.empty? %>
31

  
32
   <% if @project.nil? %>
33
     <p><%= l(:label_activity_my_recent_none) %></p>
34
   <% end %>
35

  
36
<% else %>
37

  
38
   <% if !@project.nil? %>
39
     <div class="activity box">
40
     <%= content_tag('h3', l(:label_activity_recent)) %>
41
   <% end %>
42

  
43
   <dl>
44
   <% events.sort {|x,y| y.event_datetime <=> x.event_datetime }.each do |e| -%>
45
     <dt class="<%= User.current.logged? && e.respond_to?(:event_author) && User.current == e.event_author ? 'me' : nil %>">
46
	<%= avatar(e.event_author, :size => "24") if e.respond_to?(:event_author) %>
47
     <span class="time"><%= format_time(e.event_datetime) %></span>
48
     <%= content_tag('span', link_to_project(e.project), :class => 'project') if @project.nil? || @project != e.project %>
49
     <% if e.respond_to?(:event_author) %>
50
       <span class="author"><%= e.event_author %></span>
51
     <% end %>
52
     </dt>
53
     <dd><%= link_to format_activity_title(e.event_title), e.event_url %>
54
     <span class="description"><%= format_activity_description(e.event_description) %></span>
55
     </dd>
56
   <% end -%>
57
   </dl>
58

  
59
   </div>
60

  
61
<% end %>
62

  
63
<% if events.empty? and @project.nil? %></div><% end %>
64

  
65
</div>
app/views/attachments/toggle_active.rhtml
1
<%=
2
file = Attachment.find(params[:id])
3
active_id = "active-" + file.id.to_s
4
link_to_remote image_tag(file.active? ? 'fav.png' : 'fav_off.png'),
5
  :url => {:controller => 'attachments', :action => 'toggle_active', :project_id => @project.id, :id => file},
6
  :update => active_id
7
%>
app/views/files/index.html.erb
5 5
<h2><%=l(:label_attachment_plural)%></h2>
6 6

  
7 7
<% delete_allowed = User.current.allowed_to?(:manage_files, @project) %>
8
<% active_change_allowed = delete_allowed %>
8 9

  
9 10
<table class="list files">
10 11
  <thead><tr>
12
    <%= sort_header_tag('active', :caption => l(:field_active)) %>
11 13
    <%= sort_header_tag('filename', :caption => l(:field_filename)) %>
12 14
    <%= sort_header_tag('created_on', :caption => l(:label_date), :default_order => 'desc') %>
13 15
    <%= sort_header_tag('size', :caption => l(:field_filesize), :default_order => 'desc') %>
14
    <%= sort_header_tag('downloads', :caption => l(:label_downloads_abbr), :default_order => 'desc') %>
16
    <%= sort_header_tag('downloads', :caption => l(:field_downloads), :default_order => 'desc') %>
15 17
    <th>MD5</th>
16 18
    <th></th>
17 19
  </tr></thead>
18 20
  <tbody>
21
<% have_file = false %>
19 22
<% @containers.each do |container| %>	
20 23
  <% next if container.attachments.empty? -%>
21 24
	<% if container.is_a?(Version) -%>
22 25
  <tr>
23
  	<th colspan="6" align="left">
26
  	<th colspan="7" align="left">
24 27
  		<%= link_to(h(container), {:controller => 'versions', :action => 'show', :id => container}, :class => "icon icon-package") %>
25 28
		</th>
26 29
	</tr>
27 30
	<% end -%>
28 31
  <% container.attachments.each do |file| %>		
29
  <tr class="file <%= cycle("odd", "even") %>">
30
    <td class="filename"><%= link_to_attachment file, :download => true, :title => file.description %></td>
32
  <tr class="file <%= cycle("odd", "even") %> <%= "active" if file.active? %>">
33
    <td class="active">
34
      <% have_file = true %>
35
      <% if active_change_allowed
36
           active_id = "active-" + file.id.to_s -%>
37
        <div id="<%= active_id %>">
38
        <%= link_to_remote image_tag(file.active? ? 'fav.png' : 'fav_off.png'),
39
              :url => {:controller => 'attachments', :action => 'toggle_active', :project_id => @project.id, :id => file},
40
              :update => active_id
41
        %>
42
        </div>
43
      <% else -%>
44
        <%= image_tag('fav.png') if file.active? %>
45
      <% end -%>
46
    </td>
47
    <% if file.active? %>
48
      <td class="filename active"><%= link_to_attachment file, :download => true %><br><span class="description"><%= h(file.description) %></span></td>
49
    <% else %>
50
      <td class="filename"><%= link_to_attachment file, :download => true, :title => file.description %>
51
    <% end %>
52
    </td>
31 53
    <td class="created_on"><%= format_time(file.created_on) %></td>
32 54
    <td class="filesize"><%= number_to_human_size(file.filesize) %></td>
33 55
    <td class="downloads"><%= file.downloads %></td>
......
43 65
  </tbody>
44 66
</table>
45 67

  
68
<%= l(:text_files_active_change) if active_change_allowed and have_file %>
69

  
46 70
<% html_title(l(:label_attachment_plural)) -%>
app/views/layouts/base.rhtml
54 54
      <h3 id="project-ancestors-title"><%= page_header_title[1] %></h3>
55 55
    <% end %>  
56 56

  
57
    <h1  id="project-title"
57
    <h1 id="project-title"
58 58
      <% unless page_header_title[1].empty? %>
59 59
        style="margin-top: 0px; "
60 60
      <% end %>  
61
    ><%= page_header_title[0] %></h1>
61
    ><% if display_main_menu?(@project) %>
62
       <%= link_to_project(@project) %>
63
     <% else %> 
64
       <%= page_header_title[0] %>
65
     <% end %>
66
    </h1>
62 67
    
63 68
    <% if display_main_menu?(@project) %>
64 69
    <div id="main-menu">
......
85 90
	
86 91
<div id="footer">
87 92
  <div class="bgl"><div class="bgr">
88
    Powered by <%= link_to Redmine::Info.app_name, Redmine::Info.url %> &copy; 2006-2011 Jean-Philippe Lang
93
    <small>Powered by <%= link_to Redmine::Info.app_name, Redmine::Info.url %><br>&copy; 2006-2011 Jean-Philippe Lang</small>
89 94
  </div></div>
90 95
</div>
91 96
</div>
app/views/mailer/added_to_project.text.html.rhtml
1
<p><%= l(:notice_added_to_project, :project_name => @project_name) %></p>
2
<p><%= l(:notice_project_homepage, :project_url => @project_url) %></p>
3

  
app/views/mailer/added_to_project.text.plain.rhtml
1
<%= l(:notice_added_to_project, :project_name => @project_name) %>
2
<%= l(:notice_project_homepage, :project_url => @project_url)  %>
app/views/my/blocks/_activitymyprojects.rhtml
1

  
2
<%= render :partial => 'activities/recent', :locals => { :user => User.current } %>
3

  
4

  
app/views/my/blocks/_tipoftheday.rhtml
1
    <h3><%=l(:label_tipoftheday)%></h3>
2
    <div class="tipoftheday box">
3
          <div class="tip"><%= textilizable Setting.tipoftheday_text %></div>
4
    </div>
app/views/news/_news.rhtml
1
<p><%= link_to_project(news.project) + ': ' unless @project %>
2
<%= link_to h(news.title), news_path(news) %>
3
<%= "(#{l(:label_x_comments, :count => news.comments_count)})" if news.comments_count > 0 %>
4
<br />
1
<div id="news">
2
<dt>
3
<span class="time"><%= format_time(news.created_on) %></span>
4
<% project ||= @project %>
5
<% if !project %>
6
<span class="project"><%= link_to_project(news.project) %></span>
7
<% end %>
8
<span class="headline"><%= link_to h(news.title), news_path(news) %></span>
9
<span class="comments"><%= "(#{l(:label_x_comments, :count => news.comments_count)})" if news.comments_count > 0 %></span>
10
</dt><dd>
5 11
<% unless news.summary.blank? %><span class="summary"><%=h news.summary %></span><br /><% end %>
6
<span class="author"><%= authoring news.created_on, news.author %></span></p>
12
</dd>
13
</div>
app/views/projects/settings/_members.rhtml
2 2
<% roles = Role.find_all_givable
3 3
   members = @project.member_principals.find(:all, :include => [:roles, :principal]).sort %>
4 4

  
5

  
5 6
<div class="splitcontentleft">
6 7
<% if members.any? %>
7 8
<table class="list members">
......
73 74
		<% end %>
74 75
		</div>
75 76
		
76
    <p><%= l(:label_role_plural) %>:
77
    <p><%= l(:label_set_role_plural) %>:</p>
77 78
    <% roles.each do |role| %>
78
    	<label><%= check_box_tag 'member[role_ids][]', role.id %> <%=h role %></label>
79
   	<% end %></p>
79
    	<label><%= check_box_tag 'member[role_ids][]', role.id %> <%=h role %> </label><div style="margin-left: 2em; margin-bottom: 0.5em"><i><%=l( 'label_' + role.name.downcase + "_description").to_sym %></i></div>
80
   	<% end %>
80 81
   	
81 82
    <p><%= submit_tag l(:button_add), :id => 'member-add-submit' %></p>
82 83
		</fieldset>
app/views/projects/settings/_overview.rhtml
1

  
2
<% form_for :project, @project,
3
            :url => { :action => 'overview', :id => @project },
4
            :html => {:id => 'overview-form'} do |f| %>
5

  
6
<div class="box tabular">
7

  
8
<p><%= l(:text_has_welcome_page_info, { :overview_link => link_to(l(:label_overview), { :controller => 'projects', :action => 'show' } ) } ) %></p>
9

  
10
<% if @project.module_enabled? :wiki %>
11

  
12
<p><%= link_to(l(:button_welcome_page_edit), {:controller => 'wiki', :action => 'edit', :project_id => @project, :id => Wiki.titleize("Overview")}, :class => 'icon icon-edit') %>
13

  
14
<% else %>
15

  
16
<p><%= l(:text_has_welcome_page_wiki_disabled, { :modules_link => link_to(l(:label_module_plural), { :controller => 'projects', :action => 'settings', :tab => 'modules' } ) } ) %></p>
17

  
18
<% end %>
19

  
20
<p><label for="has_welcome_page"><%= l(:label_has_welcome_page) %></label>
21
<%= check_box_tag 'has_welcome_page', 1, @project.has_welcome_page? -%>
22
<br/><em><%= l(:setting_has_welcome_page) %></em>
23

  
24
</p>
25

  
26
</div>
27

  
28
<%= submit_tag l(:button_save) %>
29

  
30
<% end %>
app/views/projects/settings/_repository.rhtml
1

  
2
<%= javascript_include_tag 'repository' %>
3

  
1 4
<% remote_form_for :repository, @repository,
2 5
                   :url => { :controller => 'repositories', :action => 'edit', :id => @project },
3 6
                   :builder => TabularFormBuilder,
......
6 9
<%= error_messages_for 'repository' %>
7 10

  
8 11
<div class="box tabular">
9
<% if !@repository || !@repository.url %>
10
<ul><li><%= l(:text_settings_repo_creation) %></li></ul>
11
<% end %>
12
<p><%= label_tag('repository_scm', l(:label_scm)) %><%= scm_select_tag(@repository) %></p>
13
<%= repository_field_tags(f, @repository) if @repository %>
12

  
13
<p>
14
<% if @repository %>
15
   <%= l(:text_settings_repo_explanation) %></ br>
16
   <% if @repository.is_external %>
17
     <p><%= l(:text_settings_repo_is_external) %></ br>
18
   <% else %>
19
     <p><%= l(:text_settings_repo_is_internal) %></ br>
20
   <% end %>
21
</p>
22

  
23

  
24

  
25

  
26

  
27
<p>
28
	<%= label_tag('repository_is_external', l(:label_is_external_repository)) %>
29
	<%= check_box :repository, :is_external, :onclick => "toggle_ext_url()" %> 
30
	<br/><em><%= l(:setting_external_repository) %></em>
31
</p>
32

  
33

  
34
<p>
35
	<%= label_tag('repository_external_url', l(:label_repository_external_url)) %>
36
	<%= text_field :repository, :external_url, :disabled => !(@repository and @repository.is_external) %> 
37
	<br/><em><%= l(:setting_external_repository_url) %></em>
38
</p>
39

  
40
<p><%= l(:text_settings_repo_need_help) %></p>
41

  
14 42
</div>
15 43

  
16 44
<div class="contextual">
......
22 50
                :id         => @project
23 51
                },
24 52
             :class => 'icon icon-user') %>
25
<%= link_to(l(:button_delete), {:controller => 'repositories', :action => 'destroy', :id => @project},
26
            :confirm => l(:text_are_you_sure),
27
            :method  => :post,
28
            :class   => 'icon icon-del') %>
29 53
<% end %>
30 54
</div>
31 55

  
32
<%= submit_tag((@repository.nil? || @repository.new_record?) ? l(:button_create) : l(:button_save), :disabled => @repository.nil?) %>
56
<%= submit_tag(l(:button_save), :onclick => remote_function(:url => { :controller => 'repositories', :action => 'edit', :id => @project }, :method => :get, :with => "Form.serialize(this.form)")) %>
57

  
58
<% else %>
59
   <%= l(:text_settings_repo_creation) %></ br>
33 60
<% end %>
61

  
62
<% end %>
app/views/projects/show.rhtml
4 4
	<% end %>
5 5
</div>
6 6

  
7
<% if @project.has_welcome_page %>
8
<% page = @project.wiki.find_page("Overview") %>
9
<% end %>
10

  
11
<% if page %>
12

  
13
<div class="contextual" style="clear: right">
14
<ul>
15
<% @users_by_role.keys.sort.each do |role| %>
16
<li><%=h role %>: <%= @users_by_role[role].sort.collect{|u| link_to_user u}.join(", ") %></li>
17
<% end %>
18
<% unless @project.homepage.blank? %><li><%=l(:field_homepage)%>: <%= auto_link(h(@project.homepage)) %></li><% end %>
19
<% if @subprojects.any? %>
20
	<li><%=l(:label_subproject_plural)%>:
21
	    <%= @subprojects.collect{|p| link_to(h(p), :action => 'show', :id => p)}.join(", ") %></li>
22
<% end %>
23
</ul>
24
</div>
25

  
26
<%= render(:partial => "wiki/content", :locals => {:content => page.content_for_version()}) %>
27

  
28
<% else %>
29

  
7 30
<h2><%=l(:label_overview)%></h2> 
8 31
	
9 32
<div class="splitcontentleft">
......
23 46
	<% end %>
24 47
	</ul>	
25 48

  
26
  <% if User.current.allowed_to?(:view_issues, @project) %>
49
  <% if User.current.allowed_to?(:view_issues, @project) and @open_issues_by_tracker.values.any? %>
50

  
27 51
  <div class="issues box">    
28 52
    <h3><%=l(:label_issue_tracking)%></h3>
29 53
    <ul>
......
46 70
			<% end %>
47 71
		</p>
48 72
  </div>
73

  
49 74
  <% end %>
75

  
50 76
  <%= call_hook(:view_projects_show_left, :project => @project) %>
51 77
</div>
52 78

  
......
60 86
    <p><%= link_to l(:label_news_view_all), :controller => 'news', :action => 'index', :project_id => @project %></p>
61 87
  </div>  
62 88
  <% end %>
89

  
90
  <%= render :partial => 'activities/recent' %>
91

  
63 92
  <%= call_hook(:view_projects_show_right, :project => @project) %>
64 93
</div>
65 94

  
......
73 102
    <%= call_hook(:view_projects_show_sidebar_bottom, :project => @project) %>
74 103
<% end %>
75 104

  
105
<% end %>
106

  
76 107
<% content_for :header_tags do %>
77 108
<%= auto_discovery_link_tag(:atom, {:controller => 'activities', :action => 'index', :id => @project, :format => 'atom', :key => User.current.rss_key}) %>
78 109
<% end %>
app/views/search/index.rhtml
19 19
</div>
20 20

  
21 21
<% if @results %>
22
    
23
    <h3><%= l(:label_result_plural) %> (<%= @results_by_type.values.sum %>)</h3>
22 24
    <div id="search-results-counts">
23 25
    <%= render_results_by_type(@results_by_type) unless @scope.size == 1 %>
24 26
    </div>
25
    
26
    <h3><%= l(:label_result_plural) %> (<%= @results_by_type.values.sum %>)</h3>
27 27
    <dl id="search-results">
28 28
      <% @results.each do |e| %>
29 29
        <dt class="<%= e.event_type %>"><%= content_tag('span', h(e.project), :class => 'project') unless @project == e.project %> <%= link_to highlight_tokens(truncate(e.event_title, :length => 255), @tokens), e.event_url %></dt>
app/views/users/edit.rhtml
9 9
<%= render_tabs user_settings_tabs %>
10 10

  
11 11
<% html_title(l(:label_user), @user.login, l(:label_administration)) -%>
12

  
app/views/welcome/index.rhtml
9 9
<div class="splitcontentleft">
10 10
  <%= textilizable Setting.welcome_text %>
11 11
  
12
  <% if @news.any? %>
13
  <div class="news box">
14
	<h3><%=l(:label_news_latest)%></h3>
15
		<%= render :partial => 'news/news', :collection => @news %>
16
		<%= link_to l(:label_news_view_all), :controller => 'news' %>
17
  </div>
18
  <% end %>
19 12
  <%= call_hook(:view_welcome_index_left, :projects => @projects) %>
20 13
</div>
21 14

  
22 15
<div class="splitcontentright">
23
  <% if not @tipsoftheday.empty? %>
24
    <div class="newsoftheday box">
25
          <h3><%=l(:label_tipoftheday)%></h3>
26
          <%= textilizable @tipsoftheday %>
27
    </div>
16
  <% if @site_news.any? %>
17
  <div class="news box">
18
	<h3><%=l(:label_news_site_latest)%></h3>
19
	<%= render :partial => 'news/news', :locals => { :project => @site_project }, :collection => @site_news %>
20
	
21
	<%= link_to l(:label_news_more), { :controller => 'projects', :action => @site_project.identifier, :id => 'news' } %>
22
  </div>
28 23
  <% end %>
29

  
30 24
    <% if @projects.any? %>
31 25
	<div class="projects box">
32 26
	<h3><%=l(:label_project_latest)%></h3>
33 27
		<ul>
34 28
		<% for project in @projects %>
35 29
		  <% @project = project %>
36
			<li>
37
			<%= link_to_project project %> (<%= format_time(project.created_on) %>)
38
			<%= textilizable project.short_description, :project => project %>
30
			<li class="latest">
31
			<span class="title"><%= link_to_project project %></span>
32
			<span class="time"><%= format_time(project.created_on)%></span>
33
			<%= render_project_short_description project %>
39 34
			</li>
40 35
		<% end %>
41 36
    <% @project = nil %>
42 37
		</ul>
38
	<%= link_to l(:label_projects_more), :controller => 'projects' %>
43 39
	</div>
44 40
	<% end %>
45 41
    <%= call_hook(:view_welcome_index_right, :projects => @projects) %>

Also available in: Unified diff