diff --git a/assets/javascripts/app/settings.coffee b/assets/javascripts/app/settings.coffee
index b33ef857..af65232e 100644
--- a/assets/javascripts/app/settings.coffee
+++ b/assets/javascripts/app/settings.coffee
@@ -2,6 +2,7 @@ class app.Settings
SETTINGS_KEY = 'settings'
DOCS_KEY = 'docs'
DARK_KEY = 'dark'
+ SIZE_KEY = 'size'
@defaults: ->
count: 0
@@ -59,8 +60,15 @@ class app.Settings
catch
return
+ setSize: (value) ->
+ try
+ Cookies.set SIZE_KEY, value, path: '/', expires: 1e8
+ catch
+ return
+
reset: ->
try Cookies.expire DOCS_KEY
try Cookies.expire DARK_KEY
+ try Cookies.expire SIZE_KEY
try @store.del(SETTINGS_KEY)
return
diff --git a/assets/javascripts/news.json b/assets/javascripts/news.json
index edfeff7e..c98f15a8 100644
--- a/assets/javascripts/news.json
+++ b/assets/javascripts/news.json
@@ -1,5 +1,8 @@
[
- [ "2015-02-15",
+ [ "2015-02-16",
+ "The sidebar is now resizable (drag & drop)."
+ ], [
+ "2015-02-15",
"New io.js, Symfony, Clojure, Lua and Yii 1.1 documentations"
], [
"2015-02-08",
diff --git a/assets/javascripts/views/layout/document.coffee b/assets/javascripts/views/layout/document.coffee
index c9c8a928..d4e95c8e 100644
--- a/assets/javascripts/views/layout/document.coffee
+++ b/assets/javascripts/views/layout/document.coffee
@@ -10,6 +10,7 @@ class app.views.Document extends app.View
init: ->
@addSubview @nav = new app.views.Nav,
@addSubview @sidebar = new app.views.Sidebar
+ @addSubview @resizer = new app.views.Resizer if app.views.Resizer.isSupported()
@addSubview @content = new app.views.Content
@addSubview @path = new app.views.Path unless app.isSingleDoc() or app.isMobile()
diff --git a/assets/javascripts/views/layout/resizer.coffee b/assets/javascripts/views/layout/resizer.coffee
new file mode 100644
index 00000000..e1d48c09
--- /dev/null
+++ b/assets/javascripts/views/layout/resizer.coffee
@@ -0,0 +1,46 @@
+class app.views.Resizer extends app.View
+ @className: '_resizer'
+
+ @events:
+ dragstart: 'onDragStart'
+ dragend: 'onDragEnd'
+ drag: 'onDrag'
+
+ @isSupported: ->
+ 'ondragstart' of document.createElement('div') and !app.isMobile()
+
+ init: ->
+ @el.setAttribute('draggable', 'true')
+ @appendTo $('._app')
+
+ @style = $('style[data-resizer]')
+ @size = @style.getAttribute('data-size')
+ return
+
+ MIN = 250
+ MAX = 600
+
+ resize: (newSize) ->
+ return unless newSize > 0
+ newSize = Math.min(Math.max(Math.round(newSize), MIN), MAX)
+ app.settings.setSize(newSize)
+ newSize = "#{newSize}px"
+ @style.innerHTML = @style.innerHTML.replace(new RegExp(@size, 'g'), newSize)
+ @size = newSize
+ return
+
+ onDragStart: (event) =>
+ @style.removeAttribute('disabled')
+ event.dataTransfer.effectAllowed = 'link'
+ event.dataTransfer.setData('text/plain', '')
+ return
+
+ onDrag: (event) =>
+ return if @lastDrag and @lastDrag > Date.now() - 50
+ @lastDrag = Date.now()
+ @resize event.clientX
+ return
+
+ onDragEnd: (event) =>
+ @resize event.screenX - window.screenX
+ return
diff --git a/assets/stylesheets/components/_sidebar.scss b/assets/stylesheets/components/_sidebar.scss
index 2e417f98..f70fd8c2 100644
--- a/assets/stylesheets/components/_sidebar.scss
+++ b/assets/stylesheets/components/_sidebar.scss
@@ -35,6 +35,17 @@
a:focus { outline: 0; }
}
+._resizer {
+ position: absolute;
+ z-index: $sidebarZ + 1;
+ top: $headerHeight;
+ bottom: 0;
+ left: $sidebarWidth;
+ margin-left: -2px;
+ width: 3px;
+ cursor: col-resize;
+}
+
//
// List
//
diff --git a/lib/app.rb b/lib/app.rb
index 0abe3600..9ee34441 100644
--- a/lib/app.rb
+++ b/lib/app.rb
@@ -136,6 +136,10 @@ class App < Sinatra::Application
dark: stylesheet_path('application-dark')
}
end
+
+ def size
+ @size ||= cookies[:size].nil? ? '18rem' : "#{cookies[:size]}px"
+ end
end
before do
diff --git a/test/app_test.rb b/test/app_test.rb
index d3a03e43..ce72d4ac 100644
--- a/test/app_test.rb
+++ b/test/app_test.rb
@@ -20,6 +20,17 @@ class AppTest < MiniTest::Spec
assert last_response.redirect?
assert_equal 'http://example.org/', last_response['Location']
end
+
+ it "sets default size" do
+ get '/'
+ assert_includes last_response.body, 'data-size="18rem"'
+ end
+
+ it "sets size from cookie" do
+ set_cookie('size=42')
+ get '/'
+ assert_includes last_response.body, 'data-size="42px"'
+ end
end
describe "/[static-page]" do
diff --git a/views/app.erb b/views/app.erb
index dd0a850a..6b7bd485 100644
--- a/views/app.erb
+++ b/views/app.erb
@@ -44,3 +44,9 @@
a.src="//secure.gaug.es/track.js";var b=document.getElementsByTagName("script")[0];
b.parentNode.insertBefore(a,b)}();
<% end %>
+