如何用jQuery实现选择Tache后展示关联Technicien与Tarification的Ajax表格
Alright, let's tackle this modification step by step. The goal is to replace the chain of dropdowns (metier → tache → tarification → technicien) with a table that displays technicians and their corresponding tarification data as soon as a tache is selected. Here's how to do it:
First, in your InterventionController, we can trim down the data passed to the view since we'll fetch relevant tarification/technician data via AJAX. We'll keep the core collections needed for initial dropdowns:
public function create() { $client = Client::orderBy('id', 'asc')->get(); $metiers = Metier::orderBy('id', 'asc')->get(); return view('intervention.create') ->with('client', $client) ->with('metiers', $metiers); }
Note: I capitalized model names (like Client instead of client) to follow Laravel's PSR-4 naming conventions.
We need a route and controller method to fetch technicians paired with their tarification data for a selected tache. Add this to your InterventionController:
/** * Fetch technicians with their tarification data for a given tache */ public function getTechniciansWithTarificationByTache($tacheId) { // Get technicians who have tarification entries for this tache, with the relevant tarification data $technicians = Technicien::whereHas('tarificationtaches', function($query) use ($tacheId) { $query->where('tache_id', $tacheId); })->with(['tarificationtaches' => function($query) use ($tacheId) { $query->where('tache_id', $tacheId); }])->get(); return response()->json(['technicians' => $technicians]); }
Then add the corresponding route in web.php:
Route::get('/technicians-with-tarification/{tacheId}', [InterventionController::class, 'getTechniciansWithTarificationByTache'])->name('technicians.tarification.by.tache');
Now let's update the view to replace the old dropdowns with a dynamic table, and adjust the JavaScript logic.
Update the JavaScript Section
Replace the existing getTarificationsByTache and getTechniciensByTarificationtache functions with this new logic to load the table:
<script type="text/javascript"> var getTachesByMetierUrl = "{{url('/tachesbymetier')}}"; var getAdresseByClientUrl = "{{url('/adressebyclient')}}"; var getTechniciansWithTarificationUrl = "{{route('technicians.tarification.by.tache', '')}}"; // Keep your existing getAdresseByClient function unchanged function getAdresseByClient(val) { if(val.length>0) { var client_id = val; $.get(getAdresseByClientUrl+'/'+client_id,function(res) { var html = '<option value="">-Select-</option>' ; $.each(res.adresses,function(index,item) { html+='<option value="'+item.id+'">'+item.code_postal+'</option>'; }); $('#adresses').html(html); }); } } // Update getTachesByMetier to clear the table when switching metiers function getTachesByMetier(val) { if(val.length>0) { var metier_id = val; $.get(getTachesByMetierUrl+'/'+metier_id,function(res) { var html = '<option value="">-Select-</option>' ; $.each(res.taches,function(index,item) { html+='<option value="'+item.id+'">'+item.libelle_tache+'</option>'; }); $('#taches').html(html); // Clear table when changing metier $('#technicians-table-container').html(''); }); } else { $('#taches').html('<option value="">-Select-</option>'); $('#technicians-table-container').html(''); } } // New function to load technicians and their tarification data into a table function loadTechniciansWithTarification(val) { if(val.length>0) { var tache_id = val; $.get(getTechniciansWithTarificationUrl+'/'+tache_id, function(res) { if(res.technicians.length === 0) { $('#technicians-table-container').html('<p class="text-muted">No technicians found for this task.</p>'); return; } // Build table HTML var tableHtml = ` <table class="table table-striped"> <thead> <tr> <th>Technician ID</th> <th>Name</th> <th>Tarif</th> <th>Estimated Duration</th> <th>Select</th> </tr> </thead> <tbody> `; $.each(res.technicians, function(index, tech) { // Assume each technician has one tarification entry for this tache var tarification = tech.tarificationtaches[0]; tableHtml += ` <tr> <td>${tech.id}</td> <td>${tech.user?.nom || 'N/A'}</td> <td>${tarification.tarif}</td> <td>${tarification.duree_prevu || 'N/A'}</td> <td> <input type="radio" name="technicien_tarification" value="${tech.id}|${tarification.id}" required> </td> </tr> `; }); tableHtml += ` </tbody> </table> `; $('#technicians-table-container').html(tableHtml); }); } else { $('#technicians-table-container').html(''); } } </script>
Update the Form Section
Replace the old tarifications and techniciens dropdowns with a table container, and update the taches dropdown to trigger our new function:
<!-- Keep existing fields like client, date, description unchanged --> <div class="form-group"> <label for="metier">Metier</label> <select onchange="getTachesByMetier(this.value)" name="metier_id" id="metier" class="form-control"> <option value="">-Select-</option> @foreach($metiers as $m) <option value="{{$m->id }}">{{$m->libelle_metier}}</option> @endforeach </select> </div> <div class="form-group"> <label for="taches">Tache</label> <select onchange="loadTechniciansWithTarification(this.value)" name="tache_id" id="taches" class="form-control"> <option value="">-Select-</option> </select> </div> <!-- Container for the dynamic technicians table --> <div class="form-group" id="technicians-table-container"> <!-- Table loads here via AJAX --> </div> <!-- Hidden fields to store selected technician and tarification IDs for submission --> <input type="hidden" name="technicien_id" id="selected-technicien-id"> <input type="hidden" name="tarification_id" id="selected-tarification-id">
Add Radio Selection Handler
Add this small script at the end of the form to populate the hidden fields when a technician is selected:
<script> // Update hidden fields when a radio button is selected $(document).on('change', 'input[name="technicien_tarification"]', function() { var [techId, tarifId] = $(this).val().split('|'); $('#selected-technicien-id').val(techId); $('#selected-tarification-id').val(tarifId); }); </script>
Update the store method to use the hidden field values (this will work if you named the fields correctly):
public function store(InterventionRequest $request) { $intervention = new Intervention(); $intervention->date_intervention = $request->input('date_intervention'); $intervention->description = $request->input('description'); $intervention->duree_prevu = $request->input('duree_prevu'); $intervention->statut = $request->has('statut') ? $request->input('statut') : 0; $intervention->technicien_id = $request->input('selected-technicien-id'); $intervention->client_id = $request->input('client_id'); $intervention->tarification_id = $request->input('selected-tarification-id'); $intervention->save(); return redirect('intervention'); }
Quick Checks:
- Ensure your
Technicienmodel has atarificationtachesrelationship defined (e.g.,public function tarificationtaches() { return $this->hasMany(Tarificationtache::class); }) - Adjust table columns in the JS to match your actual
tarificationtachetable fields - The radio buttons enforce single selection, which is needed for linking one technician/tarification to the intervention
内容的提问来源于stack exchange,提问作者chagou2704

