-
Stop showing this message
+
Stop showing this message
Welcome!
DevDocs combines multiple API documentations in a fast, organized, and searchable interface.
Here's what you should know before you start:
diff --git a/assets/javascripts/templates/sidebar_tmpl.coffee b/assets/javascripts/templates/sidebar_tmpl.coffee
index 09c4daea..635880c5 100644
--- a/assets/javascripts/templates/sidebar_tmpl.coffee
+++ b/assets/javascripts/templates/sidebar_tmpl.coffee
@@ -3,7 +3,7 @@ templates = app.templates
templates.sidebarDoc = (doc, options = {}) ->
link = """"""
+ link += """" data-slug="#{doc.slug}" title="#{doc.fullName}" tabindex="-1">"""
if options.disabled
link += """Enable"""
else
@@ -14,10 +14,10 @@ templates.sidebarDoc = (doc, options = {}) ->
link + ""
templates.sidebarType = (type) ->
- """#{type.count}#{type.name}"""
+ """#{type.count}#{type.name}"""
templates.sidebarEntry = (entry) ->
- """#{$.escape entry.name}"""
+ """#{$.escape entry.name}"""
templates.sidebarResult = (entry) ->
addons = if entry.isIndex() and app.disabledDocs.contains(entry.doc)
@@ -25,17 +25,17 @@ templates.sidebarResult = (entry) ->
else
""""""
addons += """#{entry.doc.short_version}""" if entry.doc.version and not entry.isIndex()
- """#{addons}#{$.escape entry.name}"""
+ """#{addons}#{$.escape entry.name}"""
templates.sidebarNoResults = ->
html = """
No results.
"""
html += """
-
Note: documentations must be
enabled to appear in the search.
+
Note: documentations must be
enabled to appear in the search.
""" unless app.isSingleDoc() or app.disabledDocs.isEmpty()
html
templates.sidebarPageLink = (count) ->
- """
Show more\u2026 (#{count})"""
+ """
Show more\u2026 (#{count})"""
templates.sidebarLabel = (doc, options = {}) ->
label = """
#{versions}
"""
templates.sidebarDisabled = (options) ->
"""
Disabled (#{options.count})
"""
@@ -56,7 +56,7 @@ templates.sidebarDisabledList = (html) ->
"""
#{html}
"""
templates.sidebarDisabledVersionedDoc = (doc, versions) ->
- """
#{doc.name}#{versions}
"""
+ """
#{doc.name}#{versions}
"""
templates.sidebarPickerNote = """
Tip: for faster and better search results, select only the docs you need.
@@ -67,9 +67,9 @@ sidebarFooter = (html) -> """"""
templates.sidebarSettings = ->
sidebarFooter """
+
-
"""
templates.sidebarSave = ->
diff --git a/assets/javascripts/views/layout/nav.coffee b/assets/javascripts/views/layout/nav.coffee
index 3a227561..f76523b3 100644
--- a/assets/javascripts/views/layout/nav.coffee
+++ b/assets/javascripts/views/layout/nav.coffee
@@ -9,11 +9,13 @@ class app.views.Nav extends app.View
@deselect()
if @current = @find "a[href='#{href}']"
@current.classList.add @constructor.activeClass
+ @current.setAttribute 'tabindex', '-1'
return
deselect: ->
if @current
@current.classList.remove @constructor.activeClass
+ @current.removeAttribute 'tabindex'
@current = null
return
diff --git a/assets/javascripts/views/search/search_scope.coffee b/assets/javascripts/views/search/search_scope.coffee
index 14274010..8337c136 100644
--- a/assets/javascripts/views/search/search_scope.coffee
+++ b/assets/javascripts/views/search/search_scope.coffee
@@ -84,10 +84,11 @@ class app.views.SearchScope extends app.View
if @doc and not @input.value
$.stopEvent(event)
@reset()
- else if event.which is 9 or # tab
- event.which is 32 and (app.isMobile() or $.isTouchScreen()) # space
- $.stopEvent(event)
- @search @input.value[0...@input.selectionStart]
+ else if not @doc and @input.value
+ if event.which is 9 or # tab
+ event.which is 32 and (app.isMobile() or $.isTouchScreen()) # space
+ @search @input.value[0...@input.selectionStart]
+ $.stopEvent(event) if @doc
return
extractHashValue: ->
diff --git a/assets/javascripts/views/sidebar/doc_picker.coffee b/assets/javascripts/views/sidebar/doc_picker.coffee
index 6ed17ce2..99a2dbc0 100644
--- a/assets/javascripts/views/sidebar/doc_picker.coffee
+++ b/assets/javascripts/views/sidebar/doc_picker.coffee
@@ -21,14 +21,14 @@ class app.views.DocPicker extends app.View
@render()
@findByTag('input')?.focus()
app.appCache?.on 'progress', @onAppCacheProgress
- $.on @el, 'focus', @onFocus, true
+ $.on @el, 'focus', @onDOMFocus, true
return
deactivate: ->
if super
@empty()
app.appCache?.off 'progress', @onAppCacheProgress
- $.off @el, 'focus', @onFocus, true
+ $.off @el, 'focus', @onDOMFocus, true
return
render: ->
@@ -84,14 +84,27 @@ class app.views.DocPicker extends app.View
input.name
onClick: (event) =>
+ if @focusTimeout
+ clearTimeout @focusTimeout
+ @focusTimeout = null
return if event.which isnt 1
if event.target is @saveLink
$.stopEvent(event)
@save()
return
- onFocus: (event) ->
- $.scrollTo event.target.parentNode, null, 'continuous', bottomGap: 2
+ onDOMFocus: (event) =>
+ target = event.target
+ if target.tagName is 'INPUT'
+ $.scrollTo target.parentNode, null, 'continuous', bottomGap: 2
+ else if target.classList.contains(app.views.ListFold.targetClass)
+ target.blur()
+ @focusTimeout = setTimeout =>
+ @listFold.open(target) unless target.classList.contains(app.views.ListFold.activeClass)
+ $('input', target.nextElementSibling).focus()
+ @focusTimeout = null
+ , 10
+ return
onEnter: =>
@save()
diff --git a/assets/javascripts/views/sidebar/sidebar.coffee b/assets/javascripts/views/sidebar/sidebar.coffee
index 94dcb967..654351bb 100644
--- a/assets/javascripts/views/sidebar/sidebar.coffee
+++ b/assets/javascripts/views/sidebar/sidebar.coffee
@@ -101,9 +101,11 @@ class app.views.Sidebar extends app.View
@reset()
else if event.target.hasAttribute? 'data-light'
$.stopEvent(event)
+ document.activeElement?.blur()
app.document.toggleLight()
else if event.target.hasAttribute? 'data-layout'
$.stopEvent(event)
+ document.activeElement?.blur()
app.document.toggleLayout()
return
diff --git a/assets/stylesheets/components/_header.scss b/assets/stylesheets/components/_header.scss
index 4031d56f..a16d082e 100644
--- a/assets/stylesheets/components/_header.scss
+++ b/assets/stylesheets/components/_header.scss
@@ -13,8 +13,6 @@
background: $headerBackground;
border-bottom: 1px solid $headerBorder;
@extend %user-select-none;
-
- a:focus { outline: 0; }
}
//
@@ -58,6 +56,8 @@
}
._nav-current {
+ outline: 0;
+
&:before, &:after { content: ''; }
}
diff --git a/assets/stylesheets/components/_sidebar.scss b/assets/stylesheets/components/_sidebar.scss
index c97847b7..40808032 100644
--- a/assets/stylesheets/components/_sidebar.scss
+++ b/assets/stylesheets/components/_sidebar.scss
@@ -32,8 +32,6 @@
}
}
- a:focus { outline: 0; }
-
._sidebar-hidden & {
display: none;
}
@@ -88,6 +86,8 @@
min-height: 100%;
padding-bottom: 3.5rem;
}
+
+ a:focus { outline: 0; }
}
._list-title {
@@ -422,6 +422,8 @@
}
._sidebar-footer-edit {
+ display: inline-block;
+
@if $style == 'dark' {
&:before { @extend %icon-settings-white; }
} @else {
diff --git a/assets/stylesheets/global/_base.scss b/assets/stylesheets/global/_base.scss
index e78e7afc..113fbe55 100644
--- a/assets/stylesheets/global/_base.scss
+++ b/assets/stylesheets/global/_base.scss
@@ -159,6 +159,8 @@ td {
> pre:last-child, > p:last-child, > ul:last-child, > ol:last-child { margin-bottom: 0; }
}
+section, main { outline: 0; }
+
input, button {
margin: 0;
font-family: inherit;
@@ -179,6 +181,11 @@ button, input[type="search"] {
-moz-appearance: none;
}
+button:focus {
+ outline: 1px dotted;
+ outline: -webkit-focus-ring-color auto 5px;
+}
+
input[type="search"]::-webkit-search-cancel-button,
input[type="search"]::-webkit-search-decoration {
-webkit-appearance: none;
diff --git a/assets/stylesheets/global/_classes.scss b/assets/stylesheets/global/_classes.scss
index 55843e2d..a4c1810d 100644
--- a/assets/stylesheets/global/_classes.scss
+++ b/assets/stylesheets/global/_classes.scss
@@ -22,7 +22,7 @@
%hide-text {
white-space: nowrap;
overflow: hidden;
- color: transparent !important;
+ text-indent: -1000px;
@extend %user-select-none;
}
diff --git a/views/app.erb b/views/app.erb
index 1cba7e18..9ad9494d 100644
--- a/views/app.erb
+++ b/views/app.erb
@@ -19,7 +19,7 @@
Tips
-