]> source.dussan.org Git - redmine.git/commitdiff
Adds preview option to the wiki toolbar (#27758).
authorJean-Philippe Lang <jp_lang@yahoo.fr>
Wed, 26 Sep 2018 07:27:30 +0000 (07:27 +0000)
committerJean-Philippe Lang <jp_lang@yahoo.fr>
Wed, 26 Sep 2018 07:27:30 +0000 (07:27 +0000)
Patch by Marius BALTEANU.

git-svn-id: http://svn.redmine.org/redmine/trunk@17521 e93f8b46-1217-0410-a6f0-8f06a7374b81

38 files changed:
app/controllers/messages_controller.rb
app/controllers/previews_controller.rb
app/controllers/wiki_controller.rb
app/views/boards/show.html.erb
app/views/common/_preview.html.erb
app/views/issues/_edit.html.erb
app/views/issues/_form.html.erb
app/views/issues/new.html.erb
app/views/journals/_notes_form.html.erb
app/views/messages/_form.html.erb
app/views/messages/edit.html.erb
app/views/messages/new.html.erb
app/views/messages/show.html.erb
app/views/news/_form.html.erb
app/views/news/edit.html.erb
app/views/news/index.html.erb
app/views/news/new.html.erb
app/views/news/show.html.erb
app/views/previews/issue.html.erb [deleted file]
app/views/wiki/edit.html.erb
config/locales/en.yml
config/routes.rb
lib/redmine/wiki_formatting.rb
lib/redmine/wiki_formatting/markdown/helper.rb
lib/redmine/wiki_formatting/textile/helper.rb
public/javascripts/application.js
public/javascripts/attachments.js
public/javascripts/jstoolbar/jstoolbar-textile.min.js [deleted file]
public/javascripts/jstoolbar/jstoolbar.js
public/javascripts/jstoolbar/lang/jstoolbar-en.js
public/stylesheets/application.css
public/stylesheets/jstoolbar.css
test/functional/messages_controller_test.rb
test/functional/previews_controller_test.rb
test/integration/attachments_test.rb
test/integration/layout_test.rb
test/integration/routing/previews_test.rb
test/system/issues_test.rb

index 76bc19cf6465d905d8a2ebeea548dba1896eb204..0ba360e9a42b9953d5c916adf2df5da115a6afb7 100644 (file)
@@ -118,7 +118,7 @@ class MessagesController < ApplicationController
 
   def preview
     message = @board.messages.find_by_id(params[:id])
-    @text = (params[:message] || params[:reply])[:content]
+    @text = params[:text] ? params[:text] : nil
     @previewed = message
     render :partial => 'common/preview'
   end
index 37cdc466879836a576c2b48153232218adf15de4..41e6941f9c08a7cf8453b4348aa1d41083e7b7f1 100644 (file)
 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 
 class PreviewsController < ApplicationController
-  before_action :find_project, :find_attachments
+  before_action :find_project, :except => :text 
+  before_action :find_attachments
 
   def issue
-    @issue = Issue.visible.find_by_id(params[:id]) unless params[:id].blank?
+    @issue = Issue.visible.find_by_id(params[:issue_id]) unless params[:issue_id].blank?
     if @issue
-      @description = params[:issue] && params[:issue][:description]
-      if @description && @description.gsub(/(\r?\n|\n\r?)/, "\n") == @issue.description.to_s.gsub(/(\r?\n|\n\r?)/, "\n")
-        @description = nil
-      end
-      @notes = params[:journal] ? params[:journal][:notes] : nil
-      @notes ||= params[:issue] ? params[:issue][:notes] : nil
-    else
-      @description = (params[:issue] ? params[:issue][:description] : nil)
+      @previewed = @issue
     end
-    render :layout => false
+    @text = params[:text] ? params[:text] : nil
+    render :partial => 'common/preview'
   end
 
   def news
     if params[:id].present? && news = News.visible.find_by_id(params[:id])
       @previewed = news
     end
-    @text = (params[:news] ? params[:news][:description] : nil)
+    @text = params[:text] ? params[:text] : nil
     render :partial => 'common/preview'
   end
 
+  def text
+    @text = params[:text] ? params[:text] : nil
+    render :partial => 'common/preview'
+  end
   private
 
   def find_project
index b43b933cdd101dece26ef410dcaebe99d207039b..c5f7cdc0c3d1d55d747b119f9a8e21cbd10f5d84 100644 (file)
@@ -321,7 +321,7 @@ class WikiController < ApplicationController
       @attachments += page.attachments
       @previewed = page.content
     end
-    @text = params[:content][:text]
+    @text = params[:content].present? ? params[:content][:text] : params[:text]
     render :partial => 'common/preview'
   end
 
index 4a0a588e982a54e9621275e65916ce457c5f8aa6..02dffa278e135f0d110c29fd18405bee99b4fa27 100644 (file)
 <%= form_for @message, :url => new_board_message_path(@board), :html => {:multipart => true, :id => 'message-form'} do |f| %>
   <%= render :partial => 'messages/form', :locals => {:f => f} %>
   <p><%= submit_tag l(:button_create) %>
-  <%= preview_link(preview_board_message_path(@board), 'message-form') %> |
   <%= link_to l(:button_cancel), "#", :onclick => '$("#add-message").hide(); return false;' %></p>
 <% end %>
-<div id="preview" class="wiki"></div>
 <% end %>
 </div>
 
@@ -60,7 +58,6 @@
 <% end %>
 
 <% html_title @board.name %>
-
 <% content_for :header_tags do %>
     <%= auto_discovery_link_tag(:atom, {:format => 'atom', :key => User.current.rss_key}, :title => "#{@project}: #{@board}") %>
 <% end %>
index 90d83ce8cb27e38afbfdf2ed3c90f2def405f262..ee22288c0cdf56c39226eb97268a6f92e0a84e45 100644 (file)
@@ -1,3 +1,5 @@
-<fieldset class="preview"><legend><%= l(:label_preview) %></legend>
-<%= textilizable @text, :attachments => @attachments, :object => @previewed %>
-</fieldset>
+<% unless @text.blank? %>
+  <%= textilizable @text, :attachments => @attachments, :object => @previewed %>
+<% else        %>
+  <p><%= l(:label_nothing_to_preview) %></p>
+<% end %>
\ No newline at end of file
index fe2119a07a60064935fffbfa4479e4d43146aa80..3afaee4ca91ec8d4f0d0f00eeccc5a4afabf3bd7 100644 (file)
@@ -30,7 +30,7 @@
     <% if @issue.notes_addable? %>
       <fieldset><legend><%= l(:field_notes) %></legend>
       <%= f.text_area :notes, :cols => 60, :rows => 10, :class => 'wiki-edit', :no_label => true %>
-      <%= wikitoolbar_for 'issue_notes' %>
+      <%= wikitoolbar_for 'issue_notes', preview_issue_path(:project_id => @project, :issue_id => @issue) %>
 
       <% if @issue.safe_attribute? 'private_notes' %>
       <%= f.check_box :private_notes, :no_label => true %> <label for="issue_private_notes"><%= l(:field_private_notes) %></label>
     <%= f.hidden_field :lock_version %>
     <%= hidden_field_tag 'last_journal_id', params[:last_journal_id] || @issue.last_journal_id %>
     <%= submit_tag l(:button_submit) %>
-    <%= preview_link preview_edit_issue_path(:project_id => @project, :id => @issue), 'issue-form' %>
-    | <%= link_to l(:button_cancel), issue_path(id: @issue.id), :onclick => params[:action] == 'show' ? "$('#update').hide(); return false;" : '' %>
+    <%= link_to l(:button_cancel), issue_path(id: @issue.id), :onclick => params[:action] == 'show' ? "$('#update').hide(); return false;" : '' %>
 
     <%= hidden_field_tag 'prev_issue_id', @prev_issue_id if @prev_issue_id %>
     <%= hidden_field_tag 'next_issue_id', @next_issue_id if @next_issue_id %>
     <%= hidden_field_tag 'issue_position', @issue_position if @issue_position %>
     <%= hidden_field_tag 'issue_count', @issue_count if @issue_count %>
+
 <% end %>
 
-<div id="preview" class="wiki"></div>
index f25cb3b2b891e5c01e37b6929c2bb4238a5bcdf9..c99927d8a8157f26f10ab5afcaa08486d188cf22 100644 (file)
@@ -37,7 +37,7 @@
                    :no_label => true %>
   <% end %>
 </p>
-<%= wikitoolbar_for 'issue_description' %>
+<%= wikitoolbar_for 'issue_description', preview_issue_path(:project_id => @issue.project, :issue_id => @issue.id) %>
 <% end %>
 
 <div id="attributes" class="attributes">
index 1c2c8bac8f8da3cb103ccbf1aa64092b49f3036b..22a174a11e46d9a5c18f0cf8dd578a6f647f65f8 100644 (file)
 
   <%= submit_tag l(:button_create) %>
   <%= submit_tag l(:button_create_and_continue), :name => 'continue' %>
-  <%= preview_link preview_new_issue_path(:project_id => @issue.project), 'issue-form' %>
 <% end %>
 
-<div id="preview" class="wiki"></div>
-
 <% content_for :header_tags do %>
     <%= robot_exclusion_tag %>
 <% end %>
index 2ab97876964e6243f346dd6da402ceb9f81a900b..eecc31da93d60df9f0188a5306d5bd319ba8291a 100644 (file)
     <% end %>
     <%= call_hook(:view_journals_notes_form_after_notes, { :journal => @journal}) %>
     <p><%= submit_tag l(:button_save) %>
-    <%= preview_link preview_edit_issue_path(:project_id => @project, :id => @journal.issue), 
-                     "journal-#{@journal.id}-form",
-                     "journal_#{@journal.id}_preview" %> |
     <%= link_to l(:button_cancel), '#', :onclick => "$('#journal-#{@journal.id}-form').remove(); $('#journal-#{@journal.id}-notes').show(); return false;" %></p>
-
-    <div id="journal_<%= @journal.id %>_preview" class="wiki"></div>
 <% end %>
-<%= wikitoolbar_for "journal_#{@journal.id}_notes" %>
+<%= wikitoolbar_for "journal_#{@journal.id}_notes", preview_issue_path(:project_id => @project, :issue_id => @journal.issue) %>
index d9f48af5c9a21b0d3ff61115537c92398c514883..adba0522470a50270576f4ada3f8220f7ff25377 100644 (file)
@@ -24,7 +24,7 @@
 <p>
 <%= label_tag "message_content", l(:description_message_content), :class => "hidden-for-sighted" %>
 <%= f.text_area :content, :cols => 80, :rows => 15, :class => 'wiki-edit', :id => 'message_content' %></p>
-<%= wikitoolbar_for 'message_content' %>
+<%= wikitoolbar_for 'message_content', preview_board_message_path(:board_id => @board, :id => @message) %>
 <!--[eoform:message]-->
 
 <p><%= l(:label_attachment_plural) %><br />
index 53948e4dac5133f32afa5781dc6b44d9c86fe9a1..063676197fdf0ffbbb67563937d4f9b8a0205f43 100644 (file)
@@ -12,6 +12,4 @@
   <%= render :partial => 'form',
              :locals => {:f => f, :replying => !@message.parent.nil?} %>
   <%= submit_tag l(:button_save) %>
-  <%= preview_link({:controller => 'messages', :action => 'preview', :board_id => @board, :id => @message}, 'message-form') %>
 <% end %>
-<div id="preview" class="wiki"></div>
index f8d8406949f2b337922906ce0804815fcdbe565f..be638141359d9c49eb937268d85e95edd9b5664d 100644 (file)
@@ -3,7 +3,4 @@
 <%= form_for @message, :url => {:action => 'new'}, :html => {:multipart => true, :id => 'message-form'} do |f| %>
   <%= render :partial => 'form', :locals => {:f => f} %>
   <%= submit_tag l(:button_create) %>
-  <%= preview_link({:controller => 'messages', :action => 'preview', :board_id => @board}, 'message-form') %>
 <% end %>
-
-<div id="preview" class="wiki"></div>
index db41b0cc307852e8c0638c508c4d68be91a69e2c..5756a92671eb5a3dcc22224a3bffc2d15b5d7312 100644 (file)
@@ -85,9 +85,7 @@
 <%= form_for @reply, :as => :reply, :url => {:action => 'reply', :id => @topic}, :html => {:multipart => true, :id => 'message-form'} do |f| %>
   <%= render :partial => 'form', :locals => {:f => f, :replying => true} %>
   <%= submit_tag l(:button_submit) %>
-  <%= preview_link({:controller => 'messages', :action => 'preview', :board_id => @board}, 'message-form') %>
 <% end %>
-<div id="preview" class="wiki"></div>
 </div>
 <% end %>
 
index 3f48d21de82dcb32ea6496c44b06e4cc829c4769..dbf21df484e631743fe6d16273455745cd98e312 100644 (file)
@@ -7,4 +7,4 @@
 <p id="attachments_form"><label><%= l(:label_attachment_plural) %></label><%= render :partial => 'attachments/form', :locals => {:container => @news} %></p>
 </div>
 
-<%= wikitoolbar_for 'news_description' %>
+<%= wikitoolbar_for 'news_description', preview_news_path(:project_id => @project, :id => @news) %>
\ No newline at end of file
index 4e4cf2e2b712f4d3cad2676677d8d926390e6354..50b897324a038dda99106df119be08236104f555 100644 (file)
@@ -3,9 +3,7 @@
 <%= labelled_form_for @news, :html => { :id => 'news-form', :multipart => true, :method => :put } do |f| %>
 <%= render :partial => 'form', :locals => { :f => f } %>
 <%= submit_tag l(:button_save) %>
-<%= preview_link preview_news_path(:project_id => @project, :id => @news), 'news-form' %>
 <% end %>
-<div id="preview" class="wiki"></div>
 
 <% content_for :header_tags do %>
   <%= stylesheet_link_tag 'scm' %>
index 2ff5a1c8c8e7f3c81b3bd20f22322a4d711e41a0..cd51aa950daa5561d386c52ebd172d797d3d91dc 100644 (file)
                                            :html => { :id => 'news-form', :multipart => true } do |f| %>
 <%= render :partial => 'news/form', :locals => { :f => f } %>
 <%= submit_tag l(:button_create) %>
-<%= preview_link preview_news_path(:project_id => @project), 'news-form' %> |
 <%= link_to l(:button_cancel), "#", :onclick => '$("#add-news").hide()' %>
 <% end if @project %>
-<div id="preview" class="wiki"></div>
 </div>
 
 <h2><%=l(:label_news_plural)%></h2>
index f96dd5c52c6bfe7d6e42226e2ee3347c853a8d9f..cf57140b8c32baf097912445c8d68a176ae586ff 100644 (file)
@@ -4,6 +4,4 @@
                                            :html => { :id => 'news-form', :multipart => true } do |f| %>
   <%= render :partial => 'news/form', :locals => { :f => f } %>
   <%= submit_tag l(:button_create) %>
-  <%= preview_link preview_news_path(:project_id => @project), 'news-form' %>
 <% end %>
-<div id="preview" class="wiki"></div>
index 72c94a9c72d95a4e553e5b35c3eda3360489a6ec..d8d098cce5333753fd36fda7f369deb7fdc5865f 100644 (file)
                                            :html => { :id => 'news-form', :multipart => true, :method => :put } do |f| %>
 <%= render :partial => 'form', :locals => { :f => f } %>
 <%= submit_tag l(:button_save) %>
-<%= preview_link preview_news_path(:project_id => @project, :id => @news), 'news-form' %> |
 <%= link_to l(:button_cancel), "#", :onclick => '$("#edit-news").hide(); return false;' %>
 <% end %>
-<div id="preview" class="wiki"></div>
 </div>
 <% end %>
 
@@ -56,7 +54,7 @@
 <%= form_tag({:controller => 'comments', :action => 'create', :id => @news}, :id => "add_comment_form", :style => "display:none;") do %>
 <div class="box">
     <%= text_area 'comment', 'comments', :cols => 80, :rows => 15, :class => 'wiki-edit' %>
-    <%= wikitoolbar_for 'comment_comments' %>
+    <%= wikitoolbar_for 'comment_comments', preview_news_path(:project_id => @project, :id => @news) %>
 </div>
 <p><%= submit_tag l(:button_add) %></p>
 <% end %>
diff --git a/app/views/previews/issue.html.erb b/app/views/previews/issue.html.erb
deleted file mode 100644 (file)
index a88bec6..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-<% if @notes %>
-  <fieldset class="preview"><legend><%= l(:field_notes) %></legend>
-    <%= textilizable @notes, :attachments => @attachments, :object => @issue %>
-  </fieldset>
-<% end %>
-
-<% if @description %>
-  <fieldset class="preview"><legend><%= l(:field_description) %></legend>
-    <%= textilizable @description, :attachments => @attachments, :object => @issue %>
-  </fieldset>
-<% end %>
index 6692cfa6e7f98961152801c9ce5c4a3f39dcd438..60a2f659698471164f23cb305e3e8248dd1b3e74 100644 (file)
 
 <p>
   <%= submit_tag l(:button_save) %>
-   <%= preview_link({:controller => 'wiki', :action => 'preview', :project_id => @project, :id => @page.title }, 'wiki_form') %>
-   | <%= link_to l(:button_cancel), wiki_page_edit_cancel_path(@page) %>
+  <%= link_to l(:button_cancel), wiki_page_edit_cancel_path(@page) %>
  </p>
-<%= wikitoolbar_for 'content_text' %>
+<%= wikitoolbar_for 'content_text', preview_project_wiki_page_path(:project_id => @project, :id => @page.title) %>
 <% end %>
 
-<div id="preview" class="wiki"></div>
-
 <% content_for :header_tags do %>
   <%= robot_exclusion_tag %>
 <% end %>
index 6bf07ff34df7c58f9af6d09c5dd19db251ae70b6..6e2cd75c5128ec2612a81aee69495f057577e620 100644 (file)
@@ -1030,6 +1030,7 @@ en:
   label_font_monospace: Monospaced font
   label_font_proportional: Proportional font
   label_last_notes: Last notes
+  label_nothing_to_preview: Nothing to preview
 
   button_login: Login
   button_submit: Submit
index f61f2e06792b9cce8ffab8baba640ec5b6a24ccf..0344982085f42413079a387e54e4cc96ad2f2726 100644 (file)
@@ -26,9 +26,8 @@ Rails.application.routes.draw do
   get 'account/activation_email', :to => 'account#activation_email', :as => 'activation_email'
 
   match '/news/preview', :controller => 'previews', :action => 'news', :as => 'preview_news', :via => [:get, :post, :put, :patch]
-  match '/issues/preview/new/:project_id', :to => 'previews#issue', :as => 'preview_new_issue', :via => [:get, :post, :put, :patch]
-  match '/issues/preview/edit/:id', :to => 'previews#issue', :as => 'preview_edit_issue', :via => [:get, :post, :put, :patch]
   match '/issues/preview', :to => 'previews#issue', :as => 'preview_issue', :via => [:get, :post, :put, :patch]
+  match '/preview/text', :to => 'previews#text', :as => 'preview_text', :via => [:get, :post, :put, :patch]
 
   match 'projects/:id/wiki/destroy', :to => 'wikis#destroy', :via => [:get, :post]
 
index f4496d98f3ef53d9758f47da751c6e03f4bbe83b..66764551de0f17787e4d92c42393086330e9abeb 100644 (file)
@@ -214,7 +214,7 @@ module Redmine
       end
 
       module Helper
-        def wikitoolbar_for(field_id)
+        def wikitoolbar_for(field_id, preview_url = preview_text_path)
         end
 
         def heads_for_wiki_formatter
index f41fee61c440a0eabd1cbd9852dddd53b9d22817..fac2f8bf3cd7cb7361b842e3edeb7cdec7b61184 100644 (file)
@@ -19,10 +19,10 @@ module Redmine
   module WikiFormatting
     module Markdown
       module Helper
-        def wikitoolbar_for(field_id)
+        def wikitoolbar_for(field_id, preview_url = preview_text_path)
           heads_for_wiki_formatter
           url = "#{Redmine::Utils.relative_url_root}/help/#{current_language.to_s.downcase}/wiki_syntax_markdown.html"
-          javascript_tag("var wikiToolbar = new jsToolBar(document.getElementById('#{field_id}')); wikiToolbar.setHelpLink('#{escape_javascript url}'); wikiToolbar.draw();")
+          javascript_tag("var wikiToolbar = new jsToolBar(document.getElementById('#{field_id}')); wikiToolbar.setHelpLink('#{escape_javascript url}'); wikiToolbar.setPreviewUrl('#{preview_url}'); wikiToolbar.draw();")
         end
 
         def initial_page_content(page)
index 92c7c880f7a24aae8aae334ee30117195ff49787..6e8ba9812e929bcf001964d842beface8bf07058 100644 (file)
@@ -19,11 +19,11 @@ module Redmine
   module WikiFormatting
     module Textile
       module Helper
-        def wikitoolbar_for(field_id)
+        def wikitoolbar_for(field_id, preview_url = preview_text_path)
           heads_for_wiki_formatter
           # Is there a simple way to link to a public resource?
           url = "#{Redmine::Utils.relative_url_root}/help/#{current_language.to_s.downcase}/wiki_syntax_textile.html"
-          javascript_tag("var wikiToolbar = new jsToolBar(document.getElementById('#{field_id}')); wikiToolbar.setHelpLink('#{escape_javascript url}'); wikiToolbar.draw();")
+          javascript_tag("var wikiToolbar = new jsToolBar(document.getElementById('#{field_id}')); wikiToolbar.setHelpLink('#{escape_javascript url}'); wikiToolbar.setPreviewUrl('#{preview_url}'); wikiToolbar.draw();")
         end
 
         def initial_page_content(page)
@@ -33,7 +33,8 @@ module Redmine
         def heads_for_wiki_formatter
           unless @heads_for_wiki_formatter_included
             content_for :header_tags do
-              javascript_include_tag('jstoolbar/jstoolbar-textile.min') +
+              javascript_include_tag('jstoolbar/jstoolbar') +
+              javascript_include_tag('jstoolbar/textile') +
               javascript_include_tag("jstoolbar/lang/jstoolbar-#{current_language.to_s.downcase}") +
               javascript_tag("var wikiImageMimeTypes = #{Redmine::MimeType.by_type('image').to_json};") +
               stylesheet_link_tag('jstoolbar')
index 0239e034349a9973782b00155f853f1fe1d5c4d1..dbe4a32b93a1133486f575fbd49225f8f209ac89 100644 (file)
@@ -449,17 +449,6 @@ function hideModal(el) {
   modal.dialog("close");
 }
 
-function submitPreview(url, form, target) {
-  $.ajax({
-    url: url,
-    type: 'post',
-    data: $('#'+form).serialize(),
-    success: function(data){
-      $('#'+target).html(data);
-    }
-  });
-}
-
 function collapseScmEntry(id) {
   $('.'+id).each(function() {
     if ($(this).hasClass('open')) {
@@ -846,6 +835,28 @@ $(document).ready(function(){
   toggleDisabledInit();
 });
 
+$(document).ready(function(){
+  $('#content').on('click', 'div.jstTabs a.tab-preview', function(event){
+    var tab = $(event.target);
+
+    var url = tab.data('url');
+    var form = tab.parents('form');
+    var jstBlock = tab.parents('.jstBlock');
+
+    var element = encodeURIComponent(jstBlock.find('.wiki-edit').val());
+    var attachments = form.find('.attachments_fields input').serialize();
+
+    $.ajax({
+      url: url,
+      type: 'post',
+      data: "text=" + element + '&' + attachments,
+      success: function(data){
+        jstBlock.find('.wiki-preview').html(data);
+      }
+    });
+  });
+});
+
 function keepAnchorOnSignIn(form){
   var hash = decodeURIComponent(self.document.location.hash);
   if (hash) {
index 1baafc0bdea14c14861be18e5f57f907c213044e..753855f91979d1a8312b943faec60b994094cab2 100644 (file)
@@ -237,8 +237,7 @@ function addInlineAttachmentMarkup(file) {
       'selectionStart': cursorPosition + newLineBefore,
       'selectionEnd': cursorPosition + inlineFilename.length + newLineBefore
     });
-    $textarea.closest('.jstEditor')
-      .siblings('.jstElements')
+    $textarea.parents('.jstBlock')
       .find('.jstb_img').click();
 
     // move cursor into next line
diff --git a/public/javascripts/jstoolbar/jstoolbar-textile.min.js b/public/javascripts/jstoolbar/jstoolbar-textile.min.js
deleted file mode 100644 (file)
index e087d1c..0000000
+++ /dev/null
@@ -1 +0,0 @@
-function jsToolBar(e){if(document.createElement&&e&&("undefined"!=typeof document.selection||"undefined"!=typeof e.setSelectionRange)){if(this.textarea=e,this.editor=document.createElement("div"),this.editor.className="jstEditor",this.textarea.parentNode.insertBefore(this.editor,this.textarea),this.editor.appendChild(this.textarea),this.toolbar=document.createElement("div"),this.toolbar.className="jstElements",this.editor.parentNode.insertBefore(this.toolbar,this.editor),this.editor.addEventListener&&navigator.appVersion.match(/\bMSIE\b/)){this.handle=document.createElement("div"),this.handle.className="jstHandle";var t=this.resizeDragStart,n=this;this.handle.addEventListener("mousedown",function(e){t.call(n,e)},!1),window.addEventListener("unload",function(){n.handle.parentNode.removeChild(n.handle);delete n.handle},!1),this.editor.parentNode.insertBefore(this.handle,this.editor.nextSibling)}this.context=null,this.toolNodes={}}}function jsButton(e,t,n,o){"undefined"==typeof jsToolBar.strings?this.title=e||null:this.title=jsToolBar.strings[e]||e||null,this.fn=t||function(){},this.scope=n||null,this.className=o||null}function jsSpace(e){this.id=e||null,this.width=null}function jsCombo(e,t,n,o,i){this.title=e||null,this.options=t||null,this.scope=n||null,this.fn=o||function(){},this.className=i||null}jsButton.prototype.draw=function(){if(!this.scope)return null;var e=document.createElement("button");e.setAttribute("type","button"),e.tabIndex=200,this.className&&(e.className=this.className),e.title=this.title;var t=document.createElement("span");if(t.appendChild(document.createTextNode(this.title)),e.appendChild(t),void 0!=this.icon&&(e.style.backgroundImage="url("+this.icon+")"),"function"==typeof this.fn){var n=this;e.onclick=function(){try{n.fn.apply(n.scope,arguments)}catch(e){}return!1}}return e},jsSpace.prototype.draw=function(){var e=document.createElement("span");return this.id&&(e.id=this.id),e.appendChild(document.createTextNode(String.fromCharCode(160))),e.className="jstSpacer",this.width&&(e.style.marginRight=this.width+"px"),e},jsCombo.prototype.draw=function(){if(!this.scope||!this.options)return null;var e=document.createElement("select");this.className&&(e.className=className),e.title=this.title;for(var t in this.options){var n=document.createElement("option");n.value=t,n.appendChild(document.createTextNode(this.options[t])),e.appendChild(n)}var o=this;return e.onchange=function(){try{o.fn.call(o.scope,this.value)}catch(e){alert(e)}return!1},e},jsToolBar.prototype={base_url:"",mode:"wiki",elements:{},help_link:"",getMode:function(){return this.mode},setMode:function(e){this.mode=e||"wiki"},switchMode:function(e){e=e||"wiki",this.draw(e)},setHelpLink:function(e){this.help_link=e},button:function(e){var t=this.elements[e];if("function"!=typeof t.fn[this.mode])return null;var n=new jsButton(t.title,t.fn[this.mode],this,"jstb_"+e);return void 0!=t.icon&&(n.icon=t.icon),n},space:function(e){var t=new jsSpace(e);return void 0!==this.elements[e].width&&(t.width=this.elements[e].width),t},combo:function(e){var t=this.elements[e],n=t[this.mode].list.length;if("function"!=typeof t[this.mode].fn||0==n)return null;for(var o={},i=0;n>i;i++){var s=t[this.mode].list[i];o[s]=t.options[s]}return new jsCombo(t.title,o,this,t[this.mode].fn)},draw:function(e){for(this.setMode(e);this.toolbar.hasChildNodes();)this.toolbar.removeChild(this.toolbar.firstChild);this.toolNodes={};var t,n,o;for(var i in this.elements){t=this.elements[i];var s=void 0==t.type||""==t.type||void 0!=t.disabled&&t.disabled||void 0!=t.context&&null!=t.context&&t.context!=this.context;s||"function"!=typeof this[t.type]||(n=this[t.type](i),n&&(o=n.draw()),o&&(this.toolNodes[i]=o,this.toolbar.appendChild(o)))}},singleTag:function(e,t){e=e||null,t=t||e,e&&t&&this.encloseSelection(e,t)},encloseLineSelection:function(e,t,n){this.textarea.focus(),e=e||"",t=t||"";var o,i,s,l,a,r;if("undefined"!=typeof document.selection?s=document.selection.createRange().text:"undefined"!=typeof this.textarea.setSelectionRange&&(o=this.textarea.selectionStart,i=this.textarea.selectionEnd,l=this.textarea.scrollTop,o=this.textarea.value.substring(0,o).replace(/[^\r\n]*$/g,"").length,i=this.textarea.value.length-this.textarea.value.substring(i,this.textarea.value.length).replace(/^[^\r\n]*/,"").length,s=this.textarea.value.substring(o,i)),s.match(/ $/)&&(s=s.substring(0,s.length-1),t+=" "),r="function"==typeof n?s?n.call(this,s):n(""):s?s:"",a=e+r+t,"undefined"!=typeof document.selection){document.selection.createRange().text=a;var c=this.textarea.createTextRange();c.collapse(!1),c.move("character",-t.length),c.select()}else"undefined"!=typeof this.textarea.setSelectionRange&&(this.textarea.value=this.textarea.value.substring(0,o)+a+this.textarea.value.substring(i),s?this.textarea.setSelectionRange(o+a.length,o+a.length):this.textarea.setSelectionRange(o+e.length,o+e.length),this.textarea.scrollTop=l)},encloseSelection:function(e,t,n){this.textarea.focus(),e=e||"",t=t||"";var o,i,s,l,a,r;if("undefined"!=typeof document.selection?s=document.selection.createRange().text:"undefined"!=typeof this.textarea.setSelectionRange&&(o=this.textarea.selectionStart,i=this.textarea.selectionEnd,l=this.textarea.scrollTop,s=this.textarea.value.substring(o,i),o>0&&this.textarea.value.substr(o-1, 1).match(/\S/)&&(e=" "+e),this.textarea.value.substr(i, 1).match(/\S/)&&(t=t+" ")),s.match(/ $/)&&(s=s.substring(0,s.length-1),t+=" "),r="function"==typeof n?s?n.call(this,s):n(""):s?s:"",a=e+r+t,"undefined"!=typeof document.selection){document.selection.createRange().text=a;var c=this.textarea.createTextRange();c.collapse(!1),c.move("character",-t.length),c.select()}else"undefined"!=typeof this.textarea.setSelectionRange&&(this.textarea.value=this.textarea.value.substring(0,o)+a+this.textarea.value.substring(i),s?this.textarea.setSelectionRange(o+a.length,o+a.length):this.textarea.setSelectionRange(o+e.length,o+e.length),this.textarea.scrollTop=l)},stripBaseURL:function(e){if(""!=this.base_url){var t=e.indexOf(this.base_url);0==t&&(e=e.substr(this.base_url.length))}return e}},jsToolBar.prototype.resizeSetStartH=function(){this.dragStartH=this.textarea.offsetHeight+0},jsToolBar.prototype.resizeDragStart=function(e){var t=this;this.dragStartY=e.clientY,this.resizeSetStartH(),document.addEventListener("mousemove",this.dragMoveHdlr=function(e){t.resizeDragMove(e)},!1),document.addEventListener("mouseup",this.dragStopHdlr=function(e){t.resizeDragStop(e)},!1)},jsToolBar.prototype.resizeDragMove=function(e){this.textarea.style.height=this.dragStartH+e.clientY-this.dragStartY+"px"},jsToolBar.prototype.resizeDragStop=function(e){document.removeEventListener("mousemove",this.dragMoveHdlr,!1),document.removeEventListener("mouseup",this.dragStopHdlr,!1)},jsToolBar.prototype.precodeMenu=function(e){for(var t=["c","clojure","cpp","css","delphi","diff","erb","go","groovy","haml","html","java","javascript","json","lua","php","python","ruby","sass","sql","taskpaper","text","xml","yaml"],n=$("<ul style='position:absolute;'></ul>"),o=0;o<t.length;o++)$("<li></li>").text(t[o]).appendTo(n).mousedown(function(){e($(this).text())});return $("body").append(n),n.menu().width(150).position({my:"left top",at:"left bottom",of:this.toolNodes.precode}),$(document).on("mousedown",function(){n.remove()}),!1},jsToolBar.prototype.elements.strong={type:"button",title:"Strong",fn:{wiki:function(){this.singleTag("*")}}},jsToolBar.prototype.elements.em={type:"button",title:"Italic",fn:{wiki:function(){this.singleTag("_")}}},jsToolBar.prototype.elements.ins={type:"button",title:"Underline",fn:{wiki:function(){this.singleTag("+")}}},jsToolBar.prototype.elements.del={type:"button",title:"Deleted",fn:{wiki:function(){this.singleTag("-")}}},jsToolBar.prototype.elements.code={type:"button",title:"Code",fn:{wiki:function(){this.singleTag("@")}}},jsToolBar.prototype.elements.space1={type:"space"},jsToolBar.prototype.elements.h1={type:"button",title:"Heading 1",fn:{wiki:function(){this.encloseLineSelection("h1. ","",function(e){return e=e.replace(/^h\d+\.\s+/,"")})}}},jsToolBar.prototype.elements.h2={type:"button",title:"Heading 2",fn:{wiki:function(){this.encloseLineSelection("h2. ","",function(e){return e=e.replace(/^h\d+\.\s+/,"")})}}},jsToolBar.prototype.elements.h3={type:"button",title:"Heading 3",fn:{wiki:function(){this.encloseLineSelection("h3. ","",function(e){return e=e.replace(/^h\d+\.\s+/,"")})}}},jsToolBar.prototype.elements.space2={type:"space"},jsToolBar.prototype.elements.ul={type:"button",title:"Unordered list",fn:{wiki:function(){this.encloseLineSelection("","",function(e){return e=e.replace(/\r/g,""),e.replace(/(\n|^)[#-]?\s*/g,"$1* ")})}}},jsToolBar.prototype.elements.ol={type:"button",title:"Ordered list",fn:{wiki:function(){this.encloseLineSelection("","",function(e){return e=e.replace(/\r/g,""),e.replace(/(\n|^)[*-]?\s*/g,"$1# ")})}}},jsToolBar.prototype.elements.space3={type:"space"},jsToolBar.prototype.elements.bq={type:"button",title:"Quote",fn:{wiki:function(){this.encloseLineSelection("","",function(e){return e=e.replace(/\r/g,""),e.replace(/(\n|^) *([^\n]*)/g,"$1> $2")})}}},jsToolBar.prototype.elements.unbq={type:"button",title:"Unquote",fn:{wiki:function(){this.encloseLineSelection("","",function(e){return e=e.replace(/\r/g,""),e.replace(/(\n|^) *[>]? *([^\n]*)/g,"$1$2")})}}},jsToolBar.prototype.elements.pre={type:"button",title:"Preformatted text",fn:{wiki:function(){this.encloseLineSelection("<pre>\n","\n</pre>")}}},jsToolBar.prototype.elements.precode={type:"button",title:"Highlighted code",fn:{wiki:function(){var e=this;this.precodeMenu(function(t){e.encloseLineSelection('<pre><code class="'+t+'">\n',"\n</code></pre>\n")})}}},jsToolBar.prototype.elements.space4={type:"space"},jsToolBar.prototype.elements.link={type:"button",title:"Wiki link",fn:{wiki:function(){this.encloseSelection("[[","]]")}}},jsToolBar.prototype.elements.img={type:"button",title:"Image",fn:{wiki:function(){this.encloseSelection("!","!")}}},jsToolBar.prototype.elements.space5={type:"space"},jsToolBar.prototype.elements.help={type:"button",title:"Help",fn:{wiki:function(){window.open(this.help_link,"","resizable=yes, location=no, width=300, height=640, menubar=no, status=no, scrollbars=yes")}}};
index bbda5f8b84f1029765c35b42eadb16e0d633189d..98dae6ff2b77638a5f9766e030a00c8855ad23b2 100644 (file)
@@ -7,12 +7,12 @@
  * it under the terms of the GNU General Public License as published by
  * the Free Software Foundation; either version 2 of the License, or
  * (at your option) any later version.
- * 
+ *
  * DotClear is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
- * 
+ *
  * You should have received a copy of the GNU General Public License
  * along with DotClear; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
@@ -34,15 +34,45 @@ function jsToolBar(textarea) {
 
   this.textarea = textarea;
 
+  this.toolbarBlock = document.createElement('div');
+  this.toolbarBlock.className = 'jstBlock';
+  this.textarea.parentNode.insertBefore(this.toolbarBlock, this.textarea);
+
   this.editor = document.createElement('div');
   this.editor.className = 'jstEditor';
 
-  this.textarea.parentNode.insertBefore(this.editor,this.textarea);
+  this.preview = document.createElement('div');
+  this.preview.className = 'wiki wiki-preview hidden';
+  this.preview.setAttribute('id', 'preview_' + textarea.getAttribute('id'));
+
   this.editor.appendChild(this.textarea);
+  this.editor.appendChild(this.preview);
+
+  this.tabsBlock = document.createElement('div');
+  this.tabsBlock.className = 'jstTabs tabs';
+
+  var This = this;
+  this.writeTab = new jsTab('Write', true);
+  this.writeTab.onclick = function(event) { This.hidePreview.call(This, event); return false; };
+
+  this.previewTab = new jsTab('Preview');
+  this.previewTab.onclick = function(event) { This.showPreview.call(This, event); return false; };
+
+  var elementsTab = document.createElement('li');
+  elementsTab.classList = 'tab-elements';
+
+  var tabs = document.createElement('ul');
+  tabs.appendChild(this.writeTab);
+  tabs.appendChild(this.previewTab);
+  tabs.appendChild(elementsTab);
+  this.tabsBlock.appendChild(tabs);
 
   this.toolbar = document.createElement("div");
   this.toolbar.className = 'jstElements';
-  this.editor.parentNode.insertBefore(this.toolbar,this.editor);
+  elementsTab.appendChild(this.toolbar);
+
+  this.toolbarBlock.appendChild(this.tabsBlock);
+  this.toolbarBlock.appendChild(this.editor);
 
   // Dragable resizing
   if (this.editor.addEventListener && navigator.appVersion.match(/\bMSIE\b/))
@@ -53,19 +83,40 @@ function jsToolBar(textarea) {
     var This = this;
     this.handle.addEventListener('mousedown',function(event) { dragStart.call(This,event); },false);
     // fix memory leak in Firefox (bug #241518)
-    window.addEventListener('unload',function() { 
+    window.addEventListener('unload',function() {
       var del = This.handle.parentNode.removeChild(This.handle);
       delete(This.handle);
     },false);
-    
+
     this.editor.parentNode.insertBefore(this.handle,this.editor.nextSibling);
   }
-  
+
   this.context = null;
-  this.toolNodes = {}; // lorsque la toolbar est dessinée , cet objet est garni 
+  this.toolNodes = {}; // lorsque la toolbar est dessinée , cet objet est garni
                        // de raccourcis vers les éléments DOM correspondants aux outils.
 }
 
+function jsTab(name, selected) {
+  selected = selected || false;
+  if(typeof jsToolBar.strings == 'undefined') {
+    var tabName = name || null;
+  } else {
+    var tabName = jsToolBar.strings[name] || name || null;
+  }
+
+  var tab = document.createElement('li');
+  var link = document.createElement('a');
+  link.setAttribute('href', '#');
+  link.innerText = tabName;
+  link.className = 'tab-' + name.toLowerCase();
+
+  if (selected == true) {
+    link.classList.add('selected');
+  }
+  tab.appendChild(link)
+
+  return tab;
+}
 function jsButton(title, fn, scope, className) {
   if(typeof jsToolBar.strings == 'undefined') {
     this.title = title || null;
@@ -91,6 +142,7 @@ jsButton.prototype.draw = function() {
   if (this.icon != undefined) {
     button.style.backgroundImage = 'url('+this.icon+')';
   }
+
   if (typeof(this.fn) == 'function') {
     var This = this;
     button.onclick = function() { try { This.fn.apply(This.scope, arguments) } catch (e) {} return false; };
@@ -110,7 +162,7 @@ jsSpace.prototype.draw = function() {
   if (this.width) span.style.marginRight = this.width+'px';
 
   return span;
-} 
+}
 
 function jsCombo(title, options, scope, fn, className) {
   this.title = title || null;
@@ -136,7 +188,7 @@ jsCombo.prototype.draw = function() {
 
   var This = this;
   select.onchange = function() {
-    try { 
+    try {
       This.fn.call(This.scope, this.value);
     } catch (e) { alert(e); }
 
@@ -152,7 +204,7 @@ jsToolBar.prototype = {
   mode: 'wiki',
   elements: {},
   help_link: '',
-  
+
   getMode: function() {
     return this.mode;
   },
@@ -170,6 +222,10 @@ jsToolBar.prototype = {
     this.help_link = link;
   },
 
+  setPreviewUrl: function(url) {
+    this.previewTab.firstChild.setAttribute('data-url', url);
+  },
+
   button: function(toolName) {
     var tool = this.elements[toolName];
     if (typeof tool.fn[this.mode] != 'function') return null;
@@ -292,7 +348,6 @@ jsToolBar.prototype = {
 
   encloseSelection: function(prefix, suffix, fn) {
     this.textarea.focus();
-
     prefix = prefix || '';
     suffix = suffix || '';
 
@@ -343,7 +398,24 @@ jsToolBar.prototype = {
       this.textarea.scrollTop = scrollPos;
     }
   },
+  showPreview: function(event) {
+    if (event.target.classList.contains('selected')) { return; }
+    this.preview.setAttribute('style', 'min-height: ' + this.textarea.clientHeight + 'px;')
+    this.toolbar.classList.add('hidden');
+    this.textarea.classList.add('hidden');
+    this.preview.classList.remove('hidden');
+    this.tabsBlock.getElementsByClassName('tab-write')[0].classList.remove('selected');
+    event.target.classList.add('selected');
 
+  },
+  hidePreview: function(event) {
+    if (event.target.classList.contains('selected')) { return; }
+    this.toolbar.classList.remove('hidden');
+    this.textarea.classList.remove('hidden');
+    this.preview.classList.add('hidden');
+    this.tabsBlock.getElementsByClassName('tab-preview')[0].classList.remove('selected');
+    event.target.classList.add('selected');
+  },
   stripBaseURL: function(url) {
     if (this.base_url != '') {
       var pos = url.indexOf(this.base_url);
index 4f72f087e0c33df00624856e95805dcd809e28de..c52e85508ccf8c81e102d46feff05326dcc328f6 100644 (file)
@@ -15,3 +15,5 @@ jsToolBar.strings['Unquote'] = 'Remove Quote';
 jsToolBar.strings['Preformatted text'] = 'Preformatted text';
 jsToolBar.strings['Wiki link'] = 'Link to a Wiki page';
 jsToolBar.strings['Image'] = 'Image';
+jsToolBar.strings['Write'] = 'Write';
+jsToolBar.strings['Preview'] = 'Preview';
\ No newline at end of file
index c680fac921553a7c050d806adde9547c83cb9e55..e98350679a5ba9f82670aac36421da602510e3ea 100644 (file)
@@ -274,7 +274,6 @@ tr.issue.idnt-8 td.subject {padding-left: 136px; background-position: 120px 50%;
 tr.issue.idnt-9 td.subject {padding-left: 152px; background-position: 136px 50%;}
 
 table.issue-report {table-layout:fixed;}
-table.issue-report th {white-space: normal;}
 
 tr.entry { border: 1px solid #f8f8f8; }
 tr.entry td { white-space: nowrap; }
@@ -678,7 +677,6 @@ span.pagination>span {white-space:nowrap;}
   min-height: 2em;
   clear:left;
 }
-
 html>body .tabular p {overflow:hidden;}
 
 .tabular input, .tabular select {max-width:95%}
@@ -730,11 +728,25 @@ label.no-css {
 input#time_entry_comments { width: 90%;}
 input#months { width: 30px; }
 
-fieldset.preview {margin-top: 1em; min-width: inherit; background: url(../images/draft.png)}
+.jstBlock .jstTabs, .jstBlock .wiki-preview { width: 99%; }
+
+.jstBlock .jstTabs { padding-right: 6px; }
+.jstBlock .wiki-preview { padding: 2px; }
+.jstBlock .wiki-preview p:first-child { padding-top: 0 !important;}
+.jstBlock .wiki-preview p:last-child { padding-bottom: 0 !important;}
+#content .box .jstBlock .jstTabs li { background-color: #f6f6f6; }
+
+.tabular .wiki-preview, .tabular .jstTabs {width: 95%;}
+.tabular.settings .wiki-preview, .tabular.settings .jstTabs { width: 99%; }
+.tabular .wiki-preview p {
+  min-height: initial;
+  padding: 1em 0 1em 0 !important;
+  overflow: initial;
+}
 
 .tabular.settings p{ padding-left: 300px; }
 .tabular.settings label{ margin-left: -300px; width: 295px; }
-.tabular.settings textarea { width: 99%; }
+.tabular.settings textarea, .tabular.settings .wiki-preview, .tabular.settings .jstTabs { width: 99%; }
 
 .settings.enabled_scm table {width:100%}
 .settings.enabled_scm td.scm_name{ font-weight: bold; }
index 4bf674556fca44b4b868a170c7c7b025dc5c2999..dc195b2799b454d105d365f5e9814f2859b75841 100644 (file)
@@ -1,19 +1,45 @@
+.jstBlock .hidden {
+    display: none;
+}
 .jstEditor {
     padding-left: 0px;
 }
 .jstEditor textarea, .jstEditor iframe {
     margin: 0;
 }
-
 .jstHandle {
     height: 10px;
     font-size: 0.1em;
     cursor: s-resize;
     /*background: transparent url(img/resizer.png) no-repeat 45% 50%;*/
 }
-
+#content .jstTabs.tabs {
+    margin-bottom: 10px;
+}
+#content .jstTabs.tabs li {
+    height: 42px;
+}
+#content .jstTabs.tabs li:before{
+    content: '';
+    display: inline-block;
+    vertical-align: middle;
+    height: 100%;
+}
+#content .jstTabs.tabs li a {
+    display: inline-block;
+    vertical-align: bottom;
+    line-height: 19px;
+}
 .jstElements {
-    padding: 3px 3px 3px 0;
+    display: inline-block;
+    vertical-align: bottom;
+    border-bottom: 1px solid #bbbbbb;
+    padding-left: 6px;
+    height: 26px;
+}
+.wiki-preview {
+    background-color: #ffffff;
+    border: 1px solid #bbbbbb;
 }
 
 .jstElements button {
index 353100a84fa15a6ca43bfbc1092180ca377e09a1..0f3d937db38bda1089dd40f4b69b4f00ab72791a 100644 (file)
@@ -33,7 +33,7 @@ class MessagesControllerTest < Redmine::ControllerTest
 
     assert_select 'h2', :text => 'First post'
   end
-  
+
   def test_show_should_contain_reply_field_tags_for_quoting
     @request.session[:user_id] = 2
     get :show, :params => {
@@ -214,7 +214,7 @@ class MessagesControllerTest < Redmine::ControllerTest
         :id => 1,
         :reply => {
           :content => 'This is a test reply',
-          :subject => 'Test reply' 
+          :subject => 'Test reply'
         }
       }
     reply = Message.order('id DESC').first
@@ -265,9 +265,9 @@ class MessagesControllerTest < Redmine::ControllerTest
     post :preview, :params => {
         :board_id => 1,
         :message => {
-          :subject => "",
-          :content => "Previewed text"
-        }
+          :subject => ""
+        },
+        :text => "Previewed text"
       }
     assert_response :success
     assert_include 'Previewed text', response.body
@@ -280,8 +280,8 @@ class MessagesControllerTest < Redmine::ControllerTest
         :board_id => 1,
         :message => {
           :subject => "",
-          :content => "Previewed text"
-        }
+        },
+        :text => "Previewed text"
       }
     assert_response :success
     assert_include 'Previewed text', response.body
index 65fb9ae77c8388d0901da02c82f6ca3c05644f25..5512cff2df94f9d7a9f2bec5a5ea5313047bd8b2 100644 (file)
@@ -28,62 +28,36 @@ class PreviewsControllerTest < Redmine::ControllerTest
            :journals, :journal_details,
            :news
 
-  def test_preview_new_issue
+  def test_preview_new_issue_description
     @request.session[:user_id] = 2
     post :issue, :params => {
         :project_id => '1',
-        :issue => {
-          :description => 'Foo'
-        }
+        :text => 'Foo'
       }
     assert_response :success
-    assert_select 'fieldset' do
-      assert_select 'legend', :text => 'Description'
-      assert_select 'p', :text => 'Foo'
-    end
+    assert_select 'p', :text => 'Foo'
   end
 
-  def test_preview_issue_notes_with_no_change_to_description
+  def test_preview_issue_description
     @request.session[:user_id] = 2
     post :issue, :params => {
         :project_id => '1',
-        :id => 1,
-        :issue => {
-          :description => Issue.find(1).description,
-          :notes => 'Foo'
-        }
+        :issue_id => 1,
+        :text => 'Unable to print recipes'
       }
     assert_response :success
-    assert_select 'legend', :text => 'Description', :count => 0
-    assert_select 'legend', :text => 'Notes'
-  end
 
-  def test_preview_issue_notes_with_change_to_description
-    @request.session[:user_id] = 2
-    post :issue, :params => {
-        :project_id => '1',
-        :id => 1,
-        :issue => {
-          :description => 'Changed description',
-          :notes => 'Foo'
-        }
-      }
-    assert_response :success
-    assert_select 'legend', :text => 'Description'
-    assert_select 'legend', :text => 'Notes'
+    assert_select 'p', :text => 'Unable to print recipes'
   end
 
-  def test_preview_journal_notes_for_update
+  def test_preview_issue_notes
     @request.session[:user_id] = 2
     post :issue, :params => {
         :project_id => '1',
         :id => 1,
-        :journal => {
-          :notes => 'Foo'
-        }
+        :text => 'Foo'
       }
     assert_response :success
-    assert_select 'legend', :text => 'Notes'
     assert_select 'p', :text => 'Foo'
   end
 
@@ -92,53 +66,30 @@ class PreviewsControllerTest < Redmine::ControllerTest
     @request.session[:user_id] = 2
     post :issue, :params => {
         :project_id => '1',
-        :id => 1,
-        :issue => {
-          :notes => 'attachment:foo.bar'
-        }
+        :issue_id => 1,
+        :field => 'notes',
+        :text => 'attachment:foo.bar'
       }
     assert_response :success
     assert_select 'a.attachment', :text => 'foo.bar'
   end
 
-  def test_preview_issue_with_project_changed
-    @request.session[:user_id] = 2
-    post :issue, :params => {
-        :project_id => '1',
-        :id => 1,
-        :issue => {
-          :notes => 'notes',
-          :project_id => 2
-        }
-      }
-    assert_response :success
-    assert_select 'legend', :text => 'Notes'
-  end
-
   def test_preview_new_news
     get :news, :params => {
         :project_id => 1,
-        :news => {
-          :title => '',
-          :description => 'News description',
-          :summary => ''
-        }
+        :text => 'News description',
       }
     assert_response :success
-    assert_select 'fieldset.preview', :text => /News description/
+    assert_select 'p', :text => /News description/
   end
 
   def test_preview_existing_news
     get :news, :params => {
         :project_id => 1,
         :id => 2,
-        :news => {
-          :title => '',
-          :description => 'News description',
-          :summary => ''
-        }
+        :text => 'News description'
       }
     assert_response :success
-    assert_select 'fieldset.preview', :text => /News description/
+    assert_select 'p', :text => /News description/
   end
 end
index 6fd58ed5ff283e66f16f576c24d9398bf3458e11..0b3bf186203b79b47076318e7340aaafc1cdf5f1 100644 (file)
@@ -77,8 +77,9 @@ class AttachmentsTest < Redmine::IntegrationTest
 
     token = ajax_upload('myupload.jpg', 'JPEG content')
 
-    post '/issues/preview/new/ecookbook', :params => {
-        :issue => {:tracker_id => 1, :description => 'Inline upload: !myupload.jpg!'},
+    post '/issues/preview', :params => {
+        :issue => {:tracker_id => 1, :project_id => 'ecookbook'},
+        :text => 'Inline upload: !myupload.jpg!',
         :attachments => {'1' => {:filename => 'myupload.jpg', :description => 'My uploaded file', :token => token}}
       }
     assert_response :success
index a5294325462cbf334bcb6f207351442e21cf37e7..08e7214ce34bdac0869f99c640fb17d137669ed3 100644 (file)
@@ -63,7 +63,7 @@ class LayoutTest < Redmine::IntegrationTest
     Role.anonymous.add_permission! :add_issues
 
     get '/projects/ecookbook/issues/new'
-    assert_select 'head script[src^=?]', '/javascripts/jstoolbar/jstoolbar-textile.min.js?'
+    assert_select 'head script[src^=?]', '/javascripts/jstoolbar/jstoolbar.js?'
   end
 
   def test_calendar_header_tags
index c6a78758daeb0687394e1fbc4352f89fc4ef57a4..c5b4eeaeea3057a22858ef319c1b0aa13495e84f 100644 (file)
@@ -19,14 +19,14 @@ require File.expand_path('../../../test_helper', __FILE__)
 
 class RoutingPreviewsTest < Redmine::RoutingTest
   def test_previews
-    should_route 'GET /issues/preview/new/foo' => 'previews#issue', :project_id => 'foo'
-    should_route 'PUT /issues/preview/new/foo' => 'previews#issue', :project_id => 'foo'
-    should_route 'POST /issues/preview/new/foo' => 'previews#issue', :project_id => 'foo'
-
-    should_route 'GET /issues/preview/edit/321' => 'previews#issue', :id => '321'
-    should_route 'PUT /issues/preview/edit/321' => 'previews#issue', :id => '321'
-    should_route 'POST /issues/preview/edit/321' => 'previews#issue', :id => '321'
+    should_route 'GET /issues/preview' => 'previews#issue'
+    should_route 'PUT /issues/preview' => 'previews#issue'
+    should_route 'POST /issues/preview' => 'previews#issue'
 
     should_route 'GET /news/preview' => 'previews#news'
+
+    should_route 'GET /preview/text' => 'previews#text'
+    should_route 'PUT /preview/text' => 'previews#text'
+    should_route 'POST /preview/text' => 'previews#text'
   end
 end
index 0ffc1c235ff4d84f64e68f80141f3fd6e15d4789..f4c52996d05e58ef712e582519a58ade26bb21be 100644 (file)
@@ -179,10 +179,10 @@ class IssuesTest < ApplicationSystemTestCase
       fill_in 'Subject', :with => 'new issue subject'
       fill_in 'Description', :with => 'new issue description'
       click_link 'Preview'
+      find 'div.wiki-preview', :visible => true, :text => 'new issue description'
     end
-    find 'div#preview fieldset', :visible => true, :text => 'new issue description'
     assert_difference 'Issue.count' do
-      find('input[name=commit]').click
+      click_button('Create')
     end
 
     issue = Issue.order('id desc').first
@@ -314,9 +314,9 @@ class IssuesTest < ApplicationSystemTestCase
     # Update the notes
     fill_in 'Notes', :with => 'Updated notes'
     # Preview the change
-    click_on 'Preview'
-    assert page.has_css?('#journal_2_preview')
-    assert page.first('#journal_2_preview').has_content?('Updated notes')
+    page.first('#change-2 a.tab-preview').click
+    assert page.has_css?('#preview_journal_2_notes')
+    assert page.first('#preview_journal_2_notes').has_content?('Updated notes')
     # Save
     click_on 'Save'