A complete guide to using X-Editable with all supported input types, modes, and initialization methods.
This library provides in-place editing with Bootstrap 5. It converts elements into editable controls with validation support.
Version: 1.6.0 | Author: CashEncode | Last Updated: 2025-04-22
<!-- Basic Text Input -->
<a href="#"
id="basic-text"
data-editable="true"
data-type="text"
data-pk="1"
data-title="Enter text">
Click to edit
</a>
<!-- Email Input -->
<a href="#"
id="email-input"
data-editable="true"
data-type="email"
data-pk="1"
data-title="Enter email address">
user@example.com
</a>
<!-- Password Input -->
<a href="#"
id="password-input"
data-editable="true"
data-type="password"
data-pk="1"
data-title="Enter password">
••••••••
</a>
<!-- URL Input -->
<a href="#"
id="url-input"
data-editable="true"
data-type="url"
data-pk="1"
data-title="Enter URL">
https://example.com
</a>
<!-- Tel/Phone Input -->
<a href="#"
id="tel-input"
data-editable="true"
data-type="tel"
data-pk="1"
data-title="Enter phone number">
(123) 456-7890
</a>
<!-- Text with Required Validation -->
<a href="#"
id="text-required"
data-editable="true"
data-type="text"
data-pk="1"
data-title="Required field"
data-required="true">
Required text
</a>
<!-- Inline Text Input -->
<a href="#"
id="inline-text"
data-editable="true"
data-type="text"
data-pk="1"
data-mode="inline"
data-title="Enter text">
Click to edit inline
</a>
<!-- Inline Email Input -->
<a href="#"
id="inline-email"
data-editable="true"
data-type="email"
data-pk="1"
data-mode="inline"
data-title="Enter email">
user@example.com
</a>
<!-- Inline with Buttons -->
<a href="#"
id="inline-buttons"
data-editable="true"
data-type="text"
data-pk="1"
data-mode="inline"
data-showbuttons="true"
data-title="Edit with buttons">
Click to edit with buttons
</a>
<!-- Auto Submit on Blur -->
<a href="#"
id="inline-blur"
data-editable="true"
data-type="text"
data-pk="1"
data-mode="inline"
data-onblur="submit"
data-title="Submits when focus is lost">
Submits when focus is lost
</a>
<!-- Number Input -->
<a href="#"
id="number-input"
data-editable="true"
data-type="number"
data-pk="1"
data-title="Enter number"
data-min="0"
data-max="100">
42
</a>
<!-- Number with Step -->
<a href="#"
id="number-step"
data-editable="true"
data-type="number"
data-pk="1"
data-title="Enter number"
data-min="0"
data-max="10"
data-step="0.5">
2.5
</a>
<!-- Range Input -->
<a href="#"
id="range-input"
data-editable="true"
data-type="range"
data-pk="1"
data-title="Select range"
data-min="0"
data-max="100"
data-step="5">
75
</a>
<!-- Inline Range -->
<a href="#"
id="inline-range"
data-editable="true"
data-type="range"
data-pk="1"
data-mode="inline"
data-title="Select range"
data-min="0"
data-max="100"
data-step="1">
50
</a>
<!-- Time Input -->
<a href="#"
id="time-input"
data-editable="true"
data-type="time"
data-pk="1"
data-title="Enter time">
14:30
</a>
<!-- Inline Time -->
<a href="#"
id="inline-time"
data-editable="true"
data-type="time"
data-pk="1"
data-mode="inline"
data-title="Enter time">
09:15
</a>
<!-- Textarea Input -->
<a href="#"
id="textarea-input"
data-editable="true"
data-type="textarea"
data-pk="1"
data-title="Enter text">
This is a longer text that will be displayed in a textarea when editing. Click to edit.
</a>
<!-- Inline Textarea -->
<a href="#"
id="inline-textarea"
data-editable="true"
data-type="textarea"
data-pk="1"
data-mode="inline"
data-rows="3"
data-title="Edit text">
This is an inline textarea. It will appear right where this text is when you click to edit.
</a>
<!-- Select with Array Source -->
<a href="#"
id="select-array"
data-editable="true"
data-type="select"
data-pk="1"
data-title="Select option"
data-source='["Option 1", "Option 2", "Option 3"]'>
Option 1
</a>
<!-- Select with Object Source -->
<a href="#"
id="select-object"
data-editable="true"
data-type="select"
data-pk="1"
data-title="Select status"
data-source='{"A": "Active", "I": "Inactive", "P": "Pending"}'>
Active
</a>
<!-- Select with Prepend -->
<a href="#"
id="select-prepend"
data-editable="true"
data-type="select"
data-pk="1"
data-prepend="Choose option..."
data-title="Select with custom prepend"
data-source='[{"value": "1", "text": "Option 1"}, {"value": "2", "text": "Option 2"}, {"value": "3", "text": "Option 3"}]'>
Option 2
</a>
<!-- Inline Select -->
<a href="#"
id="inline-select"
data-editable="true"
data-type="select"
data-pk="1"
data-mode="inline"
data-title="Select option"
data-source='["Red", "Green", "Blue", "Yellow", "Purple"]'>
Blue
</a>
<!-- Select2 with Flat Data -->
<a href="#"
id="select2-flat"
data-editable="true"
data-type="select2"
data-pk="1"
data-title="Select country"
data-source='{"results": [
{"id": "US", "text": "United States"},
{"id": "CA", "text": "Canada"},
{"id": "UK", "text": "United Kingdom"},
{"id": "AU", "text": "Australia"},
{"id": "DE", "text": "Germany"},
{"id": "FR", "text": "France"},
{"id": "JP", "text": "Japan"},
{"id": "CN", "text": "China"},
{"id": "BR", "text": "Brazil"},
{"id": "IN", "text": "India"}
]}'>
United States
</a>
<!-- Select2 with Search -->
<a href="#"
id="select2-search"
data-editable="true"
data-type="select2"
data-pk="1"
data-title="Select city"
data-source='{"results": [
{"id": "New York", "text": "New York"},
{"id": "Los Angeles", "text": "Los Angeles"},
{"id": "Chicago", "text": "Chicago"},
{"id": "Houston", "text": "Houston"},
{"id": "Phoenix", "text": "Phoenix"},
{"id": "Philadelphia", "text": "Philadelphia"},
{"id": "San Antonio", "text": "San Antonio"},
{"id": "San Diego", "text": "San Diego"},
{"id": "Dallas", "text": "Dallas"},
{"id": "San Jose", "text": "San Jose"}
]}'>
Chicago
</a>
<!-- Select2 with Groups (Flat Format) -->
<a href="#"
id="select2-groups"
data-editable="true"
data-type="select2"
data-pk="1"
data-title="Select option"
data-source='[
{"value":"js","text":"JavaScript", "group": "Frontend"},
{"value":"ts","text":"TypeScript", "group": "Frontend"},
{"value":"react","text":"React", "group": "Frontend"},
{"value":"vue","text":"Vue.js", "group": "Frontend"},
{"value":"php","text":"PHP", "group": "Backend"},
{"value":"python","text":"Python", "group": "Backend"},
{"value":"ruby","text":"Ruby", "group": "Backend"},
{"value":"java","text":"Java", "group": "Backend"},
{"value":"csharp","text":"C#", "group": "Backend"}
]'>
JavaScript
</a>
<!-- Select2 with Groups (Grouped Format) -->
<a href="#"
id="select2-grouped"
data-editable="true"
data-type="select2"
data-pk="1"
data-title="Select option"
data-source='{"results":[
{"text":"Frontend","children":[
{"id":"js","text":"JavaScript"},
{"id":"ts","text":"TypeScript"},
{"id":"react","text":"React"}
]},
{"text":"Backend","children":[
{"id":"php","text":"PHP"},
{"id":"python","text":"Python"},
{"id":"ruby","text":"Ruby"}
]},
{"text":"Mobile","children":[
{"id":"swift","text":"Swift"},
{"id":"kotlin","text":"Kotlin"},
{"id":"flutter","text":"Flutter"}
]}
]}'>
JavaScript
</a>
results
array containing groups with children
options// Basic text input initialization
window.editable('#js-text', {
type: 'text',
pk: 1,
title: 'Enter text',
url: '/post', // Your server endpoint for saving data
success: function(response, newValue) {
console.log('Text updated:', newValue);
}
});
// Select initialization
window.editable('#js-select', {
type: 'select',
pk: 1,
title: 'Select role',
source: [
{value: 'admin', text: 'Administrator'},
{value: 'editor', text: 'Editor'},
{value: 'user', text: 'Regular User'}
],
value: 'admin'
});
// Textarea initialization
window.editable('#js-textarea', {
type: 'textarea',
pk: 1,
title: 'Edit content',
rows: 3,
mode: 'popup'
});
// Select2 with grouped data
window.editable('#js-select2', {
type: 'select2',
pk: 1,
title: 'Select technology',
source: {
results: [
{
text: 'Frontend',
children: [
{id: 'js', text: 'JavaScript'},
{id: 'ts', text: 'TypeScript'},
{id: 'react', text: 'React'}
]
},
{
text: 'Backend',
children: [
{id: 'php', text: 'PHP'},
{id: 'python', text: 'Python'},
{id: 'ruby', text: 'Ruby'}
]
}
]
},
value: 'js',
select2: {
// Additional Select2 options
minimumResultsForSearch: 5
}
});
// Custom validation
window.editable('#js-validation', {
type: 'text',
pk: 1,
title: 'Enter text (min 5 chars)',
validate: function(value) {
if(value.length < 5) {
return 'Text must be at least 5 characters';
}
}
});
// Custom display function
window.editable('#js-display', {
type: 'number',
pk: 1,
title: 'Enter price',
value: 199.99,
display: function(value) {
return '$' + parseFloat(value).toFixed(2);
}
});
// Success callback
window.editable('#js-success', {
type: 'text',
pk: 1,
title: 'Enter value',
url: '/post',
success: function(response, newValue) {
// Show a toast or alert with success message
alert('Value successfully updated to: ' + newValue);
// You can also return an object to override the new value
return {
newValue: newValue.toUpperCase()
};
}
});
// Event handling
const eventLog = document.querySelector('.event-log');
const logEvent = function(name, detail) {
const entry = document.createElement('div');
entry.textContent = `${name} event triggered`;
eventLog.prepend(entry);
// Limit number of log entries
if (eventLog.children.length > 5) {
eventLog.removeChild(eventLog.lastChild);
}
};
const el = document.getElementById('js-events');
window.editable('#js-events', {
type: 'text',
pk: 1,
title: 'Edit text'
});
// Listen for editable events
el.addEventListener('editable:show', function(e) {
logEvent('show', e.detail);
});
el.addEventListener('editable:hidden', function(e) {
logEvent('hidden', e.detail);
});
el.addEventListener('editable:save', function(e) {
logEvent('save', e.detail);
});
el.addEventListener('editable:init', function(e) {
logEvent('init', e.detail);
});
X-Editable properly handles modals by automatically detecting modal containers and setting appropriate Select2 dropdown parents.
<!-- Button to trigger modal -->
<button type="button" class="btn btn-primary" data-bs-toggle="modal" data-bs-target="#editableModal">
Open Modal with Editable Fields
</button>
<!-- Modal -->
<div class="modal fade" id="editableModal" tabindex="-1" aria-labelledby="editableModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="editableModalLabel">Edit User Information</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<form>
<div class="mb-3">
<label class="form-label">Name:</label>
<a href="#"
id="modal-name"
data-editable="true"
data-type="text"
data-pk="1"
data-title="Enter name">
John Doe
</a>
</div>
<div class="mb-3">
<label class="form-label">Role:</label>
<a href="#"
id="modal-role"
data-editable="true"
data-type="select2"
data-pk="1"
data-value="admin"
data-title="Select role"
data-source='{
"results": [
{
"text": "Management",
"children": [
{"id": "admin", "text": "Administrator"},
{"id": "manager", "text": "Manager"}
]
},
{
"text": "Users",
"children": [
{"id": "editor", "text": "Editor"},
{"id": "user", "text": "Regular User"},
{"id": "guest", "text": "Guest"}
]
}
]
}'>
Administrator
</a>
</div>
<div class="mb-3">
<label class="form-label">Biography:</label>
<a href="#"
id="modal-bio"
data-editable="true"
data-type="textarea"
data-pk="1"
data-title="Enter biography">
This is the user's biography. Click to edit.
</a>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Close</button>
<button type="button" class="btn btn-primary">Save changes</button>
</div>
</div>
</div>
</div>