WIP: ES6 module conversion and webpack refactoring

- Convert all IIFE modules to ES6 modules with attach functions
- Split webpack configs: lib build vs demo build
- Add UMD wrapper for auto-initialization with jQuery
- Update package.json with sequential build scripts
- Clean up legacy dist files and reorganize demo structure

Status: jQuery timing issues remain - attach functions not accessible
Next: Debug UMD factory execution and jQuery parameter passing
This commit is contained in:
Micha
2025-07-31 14:38:37 +02:00
parent 09358eaaf6
commit 196db8febb
43 changed files with 2044 additions and 5679 deletions

View File

@@ -1,195 +0,0 @@
function getFiles() {
//directories
var
lib = 'src/',
forms = lib+'editable-form/',
inputs = lib+'inputs/',
containers = lib+'containers/';
//config for Bootstrap 5 only
var config = {
bootstrap5: {
filePrefix: 'bootstrap', //to have bootstrap-editable.js instead of bootstrap5-editable
form: [forms+'editable-form-bootstrap5.js'],
container: [containers+'editable-popover5.js'],
inputs: [
// Bootstrap-datepicker now loaded from npm, not bundled
inputs+'date/date.js',
inputs+'date/datefield.js'
],
css: [
// Bootstrap-datepicker CSS now loaded from npm, not bundled
]
}
};
//common js files
var js = [
forms+'editable-form.js',
forms+'editable-form-utils.js',
containers+'editable-container.js',
containers+'editable-inline.js',
lib+'element/editable-element.js',
inputs+'abstract.js',
inputs+'list.js',
inputs+'text.js',
inputs+'textarea.js',
inputs+'select.js',
inputs+'select2/select2.js',
inputs+'checklist.js',
inputs+'html5types.js'
];
//common css files
var css = [
forms+'editable-form.css',
containers+'editable-container.css',
lib+'element/editable-element.css'
];
//create 'concat' and 'uglify' tasks
var task, folder, dest, concat_files = {}, min_files = {};
for(var k in config) {
folder = '<%= dist %>/'+k+'-editable/';
var prefix = config[k].filePrefix || k;
//js
task = k+'_js';
dest = folder+'js/'+prefix+'-editable'+ (k === 'jquery' ? '-poshytip' : '');
concat_files[task] = {
src: js.concat(config[k].form).concat(config[k].container).concat(config[k].inputs),
dest: dest+'.js'
};
min_files[task] = {
src: ['<%= concat.'+task+'.dest %>'],
dest: dest + '.min.js'
};
//css
concat_files[k+'_css'] = {
src: css.concat(config[k].css),
dest: folder+'css/'+prefix+'-editable.css'
};
}
return {concat_files: concat_files, min_files: min_files};
}
/*global module:false*/
module.exports = function(grunt) {
grunt.util.linefeed = '\n';
grunt.loadNpmTasks('grunt-contrib-clean');
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-uglify');
grunt.loadNpmTasks('grunt-contrib-qunit');
grunt.loadNpmTasks('grunt-contrib-connect');
grunt.loadNpmTasks('grunt-contrib-jshint');
grunt.loadNpmTasks('grunt-contrib-copy');
//grunt.loadNpmTasks('grunt-contrib-requirejs');
//module for testing
var module = '';
// module = '&module=textarea';
//module = '&module=select';
//module = '&module=text';
//get js and css for different builds
var files = getFiles();
var banner = '/*! <%= pkg.title || pkg.name %> - v<%= pkg.version %> \n' +
'* <%= pkg.description %>\n' +
'* <%= pkg.homepage %>\n' +
'* Copyright (c) <%= grunt.template.today("yyyy") %> <%= pkg.author.name %>;' +
' Licensed <%= _.map(pkg.licenses, "type").join(", ") %> */\n';
files.concat_files.options = {banner: banner};
files.min_files.options = {banner: banner};
// Project configuration.
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
dist: 'dist',
// clean: ['<%= dist %>'],
concat: files.concat_files,
uglify: files.min_files,
qunit: {
bootstrap5: {
options: {
urls: [
'http://localhost:8000/test/index.html?f=bs5&c=popup'+module,
'http://localhost:8000/test/index.html?f=bs5&c=inline'+module
]
}
}
},
connect: {
server: {
port: 8000,
base: '.'
}
},
jshint: {
options: {
esversion: 6,
curly: true,
eqeqeq: true,
immed: true,
latedef: true,
newcap: true,
noarg: true,
sub: true,
undef: true,
boss: true,
eqnull: true,
browser: true,
evil: false,
globals: {
jQuery: true,
console: true
},
},
js: [ 'Gruntfile.js',
'src/editable-form/*.js',
'src/containers/*.js',
'src/element/*.js',
'src/inputs/*.js',
'src/inputs/date/*.js'
]
},
copy: {
dist: {
files: [
//image
{expand: true, flatten: true, dest: '<%= dist %>/bootstrap5-editable/img/', src: 'src/img/*'},
//licences
{expand: true, flatten: true, dest: '<%= dist %>/', src: ['LICENSE-MIT', 'README.md', 'CHANGELOG.txt']}
]
}
}
});
//test task
grunt.registerTask('test', ['jshint', 'connect', 'qunit:bootstrap5']);
// Default task.
grunt.registerTask('default', ['jshint', 'concat', 'uglify', 'copy']);
// alive server
grunt.registerTask('server', 'connect:server:keepalive');
// build
grunt.registerTask('build', ['jshint', 'concat', 'uglify', 'copy']);
//to run particular task use ":", e.g. copy:libs
};

View File

Before

Width:  |  Height:  |  Size: 509 B

After

Width:  |  Height:  |  Size: 509 B

View File

Before

Width:  |  Height:  |  Size: 1.8 KiB

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@@ -1,7 +1,9 @@
import $ from 'jquery';
// Ensure jQuery is available globally before any other imports
// Ensure jQuery is available globally before importing x-editable
window.$ = window.jQuery = $;
global.$ = global.jQuery = $;
if (typeof global !== 'undefined') {
global.$ = global.jQuery = $;
}
import "bootstrap"
import "bootstrap/dist/css/bootstrap.min.css"
@@ -11,15 +13,15 @@ import "bootstrap-icons/font/bootstrap-icons.min.css"
import "bootstrap-datepicker";
import "bootstrap-datepicker/dist/css/bootstrap-datepicker.min.css";
// Import the editable functionality (attaches to jQuery.fn) - using built distribution
// When using built files, you need to include select2 separately for select2 inputs
// Import select2 before x-editable
import "select2";
import "select2/dist/css/select2.min.css";
import '../dist/bootstrap5-editable/js/bootstrap-editable.min.js'
import '../dist/bootstrap5-editable/css/bootstrap-editable.css'
$.fn.editable.defaults.mode = 'inline';
// Import the editable functionality - should be synchronous
import 'dist/bootstrap5-editable/js/bootstrap-editable.js'
import 'dist/bootstrap5-editable/css/bootstrap-editable.css'
// $.fn.editable.defaults.mode = 'inline';
$(function() {

BIN
demo/dist/240c0c6464de0b4bf116.png vendored Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 509 B

BIN
demo/dist/56d4c7ce2d3591a02107.gif vendored Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

1307
demo/dist/app.js vendored Normal file

File diff suppressed because one or more lines are too long

BIN
demo/dist/fonts/bootstrap-icons.woff vendored Normal file

Binary file not shown.

BIN
demo/dist/fonts/bootstrap-icons.woff2 vendored Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -7,7 +7,7 @@
<link rel="stylesheet" href="./dist/bootstrap5-editable/css/bootstrap-editable.css">
<!-- <script src="./dist/bootstrap5-editable/js/bootstrap-editable.js"></script>-->
<!-- <script src="./dist/jquery.js"></script>-->
<script src="./dist/app.js" type="module"></script>
<script src="./demo/dist/app.js" type="module"></script>
<title>Bootstrap 5.3.3 Test</title>
</head>

237
dist/CHANGELOG.txt vendored
View File

@@ -1,237 +0,0 @@
X-editable changelog
=============================
Version 1.5.1 Nov 4, 2013
----------------------------
[enh #371] submit single field (vitalets)
[bug] select2: placeholder not shown if value initially empty (vitalets)
[enh #400] allow `validate` to change submitted value, also fix #354 (vitalets)
[enh #396] bs3 popover: placement `auto` (vitalets)
[bug #357] select2: tags mode with space separator (vitalets)
[bug #374] dateui: clear button does not submit (vitalets)
Version 1.5.0 Oct 1, 2013
----------------------------
[enh #362] add twitter typeahead.js (vitalets)
[enh] select: add `sourceOptions` to modify source request method and params (vitalets)
[enh #377] add bool option `escape` to allow html as content (vitalets)
[bug #344] fix determing empty for html content (vitalets)
[enh] update select2 to 3.4.3 (vitalets)
[enh #343] Bootstrap 3 support (vitalets)
Version 1.4.6 Aug 8, 2013
----------------------------
[bug #312] can't apply selector more than once (vitalets)
[enh #48] textarea: use `white-space: pre-wrap` instead of nl2br conversion (vitalets)
[enh #286] added HTML5 time input (Doggie52)
[enh] add `defaultValue` option (vitalets)
[enh #313] add composer support (masim)
[enh #300] Fix 'bootstrap popover falls off page if editable is too close to window edge' (belerweb)
[enh #302] allow data-datepicker and data-datetimepicker (vitalets)
[enh #287] add option to disable item in select (vitalets)
[enh #281] add collision flag to adjust tooltip position (vitalets)
[bug #279] fix jQuery UI tooltip z-index to be less than select2 dropdown (vitalets)
[bug #276] support id() and text() functions of select2 (vitalets)
Version 1.4.5 Jun 23, 2013
----------------------------
[enh #245] highlight element after update (vitalets)
[enh] select2 now works with ajax source (vitalets)
[bug] fix datefield (datetimefield) to return null for incorrect dates (vitalets)
[bug #224] do not close popup when it is saving value (vitalets)
[enh] added `submitValue` to `save` event params (vitalets)
[enh #259] allow `getValue` method to return value itself, not object (vitalets)
[enh] add `destroy` method to inputs (vitalets)
[enh #164] allow emptytext to be html (vitalets)
[enh #78] allow html in editable content (vitalets)
[enh] update container position when datetimepicker viewMode changes (vitalets)
[enh #255] remove xxxView options from first level config of datetimepicker (vitalets)
[enh] if `display` defined as function call it on init (vitalets)
[enh #218] sourceCache now disables cache totally (vitalets)
[bug #156] solve conflict of bootstrap datepicker and jQuery UI datepicker (vitalets)
[enh] update bootstrap-datepicker to 1.1.2 (vitalets)
[enh] allow follow links in disabled state (vitalets)
[enh] update combodate to 1.0.4, fix #222 (vitalets)
Version 1.4.4 May 4, 2013
----------------------------
[enh #219] added `error` callback (joekaiser)
[enh #198] new value of showbuttons: 'bottom' (vitalets)
[enh #192] add class editable-popup to have diferent css for popup and inline (vitalets)
[enh] update to bootstrap-datepicker 1.0.2 (vitalets)
[enh] update to combodate 1.0.3 with yearDescending and roundTime options (vitalets)
[enh] add 'use strict' directive (vitalets)
[enh #202] allow pk=0 (mdeweerd)
[enh #183] move datepicker icon to center of button (vitalets)
[enh] upgrade to select2 3.3.2 (vitalets)
[enh #176] update to bootstrap 2.3.1 (vitalets)
[bug #171] clear in date & datetime when showbuttons=false (vitalets)
[bug #166] clear button for input type=number (vitalets)
[bug #65] checklist don't show checked for single value (vitalets)
[enh #188] added bootstrap datetime (adeg, vitalets)
[bug] editable-poshytip on inline mode tries to write in $.Poshytip (vitalets)
Version 1.4.3 Mar 8, 2013
----------------------------
[bug #32] hotfix for jQuery UI 1.9+ (vitalets)
Version 1.4.2 Mar 7, 2013
----------------------------
[enh #132] combodate options can be defined via data-combodate json string (vitalets)
[enh] source defined as function now has scope of element and can return string used as url (vitalets)
[bug #99] select2 with Hierarchical Data (kev360)
[bug #81] wysihtml5: fix inserting image (vitalets)
[bug] remove $.browser from wysihtml5 input to support jQuery 1.9 (vitalets)
[bug #142] editable poshytip jquery 1.9+ compatibility (spiderpug)
[enh #126] Update bootstrap datepicker library and add minViewMode to options (kev360)
[enh #150] select2 with showbuttons = false (vitalets)
[bug #149] datepicker not shown when showbuttons = false (vitalets)
[bug #133] clear button incorect position due to parent line-height property (vitalets)
[bug #141] data-value ignored for empty elements (vitalets)
[bug #137] fix empty class for delegated element (vitalets)
[enh #121] add support of momentjs 2.0.0 in combodate (vitalets)
Version 1.4.1 Jan 18, 2013
----------------------------
[enh #62] new option `selector` to work with delegated targets (vitalets)
[enh] new option `unsavedclass` to set css class when value was not sent to server (vitalets)
[enh] new option `emptyclass` to set css class when element is empty (vitalets)
[enh #59] select2 input (vitalets)
[enh #17] typeahead input (vitalets)
[enh] select: support of OPTGROUP via `children` key in source (vitalets)
[enh] checklist: set checked via prop instead of attr (vitalets)
Version 1.4.0 Jan 11, 2013
----------------------------
[enh] added new input type: combodate (vitalets)
[bug #68] allow arrays for data attributes (adimitrov)
[enh] setValue method updates input if form is open (vitalets)
[enh] select: change source via option method, see #61 (vitalets)
[bug] select: source loaded twice if sourceCache = false (vitalets)
[enh] added `destroy` method, see #61 (vitalets)
[enh] textarea: added `rows` property (vitalets)
[enh #60] added wysihtml5 input (vitalets)
[enh] added IOS-style clear button for text inputs (vitalets)
[enh] date inputs changed in inline mode (vitalets)
[enh #51] popup/inline modes can be toggled via `mode` config option. No more *-inline.js versions of files (vitalets)
[enh] update bootstrap-datepicker to upstream (vitalets)
[enh] 'display' method: added param 'response' allowing to show text directly from server (vitalets)
[enh] new util method `$.fn.editableutils.itemsByValue` to easily get selected items for sourced-inputs (vitalets)
[enh] convert newlines to <br> in error message for more pretty display (vitalets)
[enh #57] remove css height for textarea (vitalets)
[enh] if new value for select is 'null' source should not load (vitalets)
[enh #53] 'name' no more appended to source defined as url (vitalets)
[enh #46] move 'img' dir outside 'css' (vitalets)
[enh #48] fix handling of newlines in textarea input (jmfontaine)
[enh #47] set select source to function (brianchance)
[bug] fix inline container move on next line in IE7 (vitalets)
Version 1.3.0 Dec 10, 2012
----------------------------
[enh] added html5 inputs support: password, email, url, tel, number, range (vitalets)
[bug #43] fix for bootstrap 2.2.2 (vitalets)
[enh #41] 'abstract' class renamed to 'abstractinput' as abstract is reserved word (vitalets)
[enh #40] 'params' option defined as function overwrites original ajax data instead of appending (vitalets)
[bug] datepicker: error when click on arrows after clear date (vitalets)
[enh] 'hidden' event: added possible value of reason param - 'nochange'. Occurs when form is submitted but value was not changed (vitalets)
[enh] 'submit' method changed: error-callback's parameter simplified (vitalets)
[enh] 'submit' method changed: now when response 200 OK it does not set pk automatically (vitalets)
[enh] 'submit' method changed: removed dataType='json'. Use 'ajaxOptions' to specify dataType if needed (vitalets)
[enh] removed default ajax dataType='json'. Use 'ajaxOptions' to specify dataType if needed (vitalets)
[enh] select: do not show 'sourceError' in element during autotext execution (vitalets)
Version 1.2.0 Dec 6, 2012
----------------------------
[enh #36] 'submit' method: added 'ajaxOptions' property to modify ajax request (vitalets)
[enh] inputs now internally use 'value2submit' method instead of previous 'value2str' (vitalets)
[enh] editableContainer removed from docs (vitalets)
[enh] editableContainer: removed 'autohide' option and 'cancel' event. Use 'hidden' event instead (vitalets)
[enh] 'hidden' event: added param 'reason' that points to reason caused hiding (vitalets)
[enh] 'select' submit by enter (vitalets)
[bug #37] fix incorrectly shown datepicker in jquery 1.7.1 + webkit (vitalets)
[enh] added url param 'jquery' to run tests in different versions of jquery, e.g. '&jquery=1.7.2' (vitalets)
[enh] 'enablefocus' option removed. More efficient to use 'save/hide' events to set focus to any element (vitalets)
[enh] 'init' event was added due to removal of render event (vitalets)
[enh] 'render' event was removed, use 'display' callback instead (vitalets)
[enh] 'checklist' submit value as array, not comma separated string (vitalets)
[enh] 'checklist' was refactored: options 'viewseparator', 'limit', 'limitText' are supressed by 'display' callback (vitalets)
[enh] new option: 'display' callback. Makes far more flexible rendering value into element's text. (vitalets)
[bug] fix typos (atrophic)
[enh] all callbacks scope changed to element (vitalets)
[enh] new option: 'savenochange' to save or cancel value when it was not changed in form (vitalets)
[enh] composite pk can be defined as JSON in data-pk attribute (vitalets)
[enh #30] new option 'sourceCache' true|false to disable cache for select (vitalets)
[bug #34] inputclass span* broken with fluid bootstrap layout. Classes changed to 'input-*'. (vitalets)
[enh] utils now added to $.fn.editableutils instead of $.fn.editableform.utils (vitalets)
[enh] input types now added to $.fn.editabletypes instead of $.fn.editableform.types (vitalets)
[enh] playground and tests now use requirejs (vitalets)
[bug #27] 'today' button toggle bug in bootstrap-datepicker (vitalets)
Version 1.1.1 Nov 30, 2012
----------------------------
[enh] 'showbuttons' option to hide buttons in form (vitalets)
[enh] object can be passed in 'option' method to set several options at once (vitalets)
[enh #20] toggle editable by 'dblclick' and 'mouseenter' (vitalets)
[enh] added 'inputs-ext' directory with sample input 'address'. They will not be concatenated to main files (vitalets)
[enh #13] 'onblur' option: to cancel, submit or ignore when user clicks outside the form (vitalets)
[enh] 'ajaxOptions' parameter for advanced ajax configuration (vitalets)
[enh] 'success' callback can return object to overwrite submitted value (vitalets)
Version 1.1.0 Nov 27, 2012
----------------------------
[enh #11] icon cancel changed to 'cross' (tarciozemel)
[enh] added support for IE7+ (vitalets)
[enh #9] 'name' or 'id' is not required anymore (vitalets)
[enh] 'clear' button added in date and dateui (vitalets)
[enh] form template changed: added DIV.editable-input, DIV.editable.buttons and $.fn.editableform.buttons (vitalets)
[enh] new input type: checklist (vitalets)
[enh] updated docs: inputs dropdown menu, global templates section (vitalets)
Version 1.0.1 Nov 22, 2012
----------------------------
[enh] contribution guide in README.md (vitalets)
[enh #7] 'shown', 'hidden' events added (vitalets)
[enh #1] params can be a function to calculate it dynamically (vitalets)
[enh #6] do not preventDefault() in click when toggle='manual'. This allows to have clickable links (vitalets)
[bug #3] should not mark element with unsave css if url is user's function (vitalets)
Version 1.0.0 Nov 19, 2012
----------------------------
Initial release. This library is new life of bootstrap-editable (1.1.4) that was strongly refactored and improved.
Main features:
- support not only bootstrap but any core library: bootstrap, jquery-ui or pure jquery
- different container classes to show form: popover, tooltip, poshytip, etc
- inline and popup versions
- new directory structure and logic in separate js files allowing easy contribution
It is not fully compatible with bootstrap-editable but has mainly the same interface and api.
Here list of differences to help you to upgrade your application:
[change] 'toggle' option value can be only click|manual (not toggling element id). In case of 'manual' you should write handler calling 'show' method.
[change] 'validate' option cannot be defined as object anymore.
[change] events 'init', 'update', 'shown', 'hidden' removed. Events 'save', 'cancel' added. Event 'render' remains.
[change] input's option 'template' renamed to 'tpl' (to exclude conflict with container's template).
[change] value can be stored internally as object (previously was always string). Useful for date input.
[change] 'error' callback option is removed. 'success' callback remained.
[enh] 'source' option in select can be array of structure [{value: 1, text: 'abc'}, {...}]. This allows to keep ordering of items in dropdown list. Previous format is supported for compatibility.
[enh] api method 'setValue' to set manually value of editable.
[change] locales directory is excluded from bootstrap-datepicker input. If you need localization you should jus download corresponding file from github.
[change] date and dateui specific options can be set only via 'datepicker' option in first level of config (previously it was possible to set some options directly in config, e.g. weekStart).
[change] if 'url' option defined as function - it is used as submit method instead of ajax (previously it was dynamically return url string and ajax occurred anyway)
Also all known bugs of bootstrap-editable were closed.

22
dist/LICENSE-MIT vendored
View File

@@ -1,22 +0,0 @@
Copyright (c) 2012 Vitaliy Potapov
Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without
restriction, including without limitation the rights to use,
copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following
conditions:
The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
OTHER DEALINGS IN THE SOFTWARE.

189
dist/README.md vendored
View File

@@ -1,189 +0,0 @@
# X-Editable (Bootstrap 5 Fork)
A drop-in replacement for legacy Bootstrap 3 x-editable projects, modernized for **Bootstrap 5** with jQuery support.
## Why This Fork?
This project was created when we needed a **drop-in replacement** for x-editable in a legacy Bootstrap 3 project. The original [vitalets/x-editable](https://github.com/vitalets/x-editable) library has not been actively maintained and doesn't support Bootstrap 5.
**Key Features:**
- **Bootstrap 5** compatibility
- **jQuery** support maintained
- **Select dropdowns** - fully functional
- **Select2 support** - advanced select with search/ajax
- **Date pickers** - using bootstrap-datepicker
- **Drop-in replacement** - minimal code changes needed
- **Streamlined codebase** - Bootstrap 5 only, legacy code removed
## Demo
The `/demo` folder contains working examples of the library in action.
**To run the demo:**
```bash
# In the project root directory
php -S 0.0.0.0:8000
# Then visit: http://localhost:8000/demo/
```
The demo showcases:
- Select inputs with AJAX and static data sources
- Select2 inputs with search functionality (requires select2 library)
- Date picker functionality
- Basic in-place editing
## Installation
### Via npm
```bash
npm install x-editable-bootstrap5
```
### Dependencies
This library automatically installs and requires:
- **Bootstrap 5** (CSS and JS)
- **jQuery 3.x**
- **bootstrap-datepicker** (for date inputs - included as dependency)
- **select2** (for select2 inputs - included as dependency)
### Quick Start
1. **Include the CSS and JS files:**
```html
<!-- Bootstrap 5 -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/css/bootstrap.min.css" rel="stylesheet">
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/js/bootstrap.bundle.min.js"></script>
<!-- jQuery -->
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<!-- Bootstrap Icons -->
<link href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.3/font/bootstrap-icons.min.css" rel="stylesheet">
<!-- Bootstrap Datepicker -->
<link href="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-datepicker/1.10.0/css/bootstrap-datepicker.min.css" rel="stylesheet">
<script src="https://cdnjs.cloudflare.com/ajax/libs/bootstrap-datepicker/1.10.0/js/bootstrap-datepicker.min.js"></script>
<!-- X-Editable Bootstrap 5 -->
<link href="dist/bootstrap5-editable/css/bootstrap-editable.css" rel="stylesheet">
<link href="dist/bootstrap5-editable/css/select2.min.css" rel="stylesheet">
<script src="dist/bootstrap5-editable/js/bootstrap-editable.js"></script>
```
**Or using npm/webpack:**
```javascript
import 'bootstrap/dist/css/bootstrap.min.css';
import 'bootstrap/dist/js/bootstrap.bundle.min.js';
import 'bootstrap-icons/font/bootstrap-icons.css';
import 'bootstrap-datepicker/dist/css/bootstrap-datepicker.min.css';
import 'bootstrap-datepicker/dist/js/bootstrap-datepicker.min.js';
import 'x-editable-bootstrap5/dist/bootstrap5-editable/css/bootstrap-editable.css';
import 'x-editable-bootstrap5/dist/bootstrap5-editable/css/select2.min.css';
import 'x-editable-bootstrap5/dist/bootstrap5-editable/js/bootstrap-editable.js';
```
2. **Initialize editable elements:**
```javascript
$('#my-editable').editable({
type: 'select',
source: [
{value: 1, text: 'Option 1'},
{value: 2, text: 'Option 2'}
],
url: '/update-endpoint'
});
```
## Select2 Support
This library includes built-in support for Select2 inputs, providing enhanced select functionality with search, AJAX loading, and more.
**Note:** Select2 is included as an npm dependency and will be automatically installed when you install x-editable-bootstrap5.
### Quick Select2 Setup
**Use select2 type in your editable:**
```javascript
$('#my-select2').editable({
type: 'select2',
source: [
{id: 'us', text: 'United States'},
{id: 'gb', text: 'Great Britain'},
{id: 'de', text: 'Germany'}
],
select2: {
placeholder: 'Select Country',
allowClear: true
},
url: '/update-endpoint'
});
```
### Select2 with AJAX
```javascript
$('#ajax-select2').editable({
type: 'select2',
select2: {
placeholder: 'Search countries...',
minimumInputLength: 2,
ajax: {
url: '/search-countries',
dataType: 'json',
data: function (term) {
return { query: term };
},
results: function (data) {
return { results: data };
}
}
},
url: '/update-endpoint'
});
```
## Migration from Bootstrap 3
If you're migrating from the original x-editable:
1. **Update Bootstrap** to version 5
2. **Replace x-editable files** with this Bootstrap 5 version (bootstrap-datepicker included as dependency)
3. **Update CSS classes** if using custom styling (Bootstrap 3 → 5 changes)
The JavaScript API remains largely the same, making it a true drop-in replacement.
## Build
To build the library from source:
```bash
# Install dependencies
npm install
# Build with Grunt
grunt build
# Or build with webpack for demo
npx webpack --mode=development
```
## Repository
**Main Repository:** [git.24unix.net/tracer/x-editable-bs5](https://git.24unix.net/tracer/x-editable-bs5)
**Mirrors:**
- GitHub: [github.com/24unix/x-editable-bs5](https://github.com/24unix/x-editable-bs5)
- GitLab: [gitlab.com/24unix/x-editable-bs5](https://gitlab.com/24unix/x-editable-bs5)
Development happens on the main repository at git.24unix.net, with mirrors automatically synced to GitHub and GitLab.
## License
This project maintains the same MIT license as the original x-editable project.
## Credits
- Original [x-editable](https://github.com/vitalets/x-editable) by [Vitaliy Potapov](https://github.com/vitalets)
- Bootstrap 5 modernization and maintenance by this fork

View File

@@ -1,7 +1,3 @@
/*! X-editable Bootstrap 5 - v25.0.7
* A maintained fork of x-editable for Bootstrap 5 support.
* https://git.24unix.net/tracer/x-editable
* Copyright (c) 2025 Micha Espey; Licensed MIT */
.editableform {
margin-bottom: 0; /* overwrites bootstrap margin */
}
@@ -239,70 +235,3 @@
display: inline-flex !important;
visibility: visible !important;
}
.editable-container.editable-popup {
max-width: none !important; /* without this rule poshytip/tooltip does not stretch */
}
.editable-container.popover {
width: auto; /* without this rule popover does not stretch */
}
.editable-container.editable-inline {
display: inline-block;
vertical-align: middle;
width: auto;
/* inline-block emulation for IE7*/
zoom: 1;
*display: inline;
}
.editable-container.ui-widget {
font-size: inherit; /* jqueryui widget font 1.1em too big, overwrite it */
z-index: 9990; /* should be less than select2 dropdown z-index to close dropdown first when click */
}
.editable-click,
a.editable-click,
a.editable-click:hover {
text-decoration: none;
border-bottom: dashed 1px #0088cc;
}
.editable-click.editable-disabled,
a.editable-click.editable-disabled,
a.editable-click.editable-disabled:hover {
color: #585858;
cursor: default;
border-bottom: none;
}
.editable-empty, .editable-empty:hover, .editable-empty:focus{
font-style: italic;
color: #DD1144;
/* border-bottom: none; */
text-decoration: none;
}
.editable-unsaved {
font-weight: bold;
}
.editable-unsaved:after {
/* content: '*'*/
}
.editable-bg-transition {
-webkit-transition: background-color 1400ms ease-out;
-moz-transition: background-color 1400ms ease-out;
-o-transition: background-color 1400ms ease-out;
-ms-transition: background-color 1400ms ease-out;
transition: background-color 1400ms ease-out;
}
/*see https://github.com/vitalets/x-editable/issues/139 */
.form-horizontal .editable
{
padding-top: 5px;
display:inline-block;
}

View File

@@ -1,237 +0,0 @@
.editableform {
margin-bottom: 0; /* overwrites bootstrap margin */
}
.editableform .control-group {
margin-bottom: 0; /* overwrites bootstrap margin */
white-space: nowrap; /* prevent wrapping buttons on new line */
line-height: 20px; /* overwriting bootstrap line-height. See #133 */
}
/*
BS3 fix: stop css from breaking when the form is inside a popup and inside a form with the class .form-horizontal
See: https://github.com/vitalets/x-editable/issues/682
*/
.form-horizontal .editable-popup .editableform .form-group {
margin-left:0;
margin-right:0;
}
/*
BS3 width:1005 for inputs breaks editable form in popup
See: https://github.com/vitalets/x-editable/issues/393
*/
.editableform .form-control {
width: auto;
}
.editable-buttons {
display: inline-block; /* should be inline to take effect of parent's white-space: nowrap */
vertical-align: top;
margin-left: 7px;
/* inline-block emulation for IE7*/
zoom: 1;
*display: inline;
}
.editable-buttons.editable-buttons-bottom {
display: block;
margin-top: 7px;
margin-left: 0;
}
.editable-input {
vertical-align: top;
display: inline-block; /* should be inline to take effect of parent's white-space: nowrap */
width: auto; /* bootstrap-responsive has width: 100% that breakes layout */
white-space: normal; /* reset white-space decalred in parent*/
/* display-inline emulation for IE7*/
zoom: 1;
*display: inline;
}
.editable-buttons .editable-cancel {
margin-left: 7px;
}
/*for jquery-ui buttons need set height to look more pretty*/
.editable-buttons button.ui-button-icon-only {
height: 24px;
width: 30px;
}
.editableform-loading {
background: url('../img/loading.gif') center center no-repeat;
height: 25px;
width: auto;
min-width: 25px;
}
.editable-inline .editableform-loading {
background-position: left 5px;
}
.editable-error-block {
max-width: 300px;
margin: 5px 0 0 0;
width: auto;
white-space: normal;
}
/*add padding for jquery ui*/
.editable-error-block.ui-state-error {
padding: 3px;
}
.editable-error {
color: red;
}
/* ---- For specific types ---- */
.editableform .editable-date {
padding: 0;
margin: 0;
float: left;
}
/* move datepicker icon to center of add-on button. See https://github.com/vitalets/x-editable/issues/183 */
.editable-inline .add-on .icon-th {
margin-top: 3px;
margin-left: 1px;
}
/* checklist vertical alignment */
.editable-checklist label input[type="checkbox"],
.editable-checklist label span {
vertical-align: middle;
margin: 0;
}
.editable-checklist label {
white-space: nowrap;
}
/* set exact width of textarea to fit buttons toolbar */
.editable-wysihtml5 {
width: 566px;
height: 250px;
}
/* clear button shown as link in date inputs */
.editable-clear {
clear: both;
font-size: 0.9em;
text-decoration: none;
text-align: right;
}
/* IOS-style clear button for text inputs */
.editable-clear-x {
background: url('../img/clear.png') center center no-repeat;
display: block;
width: 13px;
height: 13px;
position: absolute;
opacity: 0.6;
z-index: 100;
top: 50%;
right: 6px;
margin-top: -6px;
}
.editable-clear-x:hover {
opacity: 1;
}
.editable-pre-wrapped {
white-space: pre-wrap;
}
/* Position datepicker above input for datepicker-above class */
.datepicker-above .datepicker-inline {
position: absolute;
bottom: 100%;
left: 0;
right: 0;
z-index: 1000;
margin-bottom: 5px;
background: white;
border: 1px solid #dee2e6;
border-radius: 0.375rem;
box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.075);
}
/* Bootstrap 5 inline editing fixes */
.editable-inline .editableform {
display: inline-flex !important;
flex-direction: row !important;
align-items: center !important;
gap: 0.5rem !important;
flex-wrap: nowrap !important;
}
.editable-inline .editable-input {
flex-shrink: 1 !important;
min-width: 0 !important;
max-width: 200px !important; /* Prevent overly wide selects */
display: inline-block !important;
vertical-align: middle !important;
}
.editable-inline .editable-input select {
max-width: 100% !important;
min-width: 120px !important;
}
.editable-inline .editable-buttons {
flex-shrink: 0 !important;
margin-left: 0.5rem !important;
margin-top: 0 !important;
display: inline-flex !important;
align-items: center !important;
gap: 0.25rem !important;
vertical-align: middle !important;
}
.editable-inline .control-group {
white-space: nowrap !important;
display: inline-flex !important;
align-items: center !important;
}
/* Improve button styling for Bootstrap 5 */
.editable-buttons .btn {
padding: 0.25rem 0.5rem;
line-height: 1.2;
border-radius: 0.25rem;
}
.editable-buttons .btn-sm {
padding: 0.125rem 0.25rem;
font-size: 0.875rem;
}
/* Hide buttons initially for datepicker inputs - using discovered DOM structure */
/* Buttons are siblings to editable-input that contains datepicker */
.editable-input:has(.input-group.date) + .editable-buttons,
.editable-input:has(.input-group.datepicker-above) + .editable-buttons,
/* Buttons might be in same container as editable-input */
*:has(.editable-input .input-group.date) .editable-buttons,
*:has(.editable-input .input-group.datepicker-above) .editable-buttons {
display: none !important;
visibility: hidden !important;
}
/* Show buttons when they have the show-buttons class */
.editable-input:has(.input-group.date) + .editable-buttons.show-buttons,
.editable-input:has(.input-group.datepicker-above) + .editable-buttons.show-buttons,
*:has(.editable-input .input-group.date) .editable-buttons.show-buttons,
*:has(.editable-input .input-group.datepicker-above) .editable-buttons.show-buttons {
display: inline-flex !important;
visibility: visible !important;
}

File diff suppressed because one or more lines are too long

View File

@@ -1,29 +0,0 @@
/*!
* Bootstrap v5.3.3 (https://getbootstrap.com/)
* Copyright 2011-2024 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)
* Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)
*/
/*!
* Select2 4.1.0-rc.0
* https://select2.github.io
*
* Released under the MIT license
* https://github.com/select2/select2/blob/master/LICENSE.md
*/
/*!
* jQuery JavaScript Library v3.7.1
* https://jquery.com/
*
* Copyright OpenJS Foundation and other contributors
* Released under the MIT license
* https://jquery.org/license
*
* Date: 2023-08-28T13:37Z
*/
/**
* @license almond 0.3.3 Copyright jQuery Foundation and other contributors.
* Released under MIT license, http://github.com/requirejs/almond/LICENSE
*/

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

85
package-lock.json generated
View File

@@ -1,12 +1,12 @@
{
"name": "x-editable-bootstrap5",
"version": "25.0.5",
"version": "25.0.7",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "x-editable-bootstrap5",
"version": "25.0.5",
"version": "25.0.7",
"dependencies": {
"bootstrap": "^5.3.3",
"bootstrap-datepicker": "^1.10.0",
@@ -17,7 +17,6 @@
"devDependencies": {
"copy-webpack-plugin": "^13.0.0",
"css-loader": "^7.1.2",
"grunt": "^1.6.1",
"grunt-contrib-clean": "^2.0.1",
"grunt-contrib-concat": "^2.1.0",
"grunt-contrib-connect": "^5.0.1",
@@ -489,7 +488,8 @@
"resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz",
"integrity": "sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==",
"dev": true,
"license": "ISC"
"license": "ISC",
"peer": true
},
"node_modules/accepts": {
"version": "1.3.8",
@@ -623,6 +623,7 @@
"integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"sprintf-js": "~1.0.2"
}
@@ -633,6 +634,7 @@
"integrity": "sha512-zHjL5SZa68hkKHBFBK6DJCTtr9sfTCPCaph/L7tMSLcTFgy+zX7E+6q5UArbtOtMBCtxdICpfTCspRse+ywyXA==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -643,6 +645,7 @@
"integrity": "sha512-B1qMD3RBP7O8o0H2KbrXDyB0IccejMF15+87Lvlor12ONPRHP6gTjXMNkt/d3ZuOGbAe66hFmaCfECI24Ufp6w==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -862,6 +865,7 @@
"integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"fill-range": "^7.1.1"
},
@@ -1098,6 +1102,7 @@
"integrity": "sha512-ENwblkFQpqqia6b++zLD/KUWafYlVY/UNnAp7oz7LY7E924wmpye416wBOmvv/HMWzl8gL1kJlfvId/1Dg176w==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.1.90"
}
@@ -1316,6 +1321,7 @@
"integrity": "sha512-2P0p0pFGzHS5EMnhdxQi7aJN+iMheud0UhG4dlE1DLAlvL8JHjJJTX/CSm4JXwV0Ka5nGk3zC5mcb5bUQUxxMA==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": "*"
}
@@ -1382,6 +1388,7 @@
"integrity": "sha512-DtCOLG98P007x7wiiOmfI0fi3eIKyWiLTGJ2MDnVi/E04lWGbf+JzrRHMm0rgIIZJGtHpKpbVgLWHrv8xXpc3Q==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -1714,7 +1721,8 @@
"resolved": "https://registry.npmjs.org/eventemitter2/-/eventemitter2-0.4.14.tgz",
"integrity": "sha512-K7J4xq5xAD5jHsGM5ReWXRTFa3JRGofHiMcVgQ8PRwgWxzjHpMWCIzsmyf60+mh8KLsqYPcjUMa0AC4hd6lPyQ==",
"dev": true,
"license": "MIT"
"license": "MIT",
"peer": true
},
"node_modules/events": {
"version": "3.3.0",
@@ -1742,6 +1750,7 @@
"integrity": "sha512-A5EmesHW6rfnZ9ysHQjPdJRni0SRar0tjtG5MNtm9n5TUvsYU8oozprtRD4AqHxcZWWlVuAmQo2nWKfN9oyjTw==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"homedir-polyfill": "^1.0.1"
},
@@ -1754,7 +1763,8 @@
"resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz",
"integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==",
"dev": true,
"license": "MIT"
"license": "MIT",
"peer": true
},
"node_modules/extract-zip": {
"version": "2.0.1",
@@ -1882,6 +1892,7 @@
"integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"to-regex-range": "^5.0.1"
},
@@ -1928,6 +1939,7 @@
"integrity": "sha512-MzwXju70AuyflbgeOhzvQWAvvQdo1XL0A9bVvlXsYcFEBM87WR4OakL4OfZq+QRmr+duJubio+UtNQCPsVESzQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"detect-file": "^1.0.0",
"is-glob": "^4.0.3",
@@ -1944,6 +1956,7 @@
"integrity": "sha512-ZYDqPLGxDkDhDZBjZBb+oD1+j0rA4E0pXY50eplAAOPg2N/gUBSSk5IM1/QhPfyVo19lJ+CvXpqfvk+b2p/8Ng==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"expand-tilde": "^2.0.2",
"is-plain-object": "^2.0.3",
@@ -1961,6 +1974,7 @@
"integrity": "sha512-lNaHNVymajmk0OJMBn8fVUAU1BtDeKIqKoVhk4xAALB57aALg6b4W0MfJ/cUE0g9YBXy5XhSlPIpYIJ7HaY/3Q==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">= 0.10"
}
@@ -1981,6 +1995,7 @@
"integrity": "sha512-7EwmXrOjyL+ChxMhmG5lnW9MPt1aIeZEwKhQzoBUdTV0N3zuwWDZYVJatDvZ2OyzPUvdIAZDsCetk3coyMfcnQ==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -1991,6 +2006,7 @@
"integrity": "sha512-0OABksIGrxKK8K4kynWkQ7y1zounQxP+CWnyclVwj81KW3vlLlGUx57DKGcP/LH216GzqnstnPocF16Nxs0Ycg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"for-in": "^1.0.1"
},
@@ -2096,6 +2112,7 @@
"resolved": "https://registry.npmjs.org/getobject/-/getobject-1.0.2.tgz",
"integrity": "sha512-2zblDBaFcb3rB4rF77XVnuINOE2h2k/OnqXAiy0IrTxUfV1iFp3la33oAQVY9pCpWU268WFYVt2t71hlMuLsOg==",
"dev": true,
"peer": true,
"engines": {
"node": ">=10"
}
@@ -2149,6 +2166,7 @@
"integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"global-prefix": "^1.0.1",
"is-windows": "^1.0.1",
@@ -2164,6 +2182,7 @@
"integrity": "sha512-5lsx1NUDHtSjfg0eHlmYvZKv8/nVqX4ckFbM+FrGcQ+04KWcWFo9P5MxPZYSzUvyzmdTbI7Eix8Q4IbELDqzKg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"expand-tilde": "^2.0.2",
"homedir-polyfill": "^1.0.1",
@@ -2181,6 +2200,7 @@
"integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==",
"dev": true,
"license": "ISC",
"peer": true,
"dependencies": {
"isexe": "^2.0.0"
},
@@ -2202,6 +2222,7 @@
"integrity": "sha512-/ABUy3gYWu5iBmrUSRBP97JLpQUm0GgVveDCp6t3yRNIoltIYw7rEj3g5y1o2PGPR2vfTRGa7WC/LZHLTXnEzA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"dateformat": "~4.6.2",
"eventemitter2": "~0.4.13",
@@ -2230,6 +2251,7 @@
"integrity": "sha512-9Dtx/AhVeB4LYzsViCjUQkd0Kw0McN2gYpdmGYKtE2a5Yt7v1Q+HYZVWhqXc/kGnxlMtqKDxSwotiGeFmkrCoQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"grunt-known-options": "~2.0.0",
"interpret": "~1.1.0",
@@ -2250,6 +2272,7 @@
"integrity": "sha512-CvaGwVMztSMJLOeXPrez7fyfObdZqNUK1cPAEzLHrTybIua9pMdmmPR5YwtfNftIOMv3DPUhFaxsZMNTQO20Kg==",
"dev": true,
"license": "ISC",
"peer": true,
"dependencies": {
"abbrev": "1",
"osenv": "^0.1.4"
@@ -2445,6 +2468,7 @@
"integrity": "sha512-GD7cTz0I4SAede1/+pAbmJRG44zFLPipVtdL9o3vqx9IEyb7b4/Y3s7r6ofI3CchR5GvYJ+8buCSioDv5dQLiA==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -2455,6 +2479,7 @@
"integrity": "sha512-GHZQzZmhyq0u3hr7aHW4qUH0xDzwp2YXldLPZTCjlOeGscAOWWPftZG3XioW8MasGp+OBRIu39LFx14SLjXRcA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"colors": "~1.1.2",
"grunt-legacy-log-utils": "~2.1.0",
@@ -2471,6 +2496,7 @@
"integrity": "sha512-lwquaPXJtKQk0rUM1IQAop5noEpwFqOXasVoedLeNzaibf/OPWjKYvvdqnEHNmU+0T0CaReAXIbGo747ZD+Aaw==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"chalk": "~4.1.0",
"lodash": "~4.17.19"
@@ -2485,6 +2511,7 @@
"integrity": "sha512-2bQiD4fzXqX8rhNdXkAywCadeqiPiay0oQny77wA2F3WF4grPJXCvAcyoWUJV+po/b15glGkxuSiQCK299UC2w==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"async": "~3.2.0",
"exit": "~0.1.2",
@@ -2564,6 +2591,7 @@
"integrity": "sha512-eSmmWE5bZTK2Nou4g0AI3zZ9rswp7GRKoKXS1BLUkvPviOqs4YTN1djQIqrXy9k5gEtdLPy86JjRwsNM9tnDcA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"parse-passwd": "^1.0.0"
},
@@ -2725,6 +2753,7 @@
"integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"safer-buffer": ">= 2.1.2 < 3.0.0"
},
@@ -2827,14 +2856,16 @@
"resolved": "https://registry.npmjs.org/ini/-/ini-1.3.8.tgz",
"integrity": "sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==",
"dev": true,
"license": "ISC"
"license": "ISC",
"peer": true
},
"node_modules/interpret": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz",
"integrity": "sha512-CLM8SNMDu7C5psFCn6Wg/tgpj/bKAg7hc2gWqcuR9OD5Ft9PhBpIu8PLicPeis+xDd6YX2ncI8MCA64I9tftIA==",
"dev": true,
"license": "MIT"
"license": "MIT",
"peer": true
},
"node_modules/ip-address": {
"version": "9.0.5",
@@ -2863,6 +2894,7 @@
"integrity": "sha512-dOWoqflvcydARa360Gvv18DZ/gRuHKi2NU/wU5X1ZFzdYfH29nkiNZsF3mp4OJ3H4yo9Mx8A/uAGNzpzPN3yBA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"is-relative": "^1.0.0",
"is-windows": "^1.0.1"
@@ -2949,6 +2981,7 @@
"integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.12.0"
}
@@ -2982,6 +3015,7 @@
"integrity": "sha512-Kw/ReK0iqwKeu0MITLFuj0jbPAmEiOsIwyIXvvbfa6QfmN9pkD1M+8pdk7Rl/dTKbH34/XBFMbgD4iMJhLQbGA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"is-unc-path": "^1.0.0"
},
@@ -2995,6 +3029,7 @@
"integrity": "sha512-mrGpVd0fs7WWLfVsStvgF6iEJnbjDFZh9/emhRDcGWTduTfNHd9CHeUwH3gYIjdbwo4On6hunkztwOaAw0yllQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"unc-path-regex": "^0.1.2"
},
@@ -3008,6 +3043,7 @@
"integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3101,6 +3137,7 @@
"integrity": "sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"argparse": "^1.0.7",
"esprima": "^4.0.0"
@@ -3165,6 +3202,7 @@
"integrity": "sha512-yRHaiQDizWSzoXk3APcA71eOI/UuhEkNN9DiW2Tt44mhYzX4joFoCZlxsSOF7RyeLlfqzFLQI1ngFq3ggMPhOw==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"extend": "^3.0.2",
"findup-sync": "^4.0.0",
@@ -3185,6 +3223,7 @@
"integrity": "sha512-6jvvn/12IC4quLBL1KNokxC7wWTvYncaVUYSoxWw7YykPLuRrnv4qdHcSOywOI5RpkOVGeQRtWM8/q+G6W6qfQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"detect-file": "^1.0.0",
"is-glob": "^4.0.0",
@@ -3256,6 +3295,7 @@
"integrity": "sha512-pxiuXh0iVEq7VM7KMIhs5gxsfxCux2URptUQaXo4iZZJxBAzTPOLE2BumO5dbfVYq/hBJFBR/a1mFDmOx5AGmw==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"kind-of": "^6.0.2"
},
@@ -3269,6 +3309,7 @@
"integrity": "sha512-8y/eV9QQZCiyn1SprXSrCmqJN0yNRATe+PO8ztwqrvrbdRLA3eYJF0yaR0YayLWkMbsQSKWS9N2gPcGEc4UsZg==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3306,6 +3347,7 @@
"integrity": "sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"braces": "^3.0.3",
"picomatch": "^2.3.1"
@@ -3455,6 +3497,7 @@
"integrity": "sha512-4GUt3kSEYmk4ITxzB/b9vaIDfUVWN/Ml1Fwl11IlnIG2iaJ9O6WXZ9SrYM9NLI8OCBieN2Y8SWC2oJV0RQ7qYg==",
"dev": true,
"license": "ISC",
"peer": true,
"dependencies": {
"abbrev": "1"
},
@@ -3478,6 +3521,7 @@
"integrity": "sha512-c/K0mw/F11k4dEUBMW8naXUuBuhxRCfG7W+yFy8EcijU/rSmazOUd1XAEEe6bC0OuXY4HUKjTJv7xbxIMqdxrA==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"array-each": "^1.0.1",
"array-slice": "^1.0.0",
@@ -3494,6 +3538,7 @@
"integrity": "sha512-3+mAJu2PLfnSVGHwIWubpOFLscJANBKuB/6A4CxBstc4aqwQY0FWcsppuy4jU5GSB95yES5JHSI+33AWuS4k6w==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"for-own": "^1.0.0",
"make-iterator": "^1.0.0"
@@ -3508,6 +3553,7 @@
"integrity": "sha512-tqa/UMy/CCoYmj+H5qc07qvSL9dqcs/WZENZ1JbtWBlATP+iVOe778gE6MSijnyCnORzDuX6hU+LA4SZ09YjFQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"isobject": "^3.0.1"
},
@@ -3572,6 +3618,7 @@
"integrity": "sha512-B5JU3cabzk8c67mRRd3ECmROafjYMXbuzlwtqdM8IbS8ktlTix8aFGb2bAGKrSRIlnfKwovGUUr72JUPyOb6kQ==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3582,6 +3629,7 @@
"integrity": "sha512-D2FR03Vir7FIu45XBY20mTb+/ZSWB00sjU9jdQXt83gDrI4Ztz5Fs7/yy74g2N5SVQY4xY1qDr4rNddwYRVX0g==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3593,6 +3641,7 @@
"deprecated": "This package is no longer supported.",
"dev": true,
"license": "ISC",
"peer": true,
"dependencies": {
"os-homedir": "^1.0.0",
"os-tmpdir": "^1.0.0"
@@ -3715,6 +3764,7 @@
"integrity": "sha512-FwdRXKCohSVeXqwtYonZTXtbGJKrn+HNyWDYVcp5yuJlesTwNH4rsmRZ+GrKAPJ5bLpRxESMeS+Rl0VCHRvB2Q==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"is-absolute": "^1.0.0",
"map-cache": "^0.2.0",
@@ -3749,6 +3799,7 @@
"integrity": "sha512-1Y1A//QUXEZK7YKz+rD9WydcE1+EuPr6ZBgKecAB8tmoW6UFv0NREVJe1p+jRxtThkcbbKkfwIbWJe/IeE6m2Q==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3806,6 +3857,7 @@
"integrity": "sha512-QLcPegTHF11axjfojBIoDygmS2E3Lf+8+jI6wOVmNVenrKSo3mFdSGiIgdSHenczw3wPtlVMQaFVwGmM7BJdtg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"path-root-regex": "^0.1.0"
},
@@ -3819,6 +3871,7 @@
"integrity": "sha512-4GlJ6rZDhQZFE0DPVKh0e9jmZ5egZfxTkp7bcRDuPlJXbAwhxcl2dINPUAsjLdejqaLsCeg8axcLjIbvBjN4pQ==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -3843,6 +3896,7 @@
"integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=8.6"
},
@@ -4211,6 +4265,7 @@
"integrity": "sha512-/njmZ8s1wVeR6pjTZ+0nCnv8SpZNRMT2D1RLOJQESlYFDBvwpTA4KWJpZ+sBJ4+vhjILRcK7JIFdGCdxEAAitg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"resolve": "^1.9.0"
},
@@ -4295,6 +4350,7 @@
"integrity": "sha512-R7uiTjECzvOsWSfdM0QKFNBVFcK27aHOUwdvK53BcW8zqnGdYp0Fbj82cy54+2A4P2tFM22J5kRfe1R+lM/1yg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"expand-tilde": "^2.0.0",
"global-modules": "^1.0.0"
@@ -4339,7 +4395,8 @@
"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
"dev": true,
"license": "MIT"
"license": "MIT",
"peer": true
},
"node_modules/schema-utils": {
"version": "4.3.2",
@@ -4671,7 +4728,8 @@
"resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz",
"integrity": "sha512-D9cPgkvLlV3t3IzL0D0YLvGA9Ahk4PcvVwUbN0dSGr1aP0Nrt4AEnTUbuGvquEC0mA64Gqt1fzirlRs5ibXx8g==",
"dev": true,
"license": "BSD-3-Clause"
"license": "BSD-3-Clause",
"peer": true
},
"node_modules/statuses": {
"version": "1.5.0",
@@ -4950,6 +5008,7 @@
"integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"is-number": "^7.0.0"
},
@@ -5004,6 +5063,7 @@
"integrity": "sha512-eXL4nmJT7oCpkZsHZUOJo8hcX3GbsiDOa0Qu9F646fi8dT3XuSVopVqAcEiVzSKKH7UoDti23wNX3qGFxcW5Qg==",
"dev": true,
"license": "MIT",
"peer": true,
"engines": {
"node": ">=0.10.0"
}
@@ -5014,6 +5074,7 @@
"integrity": "sha512-VoC83HWXmCrF6rgkyxS9GHv8W9Q5nhMKho+OadDJGzL2oDYbYEppBaCMH6pFlwLeqj2QS+hhkw2kpXkSdD1JxQ==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"sprintf-js": "^1.1.1",
"util-deprecate": "^1.0.2"
@@ -5027,7 +5088,8 @@
"resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.1.3.tgz",
"integrity": "sha512-Oo+0REFV59/rz3gfJNKQiBlwfHaSESl1pcGyABQsnnIfWOFt6JNj5gCog2U6MLZ//IGYD+nA8nI+mTShREReaA==",
"dev": true,
"license": "BSD-3-Clause"
"license": "BSD-3-Clause",
"peer": true
},
"node_modules/undici-types": {
"version": "6.20.0",
@@ -5118,6 +5180,7 @@
"integrity": "sha512-mH8etigqMfiGWdeXpaaqGfs6BndypxusHHcv2qSHyZkGEznCd/qAXCWWRzeowtL54147cktFOC4P5y+kl8d8Jg==",
"dev": true,
"license": "MIT",
"peer": true,
"dependencies": {
"homedir-polyfill": "^1.0.1"
},

View File

@@ -42,10 +42,16 @@
"jquery": "^3.7.1",
"select2": "^4.1.0-rc.0"
},
"scripts": {
"build:lib": "webpack --mode development --config webpack.lib.js",
"build:demo": "webpack --mode development --config webpack.demo.js",
"dev": "npm run build:lib && npm run build:demo",
"watch": "webpack --mode development --watch",
"prod": "webpack --mode production"
},
"devDependencies": {
"copy-webpack-plugin": "^13.0.0",
"css-loader": "^7.1.2",
"grunt": "^1.6.1",
"grunt-contrib-clean": "^2.0.1",
"grunt-contrib-concat": "^2.1.0",
"grunt-contrib-connect": "^5.0.1",

View File

@@ -1,42 +1,62 @@
/*
X-Editable Bootstrap 5 - Complete Bundle
Uses npm bootstrap-datepicker instead of bundled version
Order matches Gruntfile.js for compatibility
Clean ES6 Module approach - all modules converted
*/
import $ from "jquery";
// Note: bootstrap-datepicker should be included separately by the user
// This bundle does not include bootstrap-datepicker to avoid dependency conflicts
import 'select2';
import 'select2/dist/css/select2.min.css';
// Import select2 from npm (JS + CSS)
import "select2";
import "select2/dist/css/select2.min.css";
// Ensure select2 is attached to window.jQuery if it exists
if (typeof window !== 'undefined' && window.jQuery && !window.jQuery.fn.select2) {
// Re-import select2 to ensure it attaches to global jQuery
require('select2');
}
// Core editable functionality - EXACT ORDER from Gruntfile
import "./editable-form/editable-form.js";
// Import all modules (functions will be available globally after import)
import "./editable-form/editable-form-utils.js";
import "./containers/editable-container.js";
import "./containers/editable-inline.js";
import "./element/editable-element.js";
import "./inputs/abstract.js";
import "./element/editable-element.js";
import "./inputs/list.js";
import "./inputs/text.js";
import "./inputs/textarea.js";
import "./inputs/select.js";
import "./inputs/select2/select2.js";
// Date input (now uses npm bootstrap-datepicker)
import "./inputs/date/date.js";
import "./inputs/date/datefield.js";
// Bootstrap 5 specific containers and forms
import "./editable-form/editable-form.js";
import "./containers/editable-container.js";
import "./containers/editable-inline.js";
import "./containers/editable-popover5.js";
import "./editable-form/editable-form-bootstrap5.js";
// Export jQuery for compatibility
export default $;
// Export initialization function - UMD will call this with jQuery
export default function initializeXEditable($) {
// UMD factory will pass jQuery as first parameter
if (!$ || !$.fn) {
console.error('x-editable: jQuery not found or invalid jQuery instance provided');
return;
}
console.log('x-editable build: Using jQuery version =', $.fn.jquery);
// Initialize x-editable synchronously in correct order
// Step 1: Attach foundational utilities
attachEditableUtils($);
attachAbstractInput($);
// Step 2: Attach all input types and containers
attachList($);
attachText($);
attachTextarea($);
attachSelect($);
attachSelect2($);
attachDate($);
attachDateField($);
attachEditableForm($);
attachEditableContainer($);
attachEditableInline($);
attachEditablePopover($);
attachEditableFormBootstrap($);
// Step 3: Finally attach the main editable functionality
attachEditable($);
console.log('x-editable build: Editable attached =', typeof $.fn.editable);
console.log('x-editable build: Select2 attached =', typeof $.fn.select2);
return $; // Return jQuery instance for chaining
}

View File

@@ -7,7 +7,7 @@
@class editableContainer
@uses editableform
**/
(function ($) {
function attachEditableContainer($) {
"use strict";
var Popup = function (element, options) {
@@ -518,4 +518,5 @@
}
};
}(window.jQuery));
return $;
}

View File

@@ -2,7 +2,7 @@
* Editable Inline
* ---------------------
*/
(function ($) {
function attachEditableInline($) {
"use strict";
//copy prototype from EditableContainer
@@ -51,4 +51,5 @@
}
});
}(window.jQuery));
return $;
}

View File

@@ -5,7 +5,7 @@
*/
import { Popover } from "bootstrap";
(function ($) {
function attachEditablePopover($) {
"use strict";
//extend methods
@@ -76,4 +76,5 @@ import { Popover } from "bootstrap";
}
});
}(window.jQuery));
return $;
}

View File

@@ -1,9 +1,7 @@
/*
Editableform based on Twitter Bootstrap 5
*/
import $ from "jquery";
(function ($) {
function attachEditableFormBootstrap5($) {
"use strict";
//store parent methods
@@ -57,4 +55,6 @@ import $ from "jquery";
$.fn.editableform.errorBlockClass = null;
//engine
$.fn.editableform.engine = 'bs5';
}(window.jQuery));
return $;
}

View File

@@ -1,7 +1,8 @@
/**
* EditableForm utilites
*/
(function ($) {
function attachEditableUtils($) {
"use strict";
//utils
@@ -246,4 +247,7 @@
}
};
}(window.jQuery));
// Return the jQuery object with attached utilities
return $;
}

View File

@@ -7,7 +7,7 @@ Editableform is linked with one of input types, e.g. 'text', 'select' etc.
@uses text
@uses textarea
**/
(function ($) {
function attachEditableForm($) {
"use strict";
var EditableForm = function (div, options) {
@@ -632,4 +632,6 @@ Editableform is linked with one of input types, e.g. 'text', 'select' etc.
//engine
$.fn.editableform.engine = 'jquery';
}(window.jQuery));
return $;
}

View File

@@ -4,7 +4,8 @@ Makes editable any HTML element on the page. Applied as jQuery method.
@class editable
@uses editableContainer
**/
(function ($) {
function attachEditable($) {
"use strict";
var Editable = function (element, options) {
@@ -72,6 +73,11 @@ Makes editable any HTML element on the page. Applied as jQuery method.
//attach handler activating editable. In disabled mode it just prevent default action (useful for links)
if(this.options.toggle !== 'manual') {
this.$element.addClass('editable-click');
// Debug: ensure toggle is set
if (!this.options.toggle) {
console.warn('Toggle option is undefined, defaulting to click');
this.options.toggle = 'click';
}
this.$element.on(this.options.toggle + '.editable', $.proxy(function(e){
//prevent following link if editable enabled
if(!this.options.disabled) {
@@ -858,4 +864,6 @@ Makes editable any HTML element on the page. Applied as jQuery method.
highlight: '#FFFF80'
};
}(window.jQuery));
// Return the jQuery object with attached editable functionality
return $;
}

View File

@@ -5,7 +5,8 @@ To create your own input you can inherit from this class.
@class abstractinput
**/
(function ($) {
function attachAbstractInput($) {
"use strict";
//types
@@ -217,4 +218,6 @@ To create your own input you can inherit from this class.
$.extend($.fn.editabletypes, {abstractinput: AbstractInput});
}(window.jQuery));
// Return the jQuery object with attached abstract input
return $;
}

View File

@@ -23,11 +23,10 @@ $(function(){
});
</script>
**/
(function ($) {
function attachDate($) {
"use strict";
var Date = function (options) {
console.log('Date input constructor called');
this.init('date', options, Date.defaults);
@@ -327,4 +326,5 @@ $(function(){
$.fn.editabletypes.date = Date;
}(window.jQuery));
return $;
}

View File

@@ -8,7 +8,7 @@ Automatically shown in inline mode.
@since 1.4.0
**/
(function ($) {
function attachDateField($) {
"use strict";
var DateField = function (options) {
@@ -192,4 +192,5 @@ Automatically shown in inline mode.
$.fn.editabletypes.datefield = DateField;
}(window.jQuery));
return $;
}

View File

@@ -4,7 +4,8 @@ List - abstract class for inputs that have source option loaded from js array or
@class list
@extends abstractinput
**/
(function ($) {
function attachList($) {
"use strict";
var List = function (options) {
@@ -333,4 +334,5 @@ List - abstract class for inputs that have source option loaded from js array or
$.fn.editabletypes.list = List;
}(window.jQuery));
return $;
}

View File

@@ -19,7 +19,7 @@ $(function(){
});
</script>
**/
(function ($) {
function attachSelect($) {
"use strict";
var Select = function (options) {
@@ -93,4 +93,5 @@ $(function(){
$.fn.editabletypes.select = Select;
}(window.jQuery));
return $;
}

View File

@@ -79,7 +79,7 @@ $(function(){
});
</script>
**/
(function ($) {
function attachSelect2($) {
"use strict";
var Constructor = function (options) {
@@ -357,4 +357,5 @@ $(function(){
$.fn.editabletypes.select2 = Constructor;
}(window.jQuery));
return $;
}

View File

@@ -15,7 +15,7 @@ $(function(){
});
</script>
**/
(function ($) {
function attachText($) {
"use strict";
var Text = function (options) {
@@ -131,4 +131,5 @@ $(function(){
$.fn.editabletypes.text = Text;
}(window.jQuery));
return $;
}

View File

@@ -16,7 +16,7 @@ $(function(){
});
</script>
**/
(function ($) {
function attachTextarea($) {
"use strict";
var Textarea = function (options) {
@@ -108,4 +108,5 @@ $(function(){
$.fn.editabletypes.textarea = Textarea;
}(window.jQuery));
return $;
}

14
src/umd-wrapper.js Normal file
View File

@@ -0,0 +1,14 @@
// UMD Wrapper for x-editable that auto-initializes with jQuery
import initializeXEditable from './bootstrap5-editable.js';
// The UMD pattern expects a factory function that receives dependencies
// This wrapper will be called by webpack's UMD template with jQuery as parameter
export default function xEditableFactory($) {
// Auto-initialize when called by UMD
if ($ && $.fn) {
return initializeXEditable($);
} else {
// Return the init function for manual use
return initializeXEditable;
}
}

View File

@@ -3,21 +3,21 @@ const CopyWebpackPlugin = require("copy-webpack-plugin");
const path = require("path");
module.exports = [
// Main bundle (jQuery, Bootstrap, App)
// Demo bundle (for demo only, not part of the library)
{
entry: {
jquery: "jquery",
app: "./demo/demo.js",
},
output: {
path: path.resolve(__dirname, "dist"), // Place them directly in dist/
filename: "[name].js", // app.js, jquery.js, bootstrap.js
path: path.resolve(__dirname, "demo/dist"), // Place in demo/dist folder
filename: "[name].js", // app.js
clean: true // Clean the demo/dist directory before emit
},
resolve: {
alias: {
jquery: path.resolve(__dirname, "node_modules/jquery"),
bootstrap: path.resolve(__dirname, "node_modules/bootstrap"),
"bootstrap5-editable": path.resolve(__dirname, "dist/bootstrap5-editable")
dist: path.resolve(__dirname, "dist")
}
},
module: {
@@ -34,32 +34,34 @@ module.exports = [
}
}
]
},
plugins: [
new webpack.ProvidePlugin({
$: "jquery",
jQuery: "jquery",
"window.jQuery": "jquery",
bootstrap: "bootstrap",
"window.bootstrap": "bootstrap"
}),
new CopyWebpackPlugin({
patterns: [
{ from: "src/editable-form/editable-form.css", to: path.resolve(__dirname, "dist/bootstrap5-editable/css") },
]
})
]
}
},
// X-Editable Plugin (Bootstrap 5)
{
entry: "./src/bootstrap5-editable.js",
output: {
path: path.resolve(__dirname, "dist/bootstrap5-editable/js"), // X-Editable stays here
path: path.resolve(__dirname, "dist/bootstrap5-editable/js"),
filename: "bootstrap-editable.js",
library: {
name: "EditableForm",
type: "umd"
},
globalObject: "this",
clean: true // Clean the output directory before emit
},
externals: {
jquery: {
commonjs: "jquery",
commonjs2: "jquery",
amd: "jquery",
root: "jQuery"
},
bootstrap: {
commonjs: "bootstrap",
commonjs2: "bootstrap",
amd: "bootstrap",
root: "bootstrap"
}
},
resolve: {
@@ -75,6 +77,20 @@ module.exports = [
use: ["style-loader", "css-loader"]
}
]
},
plugins: [
new CopyWebpackPlugin({
patterns: [
{
from: "src/editable-form/editable-form.css",
to: path.resolve(__dirname, "dist/bootstrap5-editable/css/bootstrap-editable.css")
},
{
from: "src/img",
to: path.resolve(__dirname, "dist/bootstrap5-editable/img")
}
]
})
]
}
];

35
webpack.demo.js Normal file
View File

@@ -0,0 +1,35 @@
const path = require("path");
// Demo bundle (for demo only, not part of the library)
module.exports = {
entry: {
app: "./demo/demo.js",
},
output: {
path: path.resolve(__dirname, "demo/dist"), // Place in demo/dist folder
filename: "[name].js", // app.js
clean: true // Clean the demo/dist directory before emit
},
resolve: {
alias: {
jquery: path.resolve(__dirname, "node_modules/jquery"),
bootstrap: path.resolve(__dirname, "node_modules/bootstrap"),
dist: path.resolve(__dirname, "dist")
}
},
module: {
rules: [
{
test: /\.css$/,
use: ["style-loader", "css-loader"]
},
{
test: /\.(woff|woff2|eot|ttf|svg)$/,
type: "asset/resource",
generator: {
filename: "fonts/[name][ext]"
}
}
]
}
};

68
webpack.lib.js Normal file
View File

@@ -0,0 +1,68 @@
const webpack = require("webpack");
const CopyWebpackPlugin = require("copy-webpack-plugin");
const path = require("path");
// X-Editable Plugin (Bootstrap 5) - Library build only
module.exports = {
entry: "./src/umd-wrapper.js",
output: {
path: path.resolve(__dirname, "dist/bootstrap5-editable/js"),
filename: "bootstrap-editable.js",
library: {
name: "EditableForm",
type: "umd",
export: 'default'
},
globalObject: "this",
clean: true, // Clean the output directory before emit
// Custom UMD template that auto-calls the exported function with jQuery
auxiliaryComment: {
root: "X-Editable Bootstrap 5 - Auto-initializing UMD Bundle",
commonjs: "X-Editable Bootstrap 5 - CommonJS",
commonjs2: "X-Editable Bootstrap 5 - CommonJS2",
amd: "X-Editable Bootstrap 5 - AMD"
}
},
externals: {
jquery: {
commonjs: "jquery",
commonjs2: "jquery",
amd: "jquery",
root: "jQuery"
},
bootstrap: {
commonjs: "bootstrap",
commonjs2: "bootstrap",
amd: "bootstrap",
root: "bootstrap"
}
},
resolve: {
alias: {
jquery: path.resolve(__dirname, "node_modules/jquery"),
bootstrap: path.resolve(__dirname, "node_modules/bootstrap")
}
},
module: {
rules: [
{
test: /\.css$/,
use: ["style-loader", "css-loader"]
}
]
},
plugins: [
new CopyWebpackPlugin({
patterns: [
{
from: "src/editable-form/editable-form.css",
to: path.resolve(__dirname, "dist/bootstrap5-editable/css/bootstrap-editable.css")
},
{
from: "src/img",
to: path.resolve(__dirname, "dist/bootstrap5-editable/img")
}
]
})
]
};