diff --git a/README.md b/README.md
index 9e32b24d..f0fd8ab7 100644
--- a/README.md
+++ b/README.md
@@ -3,7 +3,6 @@
[](https://www.npmjs.com/package/jQuery-QueryBuilder)
[](https://www.jsdelivr.com/package/npm/jQuery-QueryBuilder)
[](https://github.com/mistic100/jQuery-QueryBuilder/actions)
-[](https://david-dm.org/mistic100/jQuery-QueryBuilder)
[](https://gitlocalize.com/repo/5259/whole_project?utm_source=badge)
jQuery plugin offering an simple interface to create complex queries.
@@ -34,18 +33,14 @@ $ npm install jQuery-QueryBuilder
jQuery-QueryBuilder is available on [jsDelivr](https://www.jsdelivr.com/package/npm/jQuery-QueryBuilder).
### Dependencies
* [jQuery 3](https://jquery.com)
- * [Bootstrap 3](https://getbootstrap.com/docs/3.3) (CSS only)
+ * [Bootstrap 5](https://getbootstrap.com/docs/5.3/) CSS and bundle.js which includes `Popper` for tooltips and popovers
+ * [Bootstrap Icons](https://icons.getbootstrap.com/)
* [jQuery.extendext](https://github.com/mistic100/jQuery.extendext)
- * [doT.js](https://olado.github.io/doT)
* [MomentJS](https://momentjs.com) (optional, for Date/Time validation)
* [SQL Parser](https://github.com/mistic100/sql-parser) (optional, for SQL methods)
* Other Bootstrap/jQuery plugins used by plugins
-($.extendext and doT.js are directly included in the [standalone](https://github.com/mistic100/jQuery-QueryBuilder/blob/master/dist/js/query-builder.standalone.js) file)
-
-### Browser support
- * Internet Explorer >= 11
- * All other recent browsers
+($.extendext is directly included in the [standalone](https://github.com/mistic100/jQuery-QueryBuilder/blob/master/dist/js/query-builder.standalone.js) file)
diff --git a/build/jsdoc.md b/build/jsdoc.md
index 029fecb1..e329af92 100644
--- a/build/jsdoc.md
+++ b/build/jsdoc.md
@@ -1,4 +1,4 @@
-# [Main documentation](..)
+# [Main documentation](..)
# Entry point: [$.fn.QueryBuilder](external-_jQuery.fn_.html)
diff --git a/examples/index.html b/examples/index.html
index 0b697b7d..180652b8 100644
--- a/examples/index.html
+++ b/examples/index.html
@@ -1,5 +1,5 @@
-
+
@@ -7,29 +7,21 @@
jQuery QueryBuilder Example
-
-
-
+
+
-
-
-
-
+
@@ -80,7 +72,7 @@
jQuery QueryBuilder
-
@@ -106,22 +98,23 @@ Output
-
+
-
-
-
+
+
-
-
diff --git a/package.json b/package.json
index af9906cf..4111f3a0 100644
--- a/package.json
+++ b/package.json
@@ -13,7 +13,9 @@
"src/"
],
"dependencies": {
- "bootstrap": "^3.4.1",
+ "bootstrap": "^5.3.0",
+ "@popperjs/core": "^2.11.8",
+ "bootstrap-icons": "^1.11.3",
"jquery": "^3.5.1",
"jquery-extendext": "^1.0.0",
"moment": "^2.29.1",
@@ -22,10 +24,8 @@
"devDependencies": {
"alive-server": "^1.3.0",
"awesome-bootstrap-checkbox": "^0.3.7",
- "bootbox": "^4.4.0",
- "bootstrap-select": "^1.12.4",
+ "bootbox": "^6.0.0",
"bootstrap-slider": "^10.0.0",
- "bootswatch-dist": "git+https://github.com/dbtek/bootswatch-dist.git#slate",
"chosenjs": "^1.4.3",
"concurrently": "^8.2.0",
"deepmerge": "^2.1.0",
@@ -34,7 +34,7 @@
"interactjs": "^1.3.3",
"nodemon": "^2.0.22",
"sass": "^1.63.6",
- "selectize": "^0.12.4"
+ "@selectize/selectize": "^0.15.2"
},
"keywords": [
"jquery",
diff --git a/src/defaults.js b/src/defaults.js
index b6c5a5eb..b63b1251 100644
--- a/src/defaults.js
+++ b/src/defaults.js
@@ -187,10 +187,10 @@ QueryBuilder.DEFAULTS = {
],
icons: {
- add_group: 'glyphicon glyphicon-plus-sign',
- add_rule: 'glyphicon glyphicon-plus',
- remove_group: 'glyphicon glyphicon-remove',
- remove_rule: 'glyphicon glyphicon-remove',
- error: 'glyphicon glyphicon-warning-sign'
+ add_group: 'bi-plus-circle-fill',
+ add_rule: 'bi-plus-lg',
+ remove_group: 'bi-x-lg',
+ remove_rule: 'bi-x-lg',
+ error: 'bi-exclamation-triangle'
}
};
diff --git a/src/main.js b/src/main.js
index 93137f22..0659d288 100644
--- a/src/main.js
+++ b/src/main.js
@@ -134,7 +134,7 @@ var QueryBuilder = function($el, options) {
this.status.id = this.$el.attr('id');
// INIT
- this.$el.addClass('query-builder form-inline');
+ this.$el.addClass('query-builder');
this.filters = this.checkFilters(this.filters);
this.operators = this.checkOperators(this.operators);
diff --git a/src/plugins/bt-checkbox/plugin.js b/src/plugins/bt-checkbox/plugin.js
index 7a7311c2..26b0998f 100644
--- a/src/plugins/bt-checkbox/plugin.js
+++ b/src/plugins/bt-checkbox/plugin.js
@@ -3,12 +3,12 @@
* @memberof module:plugins
* @description Applies Awesome Bootstrap Checkbox for checkbox and radio inputs.
* @param {object} [options]
- * @param {string} [options.font='glyphicons']
+ * @param {string} [options.font='bootstrap-icons']
* @param {string} [options.color='default']
*/
QueryBuilder.define('bt-checkbox', function(options) {
- if (options.font == 'glyphicons') {
- this.$el.addClass('bt-checkbox-glyphicons');
+ if (options.font === 'bootstrap-icons') {
+ this.$el.addClass('bt-checkbox-bootstrap-icons');
}
this.on('getRuleInput.filter', function(h, rule, name) {
@@ -31,15 +31,11 @@ QueryBuilder.define('bt-checkbox', function(options) {
var color = filter.colors[key] || filter.colors._def_ || options.color;
var id = name + '_' + (i++);
- h.value+= '\
- \
- \
- \
-
';
+ h.value += `
`;
});
}
});
}, {
- font: 'glyphicons',
+ font: 'bootstrap-icons',
color: 'default'
});
diff --git a/src/plugins/bt-checkbox/plugin.scss b/src/plugins/bt-checkbox/plugin.scss
index 324f610f..22e21eed 100644
--- a/src/plugins/bt-checkbox/plugin.scss
+++ b/src/plugins/bt-checkbox/plugin.scss
@@ -1,12 +1,10 @@
-.query-builder.bt-checkbox-glyphicons {
- .checkbox input[type='checkbox']:checked + label::after {
- font-family: 'Glyphicons Halflings';
- content: '\e013';
+.query-builder.bt-checkbox-bootstrap-icons {
+ .checkbox input[type='checkbox'] + label::before {
+ outline: 0;
}
- .checkbox label::after {
- padding-left: 4px;
- padding-top: 2px;
- font-size: 9px;
+ .checkbox input[type='checkbox']:checked + label::after {
+ font-family: 'bootstrap-icons';
+ content: '\F633'; // https://icons.getbootstrap.com/icons/check-lg/
}
}
diff --git a/src/plugins/bt-selectpicker/plugin.js b/src/plugins/bt-selectpicker/plugin.js
deleted file mode 100644
index d9ef2812..00000000
--- a/src/plugins/bt-selectpicker/plugin.js
+++ /dev/null
@@ -1,46 +0,0 @@
-/**
- * @class BtSelectpicker
- * @memberof module:plugins
- * @descriptioon Applies Bootstrap Select on filters and operators combo-boxes.
- * @param {object} [options]
- * @param {string} [options.container='body']
- * @param {string} [options.style='btn-inverse btn-xs']
- * @param {int|string} [options.width='auto']
- * @param {boolean} [options.showIcon=false]
- * @throws MissingLibraryError
- */
-QueryBuilder.define('bt-selectpicker', function(options) {
- if (!$.fn.selectpicker || !$.fn.selectpicker.Constructor) {
- Utils.error('MissingLibrary', 'Bootstrap Select is required to use "bt-selectpicker" plugin. Get it here: http://silviomoreto.github.io/bootstrap-select');
- }
-
- var Selectors = QueryBuilder.selectors;
-
- // init selectpicker
- this.on('afterCreateRuleFilters', function(e, rule) {
- rule.$el.find(Selectors.rule_filter).removeClass('form-control').selectpicker(options);
- });
-
- this.on('afterCreateRuleOperators', function(e, rule) {
- rule.$el.find(Selectors.rule_operator).removeClass('form-control').selectpicker(options);
- });
-
- // update selectpicker on change
- this.on('afterUpdateRuleFilter', function(e, rule) {
- rule.$el.find(Selectors.rule_filter).selectpicker('render');
- });
-
- this.on('afterUpdateRuleOperator', function(e, rule) {
- rule.$el.find(Selectors.rule_operator).selectpicker('render');
- });
-
- this.on('beforeDeleteRule', function(e, rule) {
- rule.$el.find(Selectors.rule_filter).selectpicker('destroy');
- rule.$el.find(Selectors.rule_operator).selectpicker('destroy');
- });
-}, {
- container: 'body',
- style: 'btn-inverse btn-xs',
- width: 'auto',
- showIcon: false
-});
diff --git a/src/plugins/bt-tooltip-errors/plugin.js b/src/plugins/bt-tooltip-errors/plugin.js
index 68423252..52f4830d 100644
--- a/src/plugins/bt-tooltip-errors/plugin.js
+++ b/src/plugins/bt-tooltip-errors/plugin.js
@@ -7,8 +7,9 @@
* @throws MissingLibraryError
*/
QueryBuilder.define('bt-tooltip-errors', function(options) {
- if (!$.fn.tooltip || !$.fn.tooltip.Constructor || !$.fn.tooltip.Constructor.prototype.fixTitle) {
- Utils.error('MissingLibrary', 'Bootstrap Tooltip is required to use "bt-tooltip-errors" plugin. Get it here: http://getbootstrap.com');
+ if (! typeof bootstrap.Tooltip === "function") {
+ alert(typeof bootstrap.Tooltip );
+ Utils.error('MissingLibrary', 'Bootstrap Popper is required to use "bt-tooltip-errors" plugin. Get it here: http://getbootstrap.com');
}
var self = this;
@@ -16,7 +17,7 @@ QueryBuilder.define('bt-tooltip-errors', function(options) {
// add BT Tooltip data
this.on('getRuleTemplate.filter getGroupTemplate.filter', function(h) {
var $h = $($.parseHTML(h.value));
- $h.find(QueryBuilder.selectors.error_container).attr('data-toggle', 'tooltip');
+ $h.find(QueryBuilder.selectors.error_container).attr('data-bs-toggle', 'tooltip');
h.value = $h.prop('outerHTML');
});
@@ -24,9 +25,7 @@ QueryBuilder.define('bt-tooltip-errors', function(options) {
this.model.on('update', function(e, node, field) {
if (field == 'error' && self.settings.display_errors) {
node.$el.find(QueryBuilder.selectors.error_container).eq(0)
- .tooltip(options)
- .tooltip('hide')
- .tooltip('fixTitle');
+ .attr('data-bs-original-title',options).attr('data-bs-title',options).tooltip();
}
});
}, {
diff --git a/src/plugins/filter-description/plugin.js b/src/plugins/filter-description/plugin.js
index 472dd328..3027e761 100644
--- a/src/plugins/filter-description/plugin.js
+++ b/src/plugins/filter-description/plugin.js
@@ -3,7 +3,7 @@
* @memberof module:plugins
* @description Provides three ways to display a description about a filter: inline, Bootsrap Popover or Bootbox.
* @param {object} [options]
- * @param {string} [options.icon='glyphicon glyphicon-info-sign']
+ * @param {string} [options.icon='bi-info-circle-fill']
* @param {string} [options.mode='popover'] - inline, popover or bootbox
* @throws ConfigError
*/
@@ -43,30 +43,28 @@ QueryBuilder.define('filter-description', function(options) {
if (!description) {
$b.hide();
- if ($b.data('bs.popover')) {
+ if ($b.data('bs-popover')) {
$b.popover('hide');
}
}
else {
if ($b.length === 0) {
- $b = $($.parseHTML(''));
+ $b = $($.parseHTML(''));
$b.prependTo(rule.$el.find(QueryBuilder.selectors.rule_actions));
-
- $b.popover({
+ const popover = new bootstrap.Popover($b.get(0), {
placement: 'left',
container: 'body',
html: true
- });
-
+ })
$b.on('mouseout', function() {
- $b.popover('hide');
+ popover('hide');
});
}
else {
$b.css('display', '');
}
- $b.data('bs.popover').options.content = description;
+ $b.data('bs-popover').options.content = description;
if ($b.attr('aria-describedby')) {
$b.popover('show');
@@ -89,7 +87,7 @@ QueryBuilder.define('filter-description', function(options) {
}
else {
if ($b.length === 0) {
- $b = $($.parseHTML(''));
+ $b = $($.parseHTML(''));
$b.prependTo(rule.$el.find(QueryBuilder.selectors.rule_actions));
$b.on('click', function() {
@@ -105,7 +103,7 @@ QueryBuilder.define('filter-description', function(options) {
});
}
}, {
- icon: 'glyphicon glyphicon-info-sign',
+ icon: 'bi-info-circle-fill',
mode: 'popover'
});
diff --git a/src/plugins/invert/plugin.js b/src/plugins/invert/plugin.js
index c0294e84..8b0ab7ef 100644
--- a/src/plugins/invert/plugin.js
+++ b/src/plugins/invert/plugin.js
@@ -3,7 +3,7 @@
* @memberof module:plugins
* @description Allows to invert a rule operator, a group condition or the entire builder.
* @param {object} [options]
- * @param {string} [options.icon='glyphicon glyphicon-random']
+ * @param {string} [options.icon='bi-shuffle']
* @param {boolean} [options.recursive=true]
* @param {boolean} [options.invert_rules=true]
* @param {boolean} [options.display_rules_button=false]
@@ -33,7 +33,7 @@ QueryBuilder.define('invert', function(options) {
this.on('getGroupTemplate.filter', function(h) {
var $h = $($.parseHTML(h.value));
$h.find(Selectors.condition_container).after(
- '' +
+ '' +
' ' + self.translate('invert') +
''
);
@@ -44,7 +44,7 @@ QueryBuilder.define('invert', function(options) {
this.on('getRuleTemplate.filter', function(h) {
var $h = $($.parseHTML(h.value));
$h.find(Selectors.rule_actions).prepend(
- '' +
+ '' +
' ' + self.translate('invert') +
''
);
@@ -53,7 +53,7 @@ QueryBuilder.define('invert', function(options) {
}
}
}, {
- icon: 'glyphicon glyphicon-random',
+ icon: 'bi-shuffle',
recursive: true,
invert_rules: true,
display_rules_button: false,
diff --git a/src/plugins/not-group/plugin.js b/src/plugins/not-group/plugin.js
index 9c015149..be98bb00 100644
--- a/src/plugins/not-group/plugin.js
+++ b/src/plugins/not-group/plugin.js
@@ -3,8 +3,8 @@
* @memberof module:plugins
* @description Adds a "Not" checkbox in front of group conditions.
* @param {object} [options]
- * @param {string} [options.icon_checked='glyphicon glyphicon-checked']
- * @param {string} [options.icon_unchecked='glyphicon glyphicon-unchecked']
+ * @param {string} [options.icon_checked='bi-check2-square']
+ * @param {string} [options.icon_unchecked='bi-square']
*/
QueryBuilder.define('not-group', function(options) {
var self = this;
@@ -34,7 +34,7 @@ QueryBuilder.define('not-group', function(options) {
this.on('getGroupTemplate.filter', function(h) {
var $h = $($.parseHTML(h.value));
$h.find(QueryBuilder.selectors.condition_container).prepend(
- '' +
+ '' +
' ' + self.translate('NOT') +
''
);
@@ -112,8 +112,8 @@ QueryBuilder.define('not-group', function(options) {
e.value.not = !!data.not;
});
}, {
- icon_unchecked: 'glyphicon glyphicon-unchecked',
- icon_checked: 'glyphicon glyphicon-check',
+ icon_unchecked: 'bi-square',
+ icon_checked: 'bi-check2-square',
disable_template: false
});
diff --git a/src/plugins/sortable/plugin.js b/src/plugins/sortable/plugin.js
index 1eeb9dab..84b29e1f 100644
--- a/src/plugins/sortable/plugin.js
+++ b/src/plugins/sortable/plugin.js
@@ -5,7 +5,7 @@
* @param {object} [options]
* @param {boolean} [options.inherit_no_drop=true]
* @param {boolean} [options.inherit_no_sortable=true]
- * @param {string} [options.icon='glyphicon glyphicon-sort']
+ * @param {string} [options.icon='bi-sort-down']
* @throws MissingLibraryError, ConfigError
*/
QueryBuilder.define('sortable', function(options) {
@@ -177,7 +177,7 @@ QueryBuilder.define('sortable', function(options) {
}, {
inherit_no_sortable: true,
inherit_no_drop: true,
- icon: 'glyphicon glyphicon-sort',
+ icon: 'bi-sort-down',
disable_template: false
});
diff --git a/src/scss/default.scss b/src/scss/default.scss
index bc0a4524..9091634c 100644
--- a/src/scss/default.scss
+++ b/src/scss/default.scss
@@ -109,12 +109,6 @@ $ticks-position: 5px, 10px !default;
display: block;
}
}
-
- select,
- input[type='text'],
- input[type='number'] {
- padding: 1px;
- }
}
// ERRORS
diff --git a/src/template.js b/src/template.js
index 036d4e94..219aa06e 100644
--- a/src/template.js
+++ b/src/template.js
@@ -2,24 +2,24 @@ QueryBuilder.templates.group = ({ group_id, level, conditions, icons, settings,
return `