基于PHP+MySQL实现Bootstrap 3双向多选框互斥显示问题
Got it, let's build that two-way multi-select where options only appear in one box at a time. Here's a step-by-step solution tailored to your tech stack:
1. Split Your Data into Two Groups First
Before rendering the selects, separate your locations into available (not selected by the user) and selected (already assigned to the user). This makes rendering cleaner and avoids repeated checks:
// Split all active locations into available and selected arrays $selected_locations = []; $available_locations = []; foreach ($all_active_locations as $location) { // Check if this location is already in the user's selected rights $is_selected = in_array($location["location_id"], $user_location_rights_selected["selected_loc_id"]); if ($is_selected) { $selected_locations[] = $location; } else { $available_locations[] = $location; } }
2. Render the Bootstrap 3 UI
Use Bootstrap's grid and form classes to create a clean, responsive layout with two selects and move buttons:
<div class="container mt-4"> <form method="POST" action="your-save-script.php"> <div class="row"> <!-- Available Locations Box --> <div class="col-md-5"> <h4 class="mb-2">Available Locations</h4> <select name="available_locations[]" multiple="multiple" id="available-select" class="form-control" size="10" > <?php foreach ($available_locations as $loc): ?> <option value="<?= $loc["location_id"] ?>"> <?= htmlspecialchars($loc["location_name"]) ?> </option> <?php endforeach; ?> </select> </div> <!-- Move Buttons --> <div class="col-md-2 d-flex flex-column justify-content-center align-items-center"> <button type="button" id="move-right" class="btn btn-primary w-100 mb-2">>></button> <button type="button" id="move-left" class="btn btn-primary w-100"><<</button> </div> <!-- Selected Locations Box --> <div class="col-md-5"> <h4 class="mb-2">Selected Locations</h4> <select name="job_rights[]" multiple="multiple" id="selected-select" class="form-control" size="10" > <?php foreach ($selected_locations as $loc): ?> <option value="<?= $loc["location_id"] ?>"> <?= htmlspecialchars($loc["location_name"]) ?> </option> <?php endforeach; ?> </select> </div> </div> <!-- Submit Button --> <div class="mt-4"> <button type="submit" class="btn btn-success">Save Rights</button> </div> </form> </div>
3. Add JavaScript for Two-Way Interaction
This script handles moving items between boxes and ensures mutual exclusivity (an option can't exist in both boxes):
// Move selected items from available to selected document.getElementById('move-right').addEventListener('click', function() { const available = document.getElementById('available-select'); const selected = document.getElementById('selected-select'); // Get all selected options in the available box const selectedOpts = Array.from(available.selectedOptions); selectedOpts.forEach(opt => { // Move the option to the selected box selected.appendChild(opt); // Deselect it (optional, for better UX) opt.selected = false; }); }); // Move selected items from selected to available document.getElementById('move-left').addEventListener('click', function() { const available = document.getElementById('available-select'); const selected = document.getElementById('selected-select'); // Get all selected options in the selected box const selectedOpts = Array.from(selected.selectedOptions); selectedOpts.forEach(opt => { // Move the option back to available available.appendChild(opt); // Deselect it opt.selected = false; }); }); // Ensure all selected items are submitted (critical!) document.querySelector('form').addEventListener('submit', function() { const selectedBox = document.getElementById('selected-select'); // Select every option in the selected box so they're included in the form data Array.from(selectedBox.options).forEach(opt => opt.selected = true); });
4. Server-Side Handling (PHP)
When the form is submitted, you'll receive the job_rights[] array with all selected location IDs. Use this to update your MySQL database:
// In your-save-script.php if ($_SERVER['REQUEST_METHOD'] === 'POST') { // Get selected location IDs (default to empty array if none) $selected_ids = isset($_POST['job_rights']) ? array_map('intval', $_POST['job_rights']) : []; // Example: Update the user's rights in MySQL // Replace with your actual table/column names $user_id = 123; // Get current user ID from session // First, delete existing rights for the user $delete_stmt = $pdo->prepare("DELETE FROM user_location_rights WHERE user_id = ?"); $delete_stmt->execute([$user_id]); // Then insert the new selected rights if (!empty($selected_ids)) { $insert_query = "INSERT INTO user_location_rights (user_id, location_id) VALUES "; $values = []; foreach ($selected_ids as $loc_id) { $values[] = "($user_id, $loc_id)"; } $insert_query .= implode(', ', $values); $pdo->exec($insert_query); } // Redirect back or show success message header('Location: your-page.php'); exit; }
Key Notes:
- Mutual Exclusivity: Since we move options directly between boxes, an option can never be in both places at the same time.
- Security: Always use
htmlspecialchars()when outputting user/data to prevent XSS attacks. - Data Sanitization: Use prepared statements in MySQL to avoid SQL injection (the example uses PDO, adjust if you're using mysqli).
内容的提问来源于stack exchange,提问作者cijo

