mirror of
https://github.com/mdbootstrap/mdb-ui-kit.git
synced 2025-02-09 00:00:41 +03:00
#822 initial implementation of drawer es6 component, fundamentally working.
This commit is contained in:
parent
0c073ef5ef
commit
d7932d534e
|
@ -20,7 +20,7 @@ js: example.js
|
||||||
</div>
|
</div>
|
||||||
-->
|
-->
|
||||||
<div class="navbar navbar-light bg-faded navbar-static-top">
|
<div class="navbar navbar-light bg-faded navbar-static-top">
|
||||||
<button class="navbar-toggler hidden-lg-up" type="button" data-toggle="collapse" data-target="#navbar-header">
|
<button class="navbar-toggler hidden-lg-up" type="button" data-toggle="drawer" data-target="#my-drawer">
|
||||||
<span class="sr-only">Toggle drawer</span>
|
<span class="sr-only">Toggle drawer</span>
|
||||||
<i class="material-icons">menu</i>
|
<i class="material-icons">menu</i>
|
||||||
</button>
|
</button>
|
||||||
|
@ -59,7 +59,7 @@ js: example.js
|
||||||
|
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<div class="mdb-form-group mdb-collapse-inline pull-xs-right">
|
<div class="mdb-form-group mdb-collapse-inline pull-xs-right">
|
||||||
<button class="btn mdb-btn-icon" for="search" data-toggle="collapse" data-target="#collapse-search" aria-expanded="false" aria-controls="collapse-search">
|
<button class="btn mdb-btn-icon" for="search" data-toggle="collapse" data-target="#collapse-search" aria-controls="collapse-search">
|
||||||
<i class="material-icons">search</i>
|
<i class="material-icons">search</i>
|
||||||
</button>
|
</button>
|
||||||
<span id="collapse-search" class="collapse">
|
<span id="collapse-search" class="collapse">
|
||||||
|
@ -69,7 +69,7 @@ js: example.js
|
||||||
</li>
|
</li>
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<div class="dropdown">
|
<div class="dropdown">
|
||||||
<button class="btn mdb-btn-icon btn-secondary dropdown-toggle" type="button" id="nav-extras-menu" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
|
<button class="btn mdb-btn-icon btn-secondary dropdown-toggle" type="button" id="nav-extras-menu" data-toggle="dropdown" aria-haspopup="true" >
|
||||||
<i class="material-icons">more_vert</i>
|
<i class="material-icons">more_vert</i>
|
||||||
</button>
|
</button>
|
||||||
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="nav-extras-menu">
|
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="nav-extras-menu">
|
||||||
|
@ -83,13 +83,13 @@ js: example.js
|
||||||
</div>
|
</div>
|
||||||
</header>
|
</header>
|
||||||
|
|
||||||
<div class="mdb-layout-drawer">
|
<div id="my-drawer" class="mdb-layout-drawer">
|
||||||
<header>
|
<header>
|
||||||
<img src="images/user.jpg" class="avatar">
|
<img src="images/user.jpg" class="avatar">
|
||||||
<div class="account">
|
<div class="account">
|
||||||
<span>hello@example.com</span>
|
<span>hello@example.com</span>
|
||||||
<div class="dropdown">
|
<div class="dropdown">
|
||||||
<button class="btn mdb-btn-icon dropdown-toggle" type="button" id="nav-account-menu" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
|
<button class="btn mdb-btn-icon dropdown-toggle" type="button" id="nav-account-menu" data-toggle="dropdown" aria-haspopup="true">
|
||||||
<i class="material-icons">arrow_drop_down</i>
|
<i class="material-icons">arrow_drop_down</i>
|
||||||
</button>
|
</button>
|
||||||
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="nav-account-menu">
|
<div class="dropdown-menu dropdown-menu-right" aria-labelledby="nav-account-menu">
|
||||||
|
|
|
@ -4,14 +4,22 @@ import Util from './util'
|
||||||
const BaseLayout = (($) => {
|
const BaseLayout = (($) => {
|
||||||
|
|
||||||
const ClassName = {
|
const ClassName = {
|
||||||
CONTAINER: 'mdb-form-group'
|
CONTAINER: 'mdb-layout-container',
|
||||||
|
BACKDROP: `mdb-layout-backdrop`
|
||||||
}
|
}
|
||||||
|
|
||||||
const Selector = {
|
const Selector = {
|
||||||
CONTAINER: `.${ClassName.CONTAINER}`
|
CONTAINER: `.${ClassName.CONTAINER}`,
|
||||||
|
BACKDROP: `.${ClassName.BACKDROP}`
|
||||||
}
|
}
|
||||||
|
|
||||||
const Default = {}
|
const Default = {
|
||||||
|
backdrop: {
|
||||||
|
create: true,
|
||||||
|
required: true,
|
||||||
|
template: `<div class="${ClassName.BACKDROP}"></div>`
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ------------------------------------------------------------------------
|
* ------------------------------------------------------------------------
|
||||||
|
@ -22,17 +30,45 @@ const BaseLayout = (($) => {
|
||||||
|
|
||||||
constructor($element, config, properties = {}) {
|
constructor($element, config, properties = {}) {
|
||||||
super($element, $.extend(true, {}, Default, config), properties)
|
super($element, $.extend(true, {}, Default, config), properties)
|
||||||
|
|
||||||
|
this.$container = this.findContainer(true)
|
||||||
|
this.$backdrop = this.resolveBackdrop()
|
||||||
}
|
}
|
||||||
|
|
||||||
dispose(dataKey) {
|
dispose(dataKey) {
|
||||||
super.dispose(dataKey)
|
super.dispose(dataKey)
|
||||||
|
this.$container = null
|
||||||
|
this.$backdrop = null
|
||||||
}
|
}
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
// protected
|
// protected
|
||||||
|
|
||||||
|
// Will add mdb-layout-backdrop to mdb-layout-container if necessary
|
||||||
|
resolveBackdrop() {
|
||||||
|
let bd = this.findBackdrop(false)
|
||||||
|
if (bd === undefined || bd.length === 0) {
|
||||||
|
if (this.config.backdrop.create) {
|
||||||
|
this.$container.append(this.config.backdrop.template)
|
||||||
|
}
|
||||||
|
|
||||||
|
bd = this.findBackdrop(this.config.backdrop.required)
|
||||||
|
}
|
||||||
|
|
||||||
|
return bd
|
||||||
|
}
|
||||||
|
|
||||||
// Find closest mdb-layout-container based on the given context
|
// Find closest mdb-layout-container based on the given context
|
||||||
findLayoutContainer(raiseError = true, context = this.$element) {
|
findBackdrop(raiseError = true, context = this.$container) {
|
||||||
|
let backdrop = context.find(`> ${Selector.BACKDROP}`)
|
||||||
|
if (backdrop.length === 0 && raiseError) {
|
||||||
|
$.error(`Failed to find ${Selector.BACKDROP} for ${Util.describe(context)}`)
|
||||||
|
}
|
||||||
|
return backdrop
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find closest mdb-layout-container based on the given context
|
||||||
|
findContainer(raiseError = true, context = this.$element) {
|
||||||
let container = context.closest(Selector.CONTAINER)
|
let container = context.closest(Selector.CONTAINER)
|
||||||
if (container.length === 0 && raiseError) {
|
if (container.length === 0 && raiseError) {
|
||||||
$.error(`Failed to find ${Selector.CONTAINER} for ${Util.describe(context)}`)
|
$.error(`Failed to find ${Selector.CONTAINER} for ${Util.describe(context)}`)
|
||||||
|
|
7
js/src/bootstrapMaterialDesign.js
vendored
7
js/src/bootstrapMaterialDesign.js
vendored
|
@ -49,8 +49,8 @@ const BootstrapMaterialDesign = (($) => {
|
||||||
collapseInline: {
|
collapseInline: {
|
||||||
selector: '.mdb-collapse-inline [data-toggle="collapse"]'
|
selector: '.mdb-collapse-inline [data-toggle="collapse"]'
|
||||||
},
|
},
|
||||||
drawerToggle: {
|
drawer: {
|
||||||
selector: '[data-toggle="drawer"]'
|
selector: '.mdb-layout-drawer'
|
||||||
},
|
},
|
||||||
file: {
|
file: {
|
||||||
selector: 'input[type=file]'
|
selector: 'input[type=file]'
|
||||||
|
@ -97,7 +97,7 @@ const BootstrapMaterialDesign = (($) => {
|
||||||
'checkboxInline',
|
'checkboxInline',
|
||||||
'collapseInline',
|
'collapseInline',
|
||||||
'layout',
|
'layout',
|
||||||
'drawerToggle',
|
'drawer',
|
||||||
'file',
|
'file',
|
||||||
'radio',
|
'radio',
|
||||||
'radioInline',
|
'radioInline',
|
||||||
|
@ -153,6 +153,7 @@ const BootstrapMaterialDesign = (($) => {
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
let message = `Failed to instantiate component: $('${selector}')[${jqueryFn}](${componentConfig})`
|
let message = `Failed to instantiate component: $('${selector}')[${jqueryFn}](${componentConfig})`
|
||||||
console.error(message, e, `\nSelected elements: `, $(selector)) // eslint-disable-line no-console
|
console.error(message, e, `\nSelected elements: `, $(selector)) // eslint-disable-line no-console
|
||||||
|
throw e
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
166
js/src/drawer.js
Normal file
166
js/src/drawer.js
Normal file
|
@ -0,0 +1,166 @@
|
||||||
|
import BaseLayout from './baseLayout'
|
||||||
|
|
||||||
|
const Drawer = (($) => {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
* Constants
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
const NAME = 'drawer'
|
||||||
|
const DATA_KEY = `mdb.${NAME}`
|
||||||
|
const JQUERY_NAME = `mdb${NAME.charAt(0).toUpperCase() + NAME.slice(1)}`
|
||||||
|
const JQUERY_NO_CONFLICT = $.fn[JQUERY_NAME]
|
||||||
|
|
||||||
|
const Keycodes = {
|
||||||
|
ESCAPE: 27
|
||||||
|
//ENTER: 13,
|
||||||
|
//SPACE: 32
|
||||||
|
}
|
||||||
|
|
||||||
|
const ClassName = {
|
||||||
|
IN: 'in',
|
||||||
|
DRAWER_IN: `mdb-drawer-in`,
|
||||||
|
DRAWER: 'mdb-layout-drawer',
|
||||||
|
CONTAINER: 'mdb-layout-container'
|
||||||
|
}
|
||||||
|
|
||||||
|
const Default = {
|
||||||
|
focusSelector: `a, button, input`
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
* Class Definition
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
class Drawer extends BaseLayout {
|
||||||
|
|
||||||
|
// $element is expected to be the trigger
|
||||||
|
// i.e. <button class="btn mdb-btn-icon" for="search" data-toggle="drawer" data-target="#my-side-nav-drawer" aria-expanded="false" aria-controls="my-side-nav-drawer">
|
||||||
|
constructor($element, config) {
|
||||||
|
super($element, $.extend(true, {}, Default, config))
|
||||||
|
|
||||||
|
//this.$toggles = $.makeArray($(`[data-toggle="drawer"][href="#${this.$element[0].id}"], [data-toggle="drawer"][data-target="#${this.$element[0].id}"]`))
|
||||||
|
this.$toggles = $(`[data-toggle="drawer"][href="#${this.$element[0].id}"], [data-toggle="drawer"][data-target="#${this.$element[0].id}"]`)
|
||||||
|
|
||||||
|
this._addAria()
|
||||||
|
|
||||||
|
// click or escape on the backdrop closes the drawer
|
||||||
|
this.$backdrop.keydown((ev) => {
|
||||||
|
if (ev.which === Keycodes.ESCAPE) {
|
||||||
|
this.hide()
|
||||||
|
}
|
||||||
|
}).click(() => {
|
||||||
|
this.hide()
|
||||||
|
})
|
||||||
|
|
||||||
|
// escape on the drawer closes it
|
||||||
|
this.$element.keydown((ev) => {
|
||||||
|
if (ev.which === Keycodes.ESCAPE) {
|
||||||
|
this.hide()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
// any toggle button clicks
|
||||||
|
this.$toggles.click(() => {
|
||||||
|
this.toggle()
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
dispose() {
|
||||||
|
super.dispose(DATA_KEY)
|
||||||
|
this.$toggles = null
|
||||||
|
}
|
||||||
|
|
||||||
|
toggle() {
|
||||||
|
if (this._isOpen()) {
|
||||||
|
this.hide()
|
||||||
|
} else {
|
||||||
|
this.show()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
show() {
|
||||||
|
if (this._isOpen()) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
this.$toggles.attr('aria-expanded', true)
|
||||||
|
this.$element.attr('aria-expanded', true)
|
||||||
|
this.$element.attr('aria-hidden', false)
|
||||||
|
|
||||||
|
// focus on the first focusable item
|
||||||
|
let $focusOn = this.$element.find(this.config.focusSelector)
|
||||||
|
if ($focusOn.length > 0) {
|
||||||
|
$focusOn.first().focus()
|
||||||
|
}
|
||||||
|
|
||||||
|
this.$container.addClass(ClassName.DRAWER_IN)
|
||||||
|
// backdrop is responsively styled based on mdb-drawer-overlay, therefore style is none of our concern, simply add the marker class and let the scss determine if it should be displayed or not.
|
||||||
|
this.$backdrop.addClass(ClassName.IN)
|
||||||
|
}
|
||||||
|
|
||||||
|
hide() {
|
||||||
|
if (!this._isOpen()) {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
this.$toggles.attr('aria-expanded', false)
|
||||||
|
this.$element.attr('aria-expanded', false)
|
||||||
|
this.$element.attr('aria-hidden', true)
|
||||||
|
|
||||||
|
this.$container.removeClass(ClassName.DRAWER_IN)
|
||||||
|
this.$backdrop.removeClass(ClassName.IN)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// private
|
||||||
|
|
||||||
|
_isOpen() {
|
||||||
|
return this.$container.hasClass(ClassName.DRAWER_IN)
|
||||||
|
}
|
||||||
|
|
||||||
|
_addAria() {
|
||||||
|
let isOpen = this._isOpen()
|
||||||
|
this.$element.attr('aria-expanded', isOpen)
|
||||||
|
this.$element.attr('aria-hidden', isOpen)
|
||||||
|
|
||||||
|
if (this.$toggles.length) {
|
||||||
|
this.$toggles.attr('aria-expanded', isOpen)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// static
|
||||||
|
static _jQueryInterface(config) {
|
||||||
|
return this.each(function () {
|
||||||
|
let $element = $(this)
|
||||||
|
let data = $element.data(DATA_KEY)
|
||||||
|
|
||||||
|
if (!data) {
|
||||||
|
data = new Drawer($element, config)
|
||||||
|
$element.data(DATA_KEY, data)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
* jQuery
|
||||||
|
* ------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
$.fn[JQUERY_NAME] = Drawer._jQueryInterface
|
||||||
|
$.fn[JQUERY_NAME].Constructor = Drawer
|
||||||
|
$.fn[JQUERY_NAME].noConflict = () => {
|
||||||
|
$.fn[JQUERY_NAME] = JQUERY_NO_CONFLICT
|
||||||
|
return Drawer._jQueryInterface
|
||||||
|
}
|
||||||
|
|
||||||
|
return Drawer
|
||||||
|
|
||||||
|
})(jQuery)
|
||||||
|
|
||||||
|
export default Drawer
|
|
@ -1,100 +0,0 @@
|
||||||
import BaseLayout from './baseLayout'
|
|
||||||
import Util from './util'
|
|
||||||
|
|
||||||
const DrawerToggle = (($) => {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
* Constants
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
const NAME = 'drawerToggle'
|
|
||||||
const DATA_KEY = `mdb.${NAME}`
|
|
||||||
const JQUERY_NAME = `mdb${NAME.charAt(0).toUpperCase() + NAME.slice(1)}`
|
|
||||||
const JQUERY_NO_CONFLICT = $.fn[JQUERY_NAME]
|
|
||||||
|
|
||||||
const ClassName = {
|
|
||||||
//IN: 'in',
|
|
||||||
DRAWER: 'mdb-layout-drawer',
|
|
||||||
CONTAINER: 'mdb-layout-container'
|
|
||||||
|
|
||||||
//COLLAPSING: 'collapsing',
|
|
||||||
//COLLAPSED: 'collapsed',
|
|
||||||
//WIDTH: 'width'
|
|
||||||
}
|
|
||||||
|
|
||||||
//const Selector = {
|
|
||||||
// CONTAINER: `.${ClassName.CONTAINER}`
|
|
||||||
//}
|
|
||||||
|
|
||||||
|
|
||||||
const Default = {}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
* Class Definition
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
class DrawerToggle extends BaseLayout {
|
|
||||||
|
|
||||||
// $element is expected to be the trigger
|
|
||||||
// i.e. <button class="btn mdb-btn-icon" for="search" data-toggle="drawer" data-target="#my-side-nav-drawer" aria-expanded="false" aria-controls="my-side-nav-drawer">
|
|
||||||
constructor($element, config) {
|
|
||||||
super($element, $.extend(true, {}, Default, config))
|
|
||||||
|
|
||||||
let selector = $element.data('target')
|
|
||||||
this.$drawer = $(selector)
|
|
||||||
|
|
||||||
Util.assert($element, this.$drawer.length === 0, `Cannot find drawer target for ${Util.describe($element)}`)
|
|
||||||
Util.assert(this.$drawer, !this.$drawer.hasClass(ClassName.DRAWER), `${Util.describe(this.$drawer)} is expected to have the '${ClassName.DRAWER}' class. It is being targeted by ${Util.describe($element)}`)
|
|
||||||
|
|
||||||
|
|
||||||
// find the drawer's container - remember, this button may be outside the container, we only need the target's container.
|
|
||||||
this.$layoutContainer = this.findLayoutContainer(true, this.$drawer)
|
|
||||||
|
|
||||||
// get a handle to the Layout object and interact with it? i.e. show/hide?
|
|
||||||
}
|
|
||||||
|
|
||||||
dispose() {
|
|
||||||
super.dispose(DATA_KEY)
|
|
||||||
this.$drawer = null
|
|
||||||
this.$layoutContainer = null
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
|
||||||
// private
|
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
|
||||||
// static
|
|
||||||
static _jQueryInterface(config) {
|
|
||||||
return this.each(function () {
|
|
||||||
let $element = $(this)
|
|
||||||
let data = $element.data(DATA_KEY)
|
|
||||||
|
|
||||||
if (!data) {
|
|
||||||
data = new DrawerToggle($element, config)
|
|
||||||
$element.data(DATA_KEY, data)
|
|
||||||
}
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
* jQuery
|
|
||||||
* ------------------------------------------------------------------------
|
|
||||||
*/
|
|
||||||
$.fn[JQUERY_NAME] = DrawerToggle._jQueryInterface
|
|
||||||
$.fn[JQUERY_NAME].Constructor = DrawerToggle
|
|
||||||
$.fn[JQUERY_NAME].noConflict = () => {
|
|
||||||
$.fn[JQUERY_NAME] = JQUERY_NO_CONFLICT
|
|
||||||
return DrawerToggle._jQueryInterface
|
|
||||||
}
|
|
||||||
|
|
||||||
return DrawerToggle
|
|
||||||
|
|
||||||
})(jQuery)
|
|
||||||
|
|
||||||
export default DrawerToggle
|
|
|
@ -23,7 +23,7 @@ import Text from './text'
|
||||||
import Textarea from './textarea'
|
import Textarea from './textarea'
|
||||||
|
|
||||||
import Layout from './layout'
|
import Layout from './layout'
|
||||||
import DrawerToggle from './drawerToggle'
|
import DrawerToggle from './drawer'
|
||||||
|
|
||||||
import Ripples from './ripples'
|
import Ripples from './ripples'
|
||||||
import Autofill from './autofill'
|
import Autofill from './autofill'
|
||||||
|
|
177
js/src/layout.js
177
js/src/layout.js
|
@ -12,30 +12,19 @@ const Layout = (($) => {
|
||||||
const JQUERY_NAME = `mdb${NAME.charAt(0).toUpperCase() + NAME.slice(1)}`
|
const JQUERY_NAME = `mdb${NAME.charAt(0).toUpperCase() + NAME.slice(1)}`
|
||||||
const JQUERY_NO_CONFLICT = $.fn[JQUERY_NAME]
|
const JQUERY_NO_CONFLICT = $.fn[JQUERY_NAME]
|
||||||
|
|
||||||
const Keycodes = {
|
//const ClassName = {
|
||||||
ENTER: 13,
|
// CANVAS: 'mdb-layout-canvas',
|
||||||
ESCAPE: 27,
|
// HEADER: 'mdb-layout-header',
|
||||||
SPACE: 32
|
// DRAWER: 'mdb-layout-drawer',
|
||||||
}
|
// CONTENT: 'mdb-layout-content',
|
||||||
|
// BACKDROP: 'mdb-layout-backdrop',
|
||||||
|
//}
|
||||||
|
|
||||||
const ClassName = {
|
//const Selector = {
|
||||||
CANVAS: 'mdb-layout-canvas',
|
// DRAWER: `.${ClassName.DRAWER}`,
|
||||||
HEADER: 'mdb-layout-header',
|
// HEADER: `.${ClassName.HEADER}`,
|
||||||
DRAWER: 'mdb-layout-drawer',
|
// CONTENT: `.${ClassName.CONTENT}`
|
||||||
CONTENT: 'mdb-layout-content',
|
//}
|
||||||
DRAWER_BTN: 'mdb-layout-drawer-button', // FIXME: swithch to data-drawer attr finder or something like that, see navbar toggler
|
|
||||||
BACKDROP: 'mdb-layout-backdrop',
|
|
||||||
|
|
||||||
DRAWER_IN: `mdb-drawer-in`
|
|
||||||
}
|
|
||||||
|
|
||||||
const Selector = {
|
|
||||||
DRAWER_BTN: `.${ClassName.DRAWER_BTN}`,
|
|
||||||
DRAWER: `.${ClassName.DRAWER}`,
|
|
||||||
HEADER: `.${ClassName.HEADER}`,
|
|
||||||
CONTENT: `.${ClassName.CONTENT}`,
|
|
||||||
DATA_TOGGLE_DRAWER: '[data-toggle="drawer"]'
|
|
||||||
}
|
|
||||||
|
|
||||||
const Default = {}
|
const Default = {}
|
||||||
|
|
||||||
|
@ -57,151 +46,15 @@ const Layout = (($) => {
|
||||||
//this.$element.parentElement.removeChild(this.$element)
|
//this.$element.parentElement.removeChild(this.$element)
|
||||||
//canvas.appendChild(this.$element)
|
//canvas.appendChild(this.$element)
|
||||||
|
|
||||||
this.$header = $element.find(`> ${Selector.HEADER}`)
|
//this.$header = $element.find(`> ${Selector.HEADER}`)
|
||||||
this.$drawer = $element.find(`> ${Selector.DRAWER}`)
|
//this.$drawer = $element.find(`> ${Selector.DRAWER}`)
|
||||||
this.$content = $element.find(`> ${Selector.CONTENT}`)
|
//this.$content = $element.find(`> ${Selector.CONTENT}`)
|
||||||
|
|
||||||
|
|
||||||
// Add drawer toggling button to our layout, if we have an openable drawer.
|
|
||||||
if (this.$drawer) {
|
|
||||||
|
|
||||||
// FIXME: separate DrawerToggle component?
|
|
||||||
//this.$drawerBtn = $element.find(`${DRAWER_BTN}`)
|
|
||||||
//
|
|
||||||
//if (this.$drawerBtn) { // FIXME what about many drawer buttons? implies a separate jquery class
|
|
||||||
//
|
|
||||||
// this.$drawerBtn.click((ev) => {
|
|
||||||
// this._drawerToggleHandler(ev)
|
|
||||||
// })
|
|
||||||
// this.$drawerBtn.keydown((ev) => {
|
|
||||||
// this._drawerToggleHandler(ev)
|
|
||||||
// })
|
|
||||||
//}
|
|
||||||
|
|
||||||
// create the backdrop
|
|
||||||
this.$backdrop = $(`<div class="${ClassName.BACKDROP}"></div>`)
|
|
||||||
this.$backdrop.click((ev) => {
|
|
||||||
this._drawerToggleHandler(ev)
|
|
||||||
})
|
|
||||||
this.$element.append(this.$backdrop)
|
|
||||||
|
|
||||||
this.$drawer.keydown((ev) => {
|
|
||||||
this._onDrawerKeydown(ev)
|
|
||||||
})
|
|
||||||
this.$drawer.attr('aria-hidden', 'true')
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
dispose() {
|
dispose() {
|
||||||
super.dispose(DATA_KEY)
|
super.dispose(DATA_KEY)
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Toggle drawer state
|
|
||||||
*/
|
|
||||||
toggleDrawer() {
|
|
||||||
//FIXME: seems terrible, look at navbar toggler
|
|
||||||
|
|
||||||
//$drawerBtn = this.$element.querySelector(Selector.DRAWER_BTN)
|
|
||||||
//var firstLink = document.querySelector(Selector.DRAWER + ' a')
|
|
||||||
//this.$drawer.classList.toggle(ClassName.IS_DRAWER_OPEN)
|
|
||||||
//this.$backdrop.classList.toggle(ClassName.IS_DRAWER_OPEN)
|
|
||||||
//
|
|
||||||
//// focus first link if drawer will be opened otherwise focus the drawer button
|
|
||||||
//if (this.$drawer.hasClass(ClassName.IS_DRAWER_OPEN)) {
|
|
||||||
// this.$drawer.attr('aria-hidden', 'false')
|
|
||||||
// this.$drawerBtn.attr('aria-expanded', 'true')
|
|
||||||
// if (firstLink) {
|
|
||||||
// firstLink.focus()
|
|
||||||
// }
|
|
||||||
//} else {
|
|
||||||
// this.$drawer.attr('aria-hidden', 'true')
|
|
||||||
// this.$drawerBtn.attr('aria-expanded', 'false')
|
|
||||||
// this.$drawerBtn.focus()
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
toggleDrawer() {
|
|
||||||
if ($(this._element).hasClass(ClassName.DRAWER_IN)) {
|
|
||||||
this.hide()
|
|
||||||
} else {
|
|
||||||
this.show()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
show() {
|
|
||||||
if ($(this._element).hasClass(ClassName.IN)) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
this._element.setAttribute('aria-expanded', true)
|
|
||||||
|
|
||||||
if (this._triggerArray.length) {
|
|
||||||
$(this._triggerArray)
|
|
||||||
.removeClass(ClassName.COLLAPSED)
|
|
||||||
.attr('aria-expanded', true)
|
|
||||||
}
|
|
||||||
|
|
||||||
$(this._element)
|
|
||||||
.removeClass(ClassName.COLLAPSING)
|
|
||||||
.addClass(ClassName.COLLAPSE)
|
|
||||||
.addClass(ClassName.IN)
|
|
||||||
}
|
|
||||||
|
|
||||||
hide() {
|
|
||||||
if (this._isTransitioning || !$(this._element).hasClass(ClassName.IN)) {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
this._element.setAttribute('aria-expanded', false)
|
|
||||||
|
|
||||||
if (this._triggerArray.length) {
|
|
||||||
$(this._triggerArray)
|
|
||||||
.addClass(ClassName.COLLAPSED)
|
|
||||||
.attr('aria-expanded', false)
|
|
||||||
}
|
|
||||||
|
|
||||||
$(this._element)
|
|
||||||
.removeClass(ClassName.COLLAPSING)
|
|
||||||
.addClass(ClassName.COLLAPSE)
|
|
||||||
.trigger(Event.HIDDEN)
|
|
||||||
}
|
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
|
||||||
// private
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Handles events of of drawer button.
|
|
||||||
*
|
|
||||||
* @param {Event} ev The event that fired.
|
|
||||||
* @private
|
|
||||||
*/
|
|
||||||
_drawerToggleHandler(ev) {
|
|
||||||
if (ev && (ev.type === 'keydown')) {
|
|
||||||
if (ev.keyCode === Keycodes.SPACE || ev.keyCode === Keycodes.ENTER) {
|
|
||||||
// prevent scrolling in drawer nav
|
|
||||||
ev.preventDefault()
|
|
||||||
} else {
|
|
||||||
// prevent other keys
|
|
||||||
return
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
this.toggleDrawer()
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Handles a keyboard event on the drawer.
|
|
||||||
*/
|
|
||||||
_onDrawerKeydown(ev) {
|
|
||||||
if (ev.keyCode === Keycodes.ESCAPE) {
|
|
||||||
this.toggleDrawer()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// ------------------------------------------------------------------------
|
// ------------------------------------------------------------------------
|
||||||
// static
|
// static
|
||||||
static _jQueryInterface(config) {
|
static _jQueryInterface(config) {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user