Commit c70ddf70 by tady

Merge branch 'wip/130416_wysiwyg' into 140420/update_tag_page

Conflicts:
	Gemfile.lock
parents c889b5a7 dbb3c8b8
...@@ -24,4 +24,4 @@ before_script: ...@@ -24,4 +24,4 @@ before_script:
- cp config/settings.yml.example config/settings.yml - cp config/settings.yml.example config/settings.yml
after_script: after_script:
- ruby script/travis/bundle_cache.rb - ruby script/travis/bundle_cache.rb
script: bundle exec rake db:create db:test:load spec script: bundle exec rake db:create db:test:load spec teaspoon
...@@ -50,6 +50,9 @@ gem 'mysql2' ...@@ -50,6 +50,9 @@ gem 'mysql2'
gem 'devise' gem 'devise'
# http://d.hatena.ne.jp/tkawa/20130812/p1
gem 'devise-better_routes'
gem 'omniauth-google-oauth2' gem 'omniauth-google-oauth2'
# Markdown # Markdown
...@@ -89,6 +92,9 @@ group :development, :test do ...@@ -89,6 +92,9 @@ group :development, :test do
# gem 'database_cleaner' # gem 'database_cleaner'
gem 'database_rewinder' gem 'database_rewinder'
gem 'teaspoon'
gem 'guard-teaspoon'
end end
group :test do group :test do
......
...@@ -10,39 +10,40 @@ GIT ...@@ -10,39 +10,40 @@ GIT
GEM GEM
remote: https://rubygems.org/ remote: https://rubygems.org/
specs: specs:
actionmailer (4.0.4) actionmailer (4.1.0)
actionpack (= 4.0.4) actionpack (= 4.1.0)
actionview (= 4.1.0)
mail (~> 2.5.4) mail (~> 2.5.4)
actionpack (4.0.4) actionpack (4.1.0)
activesupport (= 4.0.4) actionview (= 4.1.0)
builder (~> 3.1.0) activesupport (= 4.1.0)
erubis (~> 2.7.0)
rack (~> 1.5.2) rack (~> 1.5.2)
rack-test (~> 0.6.2) rack-test (~> 0.6.2)
activemodel (4.0.4) actionview (4.1.0)
activesupport (= 4.0.4) activesupport (= 4.1.0)
builder (~> 3.1.0) builder (~> 3.1)
activerecord (4.0.4) erubis (~> 2.7.0)
activemodel (= 4.0.4) activemodel (4.1.0)
activerecord-deprecated_finders (~> 1.0.2) activesupport (= 4.1.0)
activesupport (= 4.0.4) builder (~> 3.1)
arel (~> 4.0.0) activerecord (4.1.0)
activerecord-deprecated_finders (1.0.3) activemodel (= 4.1.0)
activesupport (4.0.4) activesupport (= 4.1.0)
arel (~> 5.0.0)
activesupport (4.1.0)
i18n (~> 0.6, >= 0.6.9) i18n (~> 0.6, >= 0.6.9)
minitest (~> 4.2) json (~> 1.7, >= 1.7.7)
multi_json (~> 1.3) minitest (~> 5.1)
thread_safe (~> 0.1) thread_safe (~> 0.1)
tzinfo (~> 0.3.37) tzinfo (~> 1.1)
addressable (2.3.6) addressable (2.3.6)
ancestry (2.0.0) ancestry (2.1.0)
activerecord (>= 3.0.0) activerecord (>= 3.0.0)
annotate (2.6.2) annotate (2.6.3)
activerecord (>= 2.3.0) activerecord (>= 2.3.0)
rake (>= 0.8.7) rake (>= 0.8.7)
arel (4.0.2) arel (5.0.1.20140414130214)
ast (1.1.0) ast (1.1.0)
atomic (1.1.16)
aws-sdk (1.38.0) aws-sdk (1.38.0)
json (~> 1.4) json (~> 1.4)
nokogiri (>= 1.4.4) nokogiri (>= 1.4.4)
...@@ -55,8 +56,8 @@ GEM ...@@ -55,8 +56,8 @@ GEM
debug_inspector (>= 0.0.1) debug_inspector (>= 0.0.1)
breadcrumble (4.0.0) breadcrumble (4.0.0)
rails (>= 4.0.0) rails (>= 4.0.0)
builder (3.1.4) builder (3.2.2)
capistrano (3.1.0) capistrano (3.2.0)
i18n i18n
rake (>= 10.0.0) rake (>= 10.0.0)
sshkit (~> 1.3) sshkit (~> 1.3)
...@@ -106,6 +107,9 @@ GEM ...@@ -106,6 +107,9 @@ GEM
railties (>= 3.2.6, < 5) railties (>= 3.2.6, < 5)
thread_safe (~> 0.1) thread_safe (~> 0.1)
warden (~> 1.2.3) warden (~> 1.2.3)
devise-better_routes (0.0.4)
devise (>= 3.0.0.rc)
rails (>= 4.0.0.rc1)
diff-lcs (1.2.5) diff-lcs (1.2.5)
docile (1.1.3) docile (1.1.3)
domain_name (0.5.18) domain_name (0.5.18)
...@@ -141,10 +145,13 @@ GEM ...@@ -141,10 +145,13 @@ GEM
guard-rspec (4.2.8) guard-rspec (4.2.8)
guard (~> 2.1) guard (~> 2.1)
rspec (>= 2.14, < 4.0) rspec (>= 2.14, < 4.0)
guard-rubocop (1.0.2) guard-rubocop (1.1.0)
guard (~> 2.0) guard (~> 2.0)
rubocop (~> 0.10) rubocop (~> 0.20)
hashie (2.0.5) guard-teaspoon (0.0.4)
guard (>= 1.6.1)
teaspoon (>= 0.5.3)
hashie (2.1.1)
hike (1.2.3) hike (1.2.3)
htmlentities (4.3.1) htmlentities (4.3.1)
http-cookie (1.0.2) http-cookie (1.0.2)
...@@ -153,9 +160,9 @@ GEM ...@@ -153,9 +160,9 @@ GEM
i18n_generators (1.2.1) i18n_generators (1.2.1)
mechanize mechanize
rails (>= 3.0.0) rails (>= 3.0.0)
jbuilder (2.0.5) jbuilder (2.0.6)
activesupport (>= 3.0.0) activesupport (>= 3.0.0, < 5)
multi_json (>= 1.2.0) multi_json (~> 1.2)
jquery-rails (3.1.0) jquery-rails (3.1.0)
railties (>= 3.0, < 5.0) railties (>= 3.0, < 5.0)
thor (>= 0.14, < 2.0) thor (>= 0.14, < 2.0)
...@@ -186,14 +193,14 @@ GEM ...@@ -186,14 +193,14 @@ GEM
method_source (0.8.2) method_source (0.8.2)
mime-types (1.25.1) mime-types (1.25.1)
mini_portile (0.5.3) mini_portile (0.5.3)
minitest (4.7.5) minitest (5.3.3)
multi_json (1.9.2) multi_json (1.9.2)
multi_xml (0.5.5) multi_xml (0.5.5)
multipart-post (2.0.0) multipart-post (2.0.0)
mysql2 (0.3.15) mysql2 (0.3.15)
net-http-digest_auth (1.4) net-http-digest_auth (1.4)
net-http-persistent (2.9.4) net-http-persistent (2.9.4)
net-scp (1.1.2) net-scp (1.2.0)
net-ssh (>= 2.6.5) net-ssh (>= 2.6.5)
net-ssh (2.8.0) net-ssh (2.8.0)
newrelic_rpm (3.7.3.204) newrelic_rpm (3.7.3.204)
...@@ -211,9 +218,9 @@ GEM ...@@ -211,9 +218,9 @@ GEM
omniauth (1.2.1) omniauth (1.2.1)
hashie (>= 1.2, < 3) hashie (>= 1.2, < 3)
rack (~> 1.0) rack (~> 1.0)
omniauth-google-oauth2 (0.2.2) omniauth-google-oauth2 (0.2.3)
omniauth (~> 1.0) omniauth (~> 1.0)
omniauth-oauth2 omniauth-oauth2 (~> 1.1)
omniauth-oauth2 (1.1.2) omniauth-oauth2 (1.1.2)
faraday (>= 0.8, < 0.10) faraday (>= 0.8, < 0.10)
multi_json (~> 1.3) multi_json (~> 1.3)
...@@ -223,7 +230,7 @@ GEM ...@@ -223,7 +230,7 @@ GEM
paper_trail (3.0.1) paper_trail (3.0.1)
activerecord (>= 3.0, < 5.0) activerecord (>= 3.0, < 5.0)
activesupport (>= 3.0, < 5.0) activesupport (>= 3.0, < 5.0)
parser (2.1.7) parser (2.1.8)
ast (~> 1.1) ast (~> 1.1)
slop (~> 3.4, >= 3.4.5) slop (~> 3.4, >= 3.4.5)
poltergeist (1.5.0) poltergeist (1.5.0)
...@@ -245,21 +252,23 @@ GEM ...@@ -245,21 +252,23 @@ GEM
rack (1.5.2) rack (1.5.2)
rack-test (0.6.2) rack-test (0.6.2)
rack (>= 1.0) rack (>= 1.0)
rails (4.0.4) rails (4.1.0)
actionmailer (= 4.0.4) actionmailer (= 4.1.0)
actionpack (= 4.0.4) actionpack (= 4.1.0)
activerecord (= 4.0.4) actionview (= 4.1.0)
activesupport (= 4.0.4) activemodel (= 4.1.0)
activerecord (= 4.1.0)
activesupport (= 4.1.0)
bundler (>= 1.3.0, < 2.0) bundler (>= 1.3.0, < 2.0)
railties (= 4.0.4) railties (= 4.1.0)
sprockets-rails (~> 2.0.0) sprockets-rails (~> 2.0)
railties (4.0.4) railties (4.1.0)
actionpack (= 4.0.4) actionpack (= 4.1.0)
activesupport (= 4.0.4) activesupport (= 4.1.0)
rake (>= 0.8.7) rake (>= 0.8.7)
thor (>= 0.18.1, < 2.0) thor (>= 0.18.1, < 2.0)
rainbow (2.0.0) rainbow (2.0.0)
rake (10.2.1) rake (10.3.1)
rb-fsevent (0.9.4) rb-fsevent (0.9.4)
rb-inotify (0.9.3) rb-inotify (0.9.3)
ffi (>= 0.5.0) ffi (>= 0.5.0)
...@@ -285,18 +294,19 @@ GEM ...@@ -285,18 +294,19 @@ GEM
rspec-core (~> 2.14.0) rspec-core (~> 2.14.0)
rspec-expectations (~> 2.14.0) rspec-expectations (~> 2.14.0)
rspec-mocks (~> 2.14.0) rspec-mocks (~> 2.14.0)
rubocop (0.19.1) rubocop (0.20.1)
json (>= 1.7.7, < 2) json (>= 1.7.7, < 2)
parser (~> 2.1.7) parser (~> 2.1.7)
powerpack (~> 0.0.6) powerpack (~> 0.0.6)
rainbow (>= 1.99.1, < 3.0) rainbow (>= 1.99.1, < 3.0)
ruby-progressbar (~> 1.4) ruby-progressbar (~> 1.4)
ruby-progressbar (1.4.2) ruby-progressbar (1.4.2)
sass (3.3.4) sass (3.2.19)
sass-rails (4.0.1) sass-rails (4.0.3)
railties (>= 4.0.0, < 5.0) railties (>= 4.0.0, < 5.0)
sass (>= 3.1.10) sass (~> 3.2.0)
sprockets-rails (~> 2.0.0) sprockets (~> 2.8, <= 2.11.0)
sprockets-rails (~> 2.0)
sdoc (0.4.0) sdoc (0.4.0)
json (~> 1.8) json (~> 1.8)
rdoc (~> 4.0, < 5.0) rdoc (~> 4.0, < 5.0)
...@@ -310,19 +320,21 @@ GEM ...@@ -310,19 +320,21 @@ GEM
temple (~> 0.6.6) temple (~> 0.6.6)
tilt (>= 1.3.3, < 2.1) tilt (>= 1.3.3, < 2.1)
slop (3.5.0) slop (3.5.0)
sprockets (2.12.0) sprockets (2.11.0)
hike (~> 1.2) hike (~> 1.2)
multi_json (~> 1.0) multi_json (~> 1.0)
rack (~> 1.0) rack (~> 1.0)
tilt (~> 1.1, != 1.3.0) tilt (~> 1.1, != 1.3.0)
sprockets-rails (2.0.1) sprockets-rails (2.1.3)
actionpack (>= 3.0) actionpack (>= 3.0)
activesupport (>= 3.0) activesupport (>= 3.0)
sprockets (~> 2.8) sprockets (~> 2.8)
sshkit (1.3.0) sshkit (1.4.0)
net-scp (>= 1.1.2) net-scp (>= 1.1.2)
net-ssh net-ssh (>= 2.8.0)
term-ansicolor term-ansicolor
teaspoon (0.8.0)
railties (>= 3.2.5, < 5)
temple (0.6.7) temple (0.6.7)
term-ansicolor (1.3.0) term-ansicolor (1.3.0)
tins (~> 1.0) tins (~> 1.0)
...@@ -334,22 +346,22 @@ GEM ...@@ -334,22 +346,22 @@ GEM
eventmachine (>= 1.0.0) eventmachine (>= 1.0.0)
rack (>= 1.0.0) rack (>= 1.0.0)
thor (0.19.1) thor (0.19.1)
thread_safe (0.3.1) thread_safe (0.3.3)
atomic (>= 1.1.7, < 2)
tilt (1.4.1) tilt (1.4.1)
timers (1.1.0) timers (1.1.0)
tins (1.0.1) tins (1.1.0)
treetop (1.4.15) treetop (1.4.15)
polyglot polyglot
polyglot (>= 0.3.1) polyglot (>= 0.3.1)
turnip (1.2.1) turnip (1.2.1)
gherkin (>= 2.5) gherkin (>= 2.5)
rspec (>= 2.0, < 4.0) rspec (>= 2.0, < 4.0)
tzinfo (0.3.39) tzinfo (1.1.0)
thread_safe (~> 0.1)
uglifier (2.5.0) uglifier (2.5.0)
execjs (>= 0.3.0) execjs (>= 0.3.0)
json (>= 1.8.0) json (>= 1.8.0)
unf (0.1.3) unf (0.1.4)
unf_ext unf_ext
unf_ext (0.0.6) unf_ext (0.0.6)
uuidtools (2.1.4) uuidtools (2.1.4)
...@@ -382,12 +394,14 @@ DEPENDENCIES ...@@ -382,12 +394,14 @@ DEPENDENCIES
coveralls coveralls
database_rewinder database_rewinder
devise devise
devise-better_routes
draper (~> 1.3) draper (~> 1.3)
factory_girl_rails factory_girl_rails
faraday faraday
github-markdown github-markdown
guard-rspec guard-rspec
guard-rubocop guard-rubocop
guard-teaspoon
i18n_generators i18n_generators
jbuilder jbuilder
jquery-rails jquery-rails
...@@ -408,6 +422,7 @@ DEPENDENCIES ...@@ -408,6 +422,7 @@ DEPENDENCIES
sdoc sdoc
settingslogic settingslogic
slim slim
teaspoon
therubyracer therubyracer
thin thin
turnip turnip
......
...@@ -16,3 +16,7 @@ guard :rspec do ...@@ -16,3 +16,7 @@ guard :rspec do
watch(%r{^spec/steps/(.+)_steps\.rb$}) { |m| Dir[File.join("**/#{m[1]}.feature")][0] || 'spec/acceptance' } watch(%r{^spec/steps/(.+)_steps\.rb$}) { |m| Dir[File.join("**/#{m[1]}.feature")][0] || 'spec/acceptance' }
end end
guard :teaspoon do
watch(%r{^app/assets/javascripts/(.+).js}) { |m| "spec/javascripts/#{m[1]}_spec.js.coffee" }
watch(%r{^spec/javascripts/(.*)})
end
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
...@@ -16,6 +16,7 @@ ...@@ -16,6 +16,7 @@
// require turbolinks // require turbolinks
//= require ./lib/jquery.ui.widget //= require ./lib/jquery.ui.widget
//= require_tree ./lib //= require_tree ./lib
//= require_tree ./modules
//= require_tree . //= require_tree .
_.mixin(_.string.exports()); _.mixin(_.string.exports());
......
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
# TODO:
# mod-mdEditorがページ内に複数あった場合の処理
@_mod_md_editor = {}
class @_mod_md_editor.TextareaText
constructor: (@text, @sel_start, @sel_end) ->
total_line_num: ->
99
current_line_num: ->
80
current_line_head_pos: ->
70
current_pos_in_line: ->
4
$.fn.extend
mod_mdEditor: (options) ->
settings =
# preview api url
end_point: ''
settings = $.extend settings, options
return @each () ->
$root = $(@)
$textarea = $root.find('.mod-mdEditor-textarea')
# textareのサイズ調整
$textarea.autosize();
# textareaのtabキー制御,indent維持
$textarea.on 'keydown', (e) ->
$this = $(@)
keyCode = e.keyCode || e.which
# tab key
if keyCode is 9
e.preventDefault()
start = $this.get(0).selectionStart
end = $this.get(0).selectionEnd
# set textarea value to: text before caret + tab + text after caret
$this.val($this.val().substring(0, start) +
'\t' +
$this.val().substring(end))
# put caret at right position again
$this.get(0).selectionStart =
$this.get(0).selectionEnd = start + 1
# enter key
else if keyCode is 13
e.preventDefault()
val = $this.val()
start = $this.get(0).selectionStart
bl = val.lastIndexOf("\n", start-1)
line = val.substring(bl, start)
lm = line.match(/^\s+/)
ns = if lm? then lm[0].length - 1 else 0
nv = val.substring(0, start) + "\n"
_(ns).times ->
nv += "\t"
$this.val(nv + val.substring(start))
$this.get(0).selectionStart =
$this.get(0).selectionEnd = start + ns + 1
# タグを選択可能に
$root.find('.mod-mdEditor-tags').select2 {
tags: window.RV.AllTags
}
# Previewを生成
generatePreview = ->
$.post(settings.end_point, {
'text': $textarea.val()
'authenticity_token': $("meta[name='csrf-token']").attr('content')
})
.done (data) ->
$root.find('.mod-mdEditor-preview').html(data)
# TODO
prettyPrint()
$textarea.on('keyup mouseup change', generatePreview)
generatePreview()
# textの行数をcount
count_line_number = (text) ->
matches = text.match(/\n/g)
if matches? then matches.length + 1 else 1
replace_regexp_meta = (str) ->
str.replace(/([\.\^\$\[\]\*\+\?\|\(\)])/g, "\\$1")
# 行の先頭に文字を挿入
md_head_insert_string = (insert_str) ->
textarea_text = $textarea.val()
sel_start_pos = $textarea.get(0).selectionStart
# sel_end_pos = $textarea.get(0).selectionEnd
# # textの全行数
# line_num = count_line_number(textarea_text)
# # 現在行の行数
# current_line_num = count_line_number(textarea_text.substr(0, sel_start_pos))
# 現在行の最初の文字の位置
current_line_head_pos = textarea_text.lastIndexOf("\n", sel_start_pos - 1) + 1
# 現在行のカーソル位置
current_pos_in_line = sel_start_pos - current_line_head_pos
# すでに挿入済みの場合は取り除く
insert_str_re = new RegExp('^' + replace_regexp_meta(insert_str), "g") # TODO ?
if textarea_text.substring(current_line_head_pos).match(insert_str_re)
$textarea.val([
textarea_text.substring(0, current_line_head_pos),
textarea_text.substring(current_line_head_pos).replace(insert_str_re, '')
].join(''))
else
$textarea.val([
textarea_text.substring(0, current_line_head_pos),
insert_str,
textarea_text.substring(current_line_head_pos)
].join(''))
# 選択文字を囲う
md_wrap_string = (wrap_str) ->
textarea_text = $textarea.val()
sel_start_pos = $textarea.get(0).selectionStart
sel_end_pos = $textarea.get(0).selectionEnd
# 文字が選択されていなければplaceholderを挿入
if sel_start_pos == sel_end_pos
placeholder_str = '<ここに文字>'
$textarea.val([
textarea_text.substring(0, sel_start_pos),
placeholder_str,
textarea_text.substring(sel_end_pos)
].join(''))
$textarea.get(0).selectionEnd = sel_end_pos + 2 + 2 * wrap_str.length + placeholder_str.length
# execute self.
md_wrap_string(wrap_str)
return
# すでに挿入済みの場合は取り除く
wrap_str_re = new RegExp('^ ' + replace_regexp_meta(wrap_str))
wrap_str_re_end = new RegExp(replace_regexp_meta(wrap_str) + ' $')
if textarea_text.substring(sel_start_pos, sel_end_pos).match(wrap_str_re)
$textarea.val([
textarea_text.substring(0, sel_start_pos),
textarea_text.substring(sel_start_pos, sel_end_pos).
replace(wrap_str_re, '').
replace(wrap_str_re_end, ''),
textarea_text.substring(sel_end_pos)
].join(''))
else
$textarea.val([
textarea_text.substring(0, sel_start_pos),
' ',
wrap_str,
textarea_text.substring(sel_start_pos, sel_end_pos),
wrap_str,
' ',
textarea_text.substring(sel_end_pos)
].join(''))
# カーソルの終了位置を移動
$textarea.get(0).selectionEnd = sel_end_pos + 2 + 2 * wrap_str.length
$textarea.get(0).selectionStart = sel_start_pos
# WYSIWYG
$root.find('.mod-mdEditor-btn-h1').on 'click', (e) ->
e.preventDefault()
md_head_insert_string('# ')
generatePreview()
$root.find('.mod-mdEditor-btn-h2').on 'click', (e) ->
e.preventDefault()
md_head_insert_string('## ')
generatePreview()
$root.find('.mod-mdEditor-btn-h3').on 'click', (e) ->
e.preventDefault()
md_head_insert_string('### ')
generatePreview()
$root.find('.mod-mdEditor-btn-ol').on 'click', (e) ->
e.preventDefault()
md_head_insert_string('1. ')
generatePreview()
$root.find('.mod-mdEditor-btn-ul').on 'click', (e) ->
e.preventDefault()
md_head_insert_string('- ')
generatePreview()
$root.find('.mod-mdEditor-btn-bold').on 'click', (e) ->
e.preventDefault()
md_wrap_string('**')
generatePreview()
$root.find('.mod-mdEditor-btn-italic').on 'click', (e) ->
e.preventDefault()
md_wrap_string('_')
generatePreview()
$root.find('.mod-mdEditor-btn-strikethrough').on 'click', (e) ->
e.preventDefault()
md_wrap_string('~~')
generatePreview()
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
# Place all the behaviors and hooks related to the matching controller here.
# All this logic will automatically be available in application.js.
# You can use CoffeeScript in this file: http://coffeescript.org/
// Place all the styles related to the apis controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
...@@ -10,6 +10,7 @@ ...@@ -10,6 +10,7 @@
* *
*= require normalize *= require normalize
*= require_tree ./lib *= require_tree ./lib
*= require_tree ./modules
*= require_tree . *= require_tree .
*= require_self *= require_self
*/ */
......
// Place all the styles related to the flow controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
/* Sample */ /* Sample */
/*
.dropdown-menu { .dropdown-menu {
border: 1px solid #ddd; border: 1px solid #ddd;
background-color: white; background-color: white;
...@@ -18,6 +20,7 @@ ...@@ -18,6 +20,7 @@
.dropdown-menu .active { .dropdown-menu .active {
background-color: rgb(110, 183, 219); background-color: rgb(110, 183, 219);
} }
*/
/* SHOULD not modify */ /* SHOULD not modify */
......
...@@ -13,7 +13,7 @@ ...@@ -13,7 +13,7 @@
// } // }
// } // }
.mod-mdEditor-body { .mod-mdEditor-textarea {
width: 100%; width: 100%;
min-height: 400px; min-height: 400px;
font-size: 9pt; font-size: 9pt;
......
.panel-body.panel-body-nopadding {
padding: 0;
}
.panel-body textarea {
border: none;
border-top: 1px dashed #999;
}
// Place all the styles related to the posts controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
// Place all the styles related to the search controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
// Place all the styles related to the stock controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
// Place all the styles related to the tags controller here.
// They will automatically be included in application.css.
// You can use Sass (SCSS) here: http://sass-lang.com/
class UsersController < ApplicationController class MeController < ApplicationController
before_action :set_user, only: [:edit, :update] before_action :set_user, only: [:edit, :update]
def edit def edit
...@@ -6,12 +6,12 @@ class UsersController < ApplicationController ...@@ -6,12 +6,12 @@ class UsersController < ApplicationController
def update def update
respond_to do |format| respond_to do |format|
if @user.update(user_params) if @me.update(user_params)
format.html { redirect_to edit_user_path, flash: { notice: 'Post was successfully updated.' } } format.html { redirect_to edit_me_path, flash: { notice: 'Post was successfully updated.' } }
format.json { head :no_content } format.json { head :no_content }
else else
format.html { render action: 'edit' } format.html { render action: 'edit' }
format.json { render json: @user.errors, status: :unprocessable_entity } format.json { render json: @me.errors, status: :unprocessable_entity }
end end
end end
end end
...@@ -20,7 +20,7 @@ class UsersController < ApplicationController ...@@ -20,7 +20,7 @@ class UsersController < ApplicationController
# Use callbacks to share common setup or constraints between actions. # Use callbacks to share common setup or constraints between actions.
def set_user def set_user
@user = current_user @me = current_user
end end
def user_params def user_params
......
...@@ -33,8 +33,7 @@ class PostsController < ApplicationController ...@@ -33,8 +33,7 @@ class PostsController < ApplicationController
# GET /posts/new # GET /posts/new
def new def new
@post = Post.new @post = Post.new(title: '新しい投稿')
@post.title = '新しい投稿'
end end
def fork def fork
......
...@@ -17,7 +17,7 @@ class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController ...@@ -17,7 +17,7 @@ class Users::OmniauthCallbacksController < Devise::OmniauthCallbacksController
sign_in_and_redirect @user, event: :authentication sign_in_and_redirect @user, event: :authentication
else else
session['devise.google_data'] = request.env['omniauth.auth'] session['devise.google_data'] = request.env['omniauth.auth']
redirect_to new_user_registration_url redirect_to edit_me_path
end end
end end
end end
...@@ -62,20 +62,15 @@ class User < ActiveRecord::Base ...@@ -62,20 +62,15 @@ class User < ActiveRecord::Base
# Device # Device
def self.find_for_google_oauth2(access_token, signed_in_resource = nil) def self.find_for_google_oauth2(access_token, signed_in_resource = nil)
info = access_token.info
user = User.where(email: info['email']).first user = self.where(email: access_token.info['email']).first_or_create do |_user|
_user.name = access_token.info['name']
unless user _user.image_url = access_token.info['image']
new_nickname = (("a".."z").to_a + ("A".."Z").to_a + (0..9).to_a).shuffle[0..4].join _user.password = Devise.friendly_token[0, 20]
user = User.create(name: info['name'], _user.nickname = (("a".."z").to_a + ("A".."Z").to_a + (0..9).to_a).shuffle[0..4].join
image_url: info['image'],
email: info['email'],
password: Devise.friendly_token[0, 20],
nickname: new_nickname
)
end end
user.update_attributes( user.update(
google_auth_token: access_token.credentials['token'], google_auth_token: access_token.credentials['token'],
google_refresh_token: access_token.credentials['refresh_token'], google_refresh_token: access_token.credentials['refresh_token'],
google_token_expires_at: Time.at(access_token.credentials['expires_at']) google_token_expires_at: Time.at(access_token.credentials['expires_at'])
......
...@@ -8,6 +8,7 @@ html lang="ja" ...@@ -8,6 +8,7 @@ html lang="ja"
link href="//netdna.bootstrapcdn.com/bootstrap/3.0.2/css/bootstrap-theme.min.css" rel="stylesheet" / link href="//netdna.bootstrapcdn.com/bootstrap/3.0.2/css/bootstrap-theme.min.css" rel="stylesheet" /
link href="//cdnjs.cloudflare.com/ajax/libs/fullcalendar/1.6.4/fullcalendar.css" rel="stylesheet" / link href="//cdnjs.cloudflare.com/ajax/libs/fullcalendar/1.6.4/fullcalendar.css" rel="stylesheet" /
link href="//cdnjs.cloudflare.com/ajax/libs/fullcalendar/1.6.4/fullcalendar.print.css" rel="stylesheet" / link href="//cdnjs.cloudflare.com/ajax/libs/fullcalendar/1.6.4/fullcalendar.print.css" rel="stylesheet" /
link href="//netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.css" rel="stylesheet"
= stylesheet_link_tag "application", media: "all" = stylesheet_link_tag "application", media: "all"
= render_style = render_style
= csrf_meta_tags = csrf_meta_tags
......
#post-form #post-form
= form_for(@user) do |f| = form_for(@me, url: me_path) do |f|
- if @user.errors.any? - if @me.errors.any?
#error_explanation #error_explanation
h2 h2
= pluralize(@user.errors.count, "error") = pluralize(@me.errors.count, "error")
| prohibited this post from being saved: | prohibited this post from being saved:
ul ul
- @user.errors.full_messages.each do |msg| - @me.errors.full_messages.each do |msg|
li= msg li= msg
.row .row
......
...@@ -37,9 +37,9 @@ nav.navbar.navbar-default.navbar-fixed-top role="navigation" ...@@ -37,9 +37,9 @@ nav.navbar.navbar-default.navbar-fixed-top role="navigation"
| 下書き | 下書き
span.badge.pull-right = current_user.decorate.draft_count span.badge.pull-right = current_user.decorate.draft_count
li li
a href=edit_user_path(current_user) マイページ a href=edit_me_path マイページ
li.divider li.divider
li li
a href=sign_out_path data-method="delete" rel="nofollow" SignOut a href=me_session_path data-method="delete" rel="nofollow" SignOut
#post-form #post-form
= form_for(@post) do |f| = form_for(@post, role: 'form') do |f|
- if @post.errors.any? - if @post.errors.any?
#error_explanation #error_explanation
h2 h2
...@@ -8,6 +8,7 @@ ...@@ -8,6 +8,7 @@
ul ul
- @post.errors.full_messages.each do |msg| - @post.errors.full_messages.each do |msg|
li= msg li= msg
.row .row
.col-xs-9 .col-xs-9
.field .field
...@@ -30,11 +31,35 @@ ...@@ -30,11 +31,35 @@
= f.date_select :specified_date = f.date_select :specified_date
br/ br/
.row .row
.col-xs-6.col-md-6 .col-xs-6
.field .panel.panel-default
= f.text_area :body, class: 'mod-mdEditor-body' .panel-heading
.col-xs-12.col-sm-6.col-md-6 .btn-toolbar role="toolbar"
.btn-group.btn-group-xs
button.btn.btn-default.mod-mdEditor-btn-h1 type="button" title="Header level 1" H1
button.btn.btn-default.mod-mdEditor-btn-h2 type="button" title="Header level 2" H2
button.btn.btn-default.mod-mdEditor-btn-h3 type="button" title="Header level 3" H3
.btn-group.btn-group-xs
button.btn.btn-default.mod-mdEditor-btn-bold type="button" title="Text bold"
i.fa.fa-bold
button.btn.btn-default.mod-mdEditor-btn-italic type="button" title="Text itelic"
i.fa.fa-italic
.btn-group.btn-group-xs
button.btn.btn-default.mod-mdEditor-btn-ol type="button" title="順序リスト"
i.fa.fa-list-ol
button.btn.btn-default.mod-mdEditor-btn-ul type="button" title="リスト"
i.fa.fa-list-ul
button.btn.btn-default.mod-mdEditor-btn-strikethrough type="button" title="打ち消し線"
i.fa.fa-strikethrough
/ button.btn.btn-default.mod-mdEditor-btn-link type="button"
/ i.fa.fa-link
.panel-body.panel-body-nopadding
= f.text_area :body, class: 'mod-mdEditor-textarea'
.col-xs-6
.box-text .box-text
.text-box.body.viewer.github.mod-mdEditor-preview .text-box.body.viewer.github.mod-mdEditor-preview
...@@ -42,13 +67,13 @@ input#fileupload data-url="/apis/file_receiver" multiple="" name="files[]" style ...@@ -42,13 +67,13 @@ input#fileupload data-url="/apis/file_receiver" multiple="" name="files[]" style
- content_for :footer_js do - content_for :footer_js do
javascript: javascript:
$.setConfirmUnload(); // $.setConfirmUnload();
$('#post-form').mod_mdEditor({end_point: '/apis/markdown_preview'}); $('#post-form').mod_mdEditor({end_point: '/apis/markdown_preview'});
$.mod_fileuploader({ $.mod_fileuploader({
$input: $('#fileupload'), $input: $('#fileupload'),
$textarea: $('.mod-mdEditor-body') $textarea: $('.mod-mdEditor-textarea')
}); });
// 下書き保存 // 下書き保存
......
...@@ -25,7 +25,7 @@ a.list-group-item.post-list.mod-hover-hidden data-post-id=post.id href=post_path ...@@ -25,7 +25,7 @@ a.list-group-item.post-list.mod-hover-hidden data-post-id=post.id href=post_path
span.mod-hover-hidden-item span.mod-hover-hidden-item
| 読了時間 | 読了時間
| &nbsp;#{post.read_time}&nbsp;&nbsp; | &nbsp;#{post.read_time}&nbsp;&nbsp;
span.glyphicon.glyphicon-edit span.glyphicon.glyphicon-comment
span.mod-hover-hidden-item span.mod-hover-hidden-item
| コメント | コメント
| &nbsp;#{post.comments.count}&nbsp;&nbsp; | &nbsp;#{post.comments.count}&nbsp;&nbsp;
......
...@@ -22,7 +22,7 @@ ...@@ -22,7 +22,7 @@
.col-xs-6.col-md-6 .col-xs-6.col-md-6
.field .field
/! <haml:loud> f.label :body </haml:loud><br /! <haml:loud> f.label :body </haml:loud><br
= f.text_area :body, class: 'mod-mdEditor-body' = f.text_area :body, class: 'mod-mdEditor-textarea'
/! /span /! /span
.col-xs-12.col-sm-6.col-md-6 .col-xs-12.col-sm-6.col-md-6
.box-text .box-text
......
Teaspoon.setup do |config|
# This determines where the Teaspoon routes will be mounted. Changing this to "/jasmine" would allow you to browse to
# http://localhost:3000/jasmine to run your specs.
config.mount_at = "/teaspoon"
# This defaults to Rails.root if left nil. If you're testing an engine using a dummy application it can be useful to
# set this to your engines root.. E.g. `Teaspoon::Engine.root`
config.root = nil
# These paths are appended to the Rails assets paths (relative to config.root), and by default is an array that you
# can replace or add to.
config.asset_paths = ["spec/javascripts", "spec/javascripts/stylesheets"]
# Fixtures are rendered through a standard controller. This means you can use things like HAML or RABL/JBuilder, etc.
# to generate fixtures within this path.
config.fixture_path = "spec/javascripts/fixtures"
# You can modify the default suite configuration and create new suites here. Suites can be isolated from one another.
# When defining a suite you can provide a name and a block. If the name is left blank, :default is assumed. You can
# omit various directives and the defaults will be used.
#
# To run a specific suite
# - in the browser: http://localhost/teaspoon/[suite_name]
# - from the command line: rake teaspoon suite=[suite_name]
config.suite do |suite|
# You can specify a file matcher and all matching files will be loaded when the suite is run. It's important that
# these files are serve-able from sprockets.
#
# Note: Can also be set to nil.
suite.matcher = "{spec/javascripts,app/assets}/**/*_spec.{js,js.coffee,coffee}"
# Each suite can load a different helper, which can in turn require additional files. This file is loaded before
# your specs are loaded, and can be used as a manifest.
suite.helper = "spec_helper"
# These are the core Teaspoon javascripts. It's strongly encouraged to include only the base files here. You can
# require other support libraries in your spec helper, which allows you to change them without having to restart the
# server.
#
# Available frameworks: teaspoon-jasmine, teaspoon-mocha, teaspoon-qunit
#
# Note: To use the CoffeeScript source files use `"teaspoon/jasmine"` etc.
suite.javascripts = ["teaspoon-jasmine"]
# If you want to change how Teaspoon looks, or include your own stylesheets you can do that here. The default is the
# stylesheet for the HTML reporter.
suite.stylesheets = ["teaspoon"]
# When running coverage reports, you probably want to exclude libraries that you're not testing.
# Accepts an array of filenames or regular expressions. The default is to exclude assets from vendors or gems.
suite.no_coverage = [%r{/lib/ruby/gems/}, %r{/vendor/assets/}, %r{/support/}, %r{/(.+)_helper.}]
# suite.no_coverage << "jquery.min.js" # excludes jquery from coverage reports
end
# Example suite. Since we're just filtering to files already within the root spec/javascripts, these files will also
# be run in the default suite -- but can be focused into a more specific suite.
#config.suite :targeted do |suite|
# suite.matcher = "spec/javascripts/targeted/*_spec.{js,js.coffee,coffee}"
#end
end if defined?(Teaspoon) && Teaspoon.respond_to?(:setup) # let Teaspoon be undefined outside of development/test/asset groups
...@@ -21,15 +21,22 @@ Rendezvous::Application.routes.draw do ...@@ -21,15 +21,22 @@ Rendezvous::Application.routes.draw do
post 'tags/:name/move_to/:move_to_name' => 'tags#move_to', as: 'move_to_tag' post 'tags/:name/move_to/:move_to_name' => 'tags#move_to', as: 'move_to_tag'
resources :tags, :param => :name resources :tags, :param => :name
resource :user, :only => [:edit, :update] # resource :user, :only => [:edit, :update]
# devise_for :users , controllers: { omniauth_callbacks: 'users/omniauth_callbacks' } # devise_for :users , controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }
# devise_for :users , only: [:sign_in, :sign_out, :session] # devise_for :users , only: [:sign_in, :sign_out, :session]
devise_for :users, controllers: { omniauth_callbacks: 'users/omniauth_callbacks' }, skip: [:sessions]
devise_scope :user do devise_for :users,
# get 'sign_in', to: 'users/sessions#new', as: :new_user_session path_names: {current_user: 'me'},
delete 'sign_out', to: 'devise/sessions#destroy', as: :sign_out controllers: { omniauth_callbacks: 'users/omniauth_callbacks' },
end skip: [:passwords]
# , controllers: { omniauth_callbacks: 'users/omniauth_callbacks' } # , skip: [:sessions]
# devise_scope :user do
# get 'sign_in', to: 'users/sessions#new', as: :new_user_session
# delete 'sign_out', to: 'devise/sessions#destroy', as: :sign_out
# end
# get 'users/edit' => 'users#edit', as: 'edit_user' # get 'users/edit' => 'users#edit', as: 'edit_user'
# post 'users/update' => 'users#update', as: 'update_user' # post 'users/update' => 'users#update', as: 'update_user'
......
#= require modules/mod-md-editor
describe "mod-md-editor", ->
text = new _mod_md_editor.TextareaText("aaaaaaaa\nbbbbbb\n\ncccccc", 10, 18)
it "_mod_md_editor.parse", ->
expect(text.total_line_num()).toBe(4)
expect(text.current_line_num()).toBe()
expect(text.current_line_head_pos()).toBe(4)
expect(text.current_pos_in_line()).toBe(4)
// Teaspoon includes some support files, but you can use anything from your own support path too.
// require support/jasmine-jquery
// require support/sinon
// require support/your-support-file
//
// PhantomJS (Teaspoons default driver) doesn't have support for Function.prototype.bind, which has caused confusion. Use
// this polyfill to avoid the confusion.
//= require support/bind-poly
//
// Deferring execution
// If you're using CommonJS, RequireJS or some other asynchronous library you can defer execution. Call Teaspoon.execute()
// after everything has been loaded. Simple example of a timeout:
//
// Teaspoon.defer = true
// setTimeout(Teaspoon.execute, 1000)
//
// Matching files
// By default Teaspoon will look for files that match _spec.{js,js.coffee,.coffee}. Add a filename_spec.js file in your
// spec path and it'll be included in the default suite automatically. If you want to customize suites, check out the
// configuration in config/initializers/teaspoon.rb
//
// Manifest
// If you'd rather require your spec files manually (to control order for instance) you can disable the suite matcher in
// the configuration and use this file as a manifest.
//
// For more information: http://github.com/modeset/teaspoon
//
// You can require javascript files here. A good place to start is by requiring your application.js.
//= require application
# This file allows you to override various Teaspoon configuration directives when running from the command line. It is not
# required from within the Rails environment, so overriding directives that have been defined within the initializer
# is not possible.
#
# Set RAILS_ROOT and load the environment.
ENV["RAILS_ROOT"] = File.expand_path("../../", __FILE__)
require File.expand_path("../../config/environment", __FILE__)
# Provide default configuration.
#
# You can override various configuration directives defined here by using arguments with the teaspoon command.
#
# teaspoon --driver=selenium --suppress-log
# rake teaspoon DRIVER=selenium SUPPRESS_LOG=false
Teaspoon.setup do |config|
# Driver / Server
config.driver = "phantomjs" # available: phantomjs, selenium
#config.server = nil # defaults to Rack::Server
# Behaviors
#config.server_timeout = 20 # timeout for starting the server
#config.server_port = nil # defaults to any open port unless specified
#config.fail_fast = true # abort after the first failing suite
# Output
#config.formatters = "dot" # available: dot, tap, tap_y, swayze_or_oprah
#config.suppress_log = false # suppress logs coming from console[log/error/debug]
#config.color = true
# Coverage (requires istanbul -- https://github.com/gotwarlost/istanbul)
#config.coverage = true
#config.coverage_reports = "text,html,cobertura"
#config.coverage_output_dir = "coverage"
#config.statements_coverage_threshold = 50
#config.functions_coverage_threshold = 50
#config.branches_coverage_threshold = 50
#config.lines_coverage_threshold = 50
end
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment