diff --git a/docs/_data/nav.yml b/docs/_data/nav.yml index 7f101146..efc9e696 100644 --- a/docs/_data/nav.yml +++ b/docs/_data/nav.yml @@ -25,6 +25,7 @@ - title: Material Design pages: + - title: Test - title: Forms - title: Components diff --git a/docs/assets/js/src/application.js b/docs/assets/js/src/application.js index 2b88f802..b903c88c 100644 --- a/docs/assets/js/src/application.js +++ b/docs/assets/js/src/application.js @@ -107,12 +107,20 @@ class Application { .tooltip('_fixTitle') }) } + + manipulateSearchBox() { + let $search = $('#search-input') + $search.wrap(`
`) + $search.before(``) + $search.removeAttr('placeholder') + } } $(() => { let app = new Application() app.displayTypographyProperties() app.initializeClipboard() + app.manipulateSearchBox() // FIXME: file inputs seems to be in flux, delete the offending one for now. $('#exampleInputFile').closest('.form-group').detach() diff --git a/docs/material-design/test.md b/docs/material-design/test.md new file mode 100644 index 00000000..ebe66430 --- /dev/null +++ b/docs/material-design/test.md @@ -0,0 +1,15 @@ +--- +layout: docs +title: Test +group: material-design +--- + +{% example html %} + +{% endexample %} diff --git a/js/src/autofill.js b/js/src/autofill.js index 96ead153..6a5b6e09 100644 --- a/js/src/autofill.js +++ b/js/src/autofill.js @@ -21,7 +21,7 @@ const Autofill = (($) => { constructor($element, config) { this.$element = $element - this.config = $.extend({}, Default, config) + this.config = $.extend(true, {}, Default, config) this._watchLoading() this._attachEventHandlers() diff --git a/js/src/baseInput.js b/js/src/baseInput.js index 0efda33b..f67f1179 100644 --- a/js/src/baseInput.js +++ b/js/src/baseInput.js @@ -2,6 +2,23 @@ import Util from './util' const BaseInput = (($) => { + const ClassName = { + FORM_GROUP: 'form-group', + MDB_FORM_GROUP: 'mdb-form-group', + MDB_LABEL: 'mdb-label', + MDB_LABEL_PLACEHOLDER: 'mdb-label-placeholder', + MDB_LABEL_FLOATING: 'mdb-label-floating', + HAS_DANGER: 'has-danger', + IS_EMPTY: 'is-empty', + IS_FOCUSED: 'is-focused' + } + + const Selector = { + FORM_GROUP: `.${ClassName.FORM_GROUP}`, + MDB_FORM_GROUP: `.${ClassName.MDB_FORM_GROUP}`, + MDB_LABEL_WILDCARD: `label[class^='${ClassName.MDB_LABEL}'], label[class*=' ${ClassName.MDB_LABEL}']` // match any label variant if specified + } + const Default = { validate: false, formGroup: { @@ -10,25 +27,27 @@ const BaseInput = (($) => { mdbFormGroup: { template: `` }, + mdbLabel: { + required: false, + + // Prioritized find order for resolving the label to be used as an mdb-label if not specified in the markup + // - a function(thisComponent); or + // - a string selector used like $mdbFormGroup.find(selector) + // + // Note this only runs if $mdbFormGroup.find(Selector.MDB_LABEL_WILDCARD) fails to find a label (as authored in the markup) + // + selectors: [ + `.form-control-label`, // in the case of horizontal or inline forms, this will be marked + `> label` // usual case for text inputs + ], + className: `mdb-label` + }, requiredClasses: [], invalidComponentMatches: [], convertInputSizeVariations: true } - const ClassName = { - FORM_GROUP: 'form-group', - MDB_FORM_GROUP: 'mdb-form-group', - HAS_DANGER: 'has-danger', - IS_EMPTY: 'is-empty', - IS_FOCUSED: 'is-focused' - } - - const Selector = { - FORM_GROUP: `.${ClassName.FORM_GROUP}`, - MDB_FORM_GROUP: `.${ClassName.MDB_FORM_GROUP}` - } - - const FormControlSizeConversions = { + const FormControlSizeMarkers = { 'form-control-lg': 'mdb-form-group-lg', 'form-control-sm': 'mdb-form-group-sm' } @@ -48,7 +67,7 @@ const BaseInput = (($) => { */ constructor($element, config, properties = {}) { this.$element = $element - this.config = $.extend({}, Default, config) + this.config = $.extend(true, {}, Default, config) // set properties for use in the constructor initialization for (let key in properties) { @@ -73,6 +92,9 @@ const BaseInput = (($) => { // rendering changes once added. this.$mdbFormGroup = this.resolveMdbFormGroup() + // Resolve and mark the mdbLabel if necessary as defined by the config + this.$mdbLabel = this.resolveMdbLabel() + // Signal to the mdb-form-group that a form-control-* variation is being used this.resolveMdbFormGroupSizing() @@ -197,6 +219,48 @@ const BaseInput = (($) => { return this.$element } + // Will add mdb-label to mdb-form-group if not already specified + resolveMdbLabel() { + + let label = this.$mdbFormGroup.find(Selector.MDB_LABEL_WILDCARD) + if (label === undefined || label.length === 0) { + // we need to find it based on the configured selectors + label = this.findMdbLabel(this.config.mdbLabel.required) + + if (label === undefined || label.length === 0) { + // no label found, and finder did not require one + } else { + // a candidate label was found, add the configured default class name + label.addClass(this.config.mdbLabel.className) + } + } + + return label + } + + // Find mdb-label variant based on the config selectors + findMdbLabel(raiseError = true) { + let label = null + + // use the specified selector order + for (let selector of this.config.mdbLabel.selectors) { + if ($.isFunction(selector)) { + label = selector(this) + } else { + label = this.$mdbFormGroup.find(selector) + } + + if(label !== undefined && label.length > 0){ + break; + } + } + + if (label.length === 0 && raiseError) { + $.error(`Failed to find ${Selector.MDB_LABEL_WILDCARD} within form-group for ${Util.describe(this.$element)}`) + } + return label + } + // Find mdb-form-group findMdbFormGroup(raiseError = true) { let mfg = this.$element.closest(Selector.MDB_FORM_GROUP) @@ -223,10 +287,10 @@ const BaseInput = (($) => { } // Modification - Change text-sm/lg to form-group-sm/lg instead (preferred standard and simpler css/less variants) - for (let inputSize in FormControlSizeConversions) { + for (let inputSize in FormControlSizeMarkers) { if (this.$element.hasClass(inputSize)) { //this.$element.removeClass(inputSize) - this.$mdbFormGroup.addClass(FormControlSizeConversions[inputSize]) + this.$mdbFormGroup.addClass(FormControlSizeMarkers[inputSize]) } } } diff --git a/js/src/baseToggle.js b/js/src/baseToggle.js index dbe91886..29a769e2 100644 --- a/js/src/baseToggle.js +++ b/js/src/baseToggle.js @@ -8,7 +8,22 @@ const BaseToggle = (($) => { * Constants * ------------------------------------------------------------------------ */ - const Default = {} + const Default = { + mdbLabel: { + required: false + + // Prioritized find order for resolving the label to be used as an mdb-label if not specified in the markup + // - a function(thisComponent); or + // - a string selector used like $mdbFormGroup.find(selector) + // + // Note this only runs if $mdbFormGroup.find(Selector.MDB_LABEL_WILDCARD) fails to find a label (as authored in the markup) + // + //selectors: [ + // `.form-control-label`, // in the case of horizontal or inline forms, this will be marked + // `> label` // usual case for text inputs + //] + } + } const Selector = { LABEL: 'label' @@ -26,7 +41,7 @@ const BaseToggle = (($) => { // '.checkbox|switch|radio > label > input[type=checkbox|radio]' // '.${this.outerClass} > label > input[type=${this.inputType}]' - super($element, $.extend({}, Default, config), properties) + super($element, $.extend(true, {}, Default, config), properties) this.$element.after(this.config.template) } diff --git a/js/src/bootstrapMaterialDesign.js b/js/src/bootstrapMaterialDesign.js index c5c9855d..cf3915b0 100644 --- a/js/src/bootstrapMaterialDesign.js +++ b/js/src/bootstrapMaterialDesign.js @@ -30,7 +30,10 @@ const BootstrapMaterialDesign = (($) => { */ const Default = { global: { - validate: false + validate: false, + mdbLabel: { + className: `mdb-label` + } }, ripples: { selector: [ @@ -100,7 +103,7 @@ const BootstrapMaterialDesign = (($) => { constructor($element, config) { this.$element = $element - this.config = $.extend({}, Default, config) + this.config = $.extend(true, {}, Default, config) let $document = $(document) for (let component of this.config.instantiation) { @@ -115,7 +118,7 @@ const BootstrapMaterialDesign = (($) => { let selector = this._resolveSelector(componentConfig) // mix in global options - componentConfig = $.extend({}, this.config.global, componentConfig) + componentConfig = $.extend(true, {}, this.config.global, componentConfig) // create the jquery fn name e.g. 'mdbText' for 'text' let jqueryFn = `mdb${component.charAt(0).toUpperCase() + component.slice(1)}` diff --git a/js/src/checkbox.js b/js/src/checkbox.js index c4692662..44c5d789 100644 --- a/js/src/checkbox.js +++ b/js/src/checkbox.js @@ -30,7 +30,7 @@ const Checkbox = (($) => { class Checkbox extends BaseToggle { constructor($element, config, properties = {inputType: NAME, outerClass: NAME}) { - super($element, $.extend({ + super($element, $.extend(true, { invalidComponentMatches: [File, Radio, Text, Textarea, Select] }, Default, config), properties) } diff --git a/js/src/checkboxInline.js b/js/src/checkboxInline.js index 1cc0eaa0..6d06ce42 100644 --- a/js/src/checkboxInline.js +++ b/js/src/checkboxInline.js @@ -22,7 +22,7 @@ const CheckboxInline = (($) => { class CheckboxInline extends Checkbox { constructor($element, config, properties = {inputType: 'checkbox', outerClass: 'checkbox-inline'}) { - super($element, $.extend({}, Default, config), properties) + super($element, $.extend(true, {}, Default, config), properties) } dispose() { diff --git a/js/src/file.js b/js/src/file.js index 8a10fe8f..ea04046b 100644 --- a/js/src/file.js +++ b/js/src/file.js @@ -38,7 +38,7 @@ const File = (($) => { class File extends BaseInput { constructor($element, config) { - super($element, $.extend({invalidComponentMatches: [Checkbox, Radio, Text, Textarea, Select, Switch]}, Default, config)) + super($element, $.extend(true, {invalidComponentMatches: [Checkbox, Radio, Text, Textarea, Select, Switch]}, Default, config)) this.$mdbFormGroup.addClass(ClassName.IS_FILE) } diff --git a/js/src/old/es6Template.js b/js/src/old/es6Template.js index 3e7ec2c7..06ace1ca 100644 --- a/js/src/old/es6Template.js +++ b/js/src/old/es6Template.js @@ -24,7 +24,7 @@ const Foo = (($) => { constructor($element, config) { this.$element = $element - this.config = $.extend({}, Default, config) + this.config = $.extend(true, {}, Default, config) } dispose() { diff --git a/js/src/radio.js b/js/src/radio.js index 141fa4ec..1a49f2c7 100644 --- a/js/src/radio.js +++ b/js/src/radio.js @@ -29,7 +29,7 @@ const Radio = (($) => { class Radio extends BaseToggle { constructor($element, config, properties = {inputType: NAME, outerClass: NAME}) { - super($element, $.extend({ + super($element, $.extend(true, { invalidComponentMatches: [Checkbox, File, Switch, Text] }, Default, config), properties) } diff --git a/js/src/radioInline.js b/js/src/radioInline.js index 3272260d..76dc006e 100644 --- a/js/src/radioInline.js +++ b/js/src/radioInline.js @@ -22,7 +22,7 @@ const RadioInline = (($) => { class RadioInline extends Radio { constructor($element, config, properties = {inputType: 'radio', outerClass: 'radio-inline'}) { - super($element, $.extend({}, Default, config), properties) + super($element, $.extend(true, {}, Default, config), properties) } dispose() { diff --git a/js/src/ripples.js b/js/src/ripples.js index 613febee..38875474 100644 --- a/js/src/ripples.js +++ b/js/src/ripples.js @@ -49,7 +49,7 @@ const Ripples = (($) => { this.$element = $element //console.log(`Adding ripples to ${Util.describe(this.$element)}`) // eslint-disable-line no-console - this.config = $.extend({}, Default, config) + this.config = $.extend(true, {}, Default, config) // attach initial listener this.$element.on(this.config.triggerStart, this._onStartRipple) diff --git a/js/src/select.js b/js/src/select.js index e4fedfe4..40233e6c 100644 --- a/js/src/select.js +++ b/js/src/select.js @@ -30,7 +30,7 @@ const Select = (($) => { class Select extends Text { constructor($element, config) { - super($element, $.extend({invalidComponentMatches: [Checkbox, File, Radio, Switch, Text, Textarea]}, Default, config)) + super($element, $.extend(true, {invalidComponentMatches: [Checkbox, File, Radio, Switch, Text, Textarea]}, Default, config)) } dispose() { diff --git a/js/src/switch.js b/js/src/switch.js index bc2687ef..93656511 100644 --- a/js/src/switch.js +++ b/js/src/switch.js @@ -24,7 +24,7 @@ const Switch = (($) => { class Switch extends Checkbox { constructor($element, config) { - super($element, $.extend({}, Default, config), 'checkbox', NAME) + super($element, $.extend(true, {}, Default, config), 'checkbox', NAME) // selector: '.switch > label > input[type=checkbox]' } diff --git a/js/src/text.js b/js/src/text.js index 2fb023ab..6c3cff3d 100644 --- a/js/src/text.js +++ b/js/src/text.js @@ -34,7 +34,7 @@ const Text = (($) => { class Text extends BaseInput { constructor($element, config) { - super($element, $.extend({invalidComponentMatches: [Checkbox, File, Radio, Select, Switch, Textarea]}, Default, config)) + super($element, $.extend(true, {invalidComponentMatches: [Checkbox, File, Radio, Select, Switch, Textarea]}, Default, config)) // Initially mark as empty if (this.isEmpty()) { diff --git a/js/src/textarea.js b/js/src/textarea.js index cba01c22..7e377747 100644 --- a/js/src/textarea.js +++ b/js/src/textarea.js @@ -28,7 +28,7 @@ const Textarea = (($) => { class Textarea extends Text { constructor($element, config) { - super($element, $.extend({invalidComponentMatches: [Checkbox, File, Radio, Text, Select, Switch]}, Default, config)) + super($element, $.extend(true, {invalidComponentMatches: [Checkbox, File, Radio, Text, Select, Switch]}, Default, config)) } dispose() { diff --git a/js/src/util.js b/js/src/util.js index 60c27f7a..cb37f320 100644 --- a/js/src/util.js +++ b/js/src/util.js @@ -72,7 +72,7 @@ const Util = (($) => { $element.css('border', '1px solid red') } console.error(message, $element) // eslint-disable-line no-console - $.error(message) + throw message } },