Livewire Select2 Dynamic not updating public view

I am using a select2 component with wire:ignore and i want to update the select2 value dynamically after clicking a button. I set up this functionality with events and events work fine, so does the variable gets initialized as well. I am failing to update this public view of this select2.

my blade

<select class="select2-example form-control" id="subjects" wire:model.lazy="subjects"  name="subjects"> 
 </select> 

@push('scripts')
<script>
$('#subjects').select2({
        maximumSelectionLength: 1,
        minimumInputLength:2,        
        tags: false,
        placeholder: 'Enter Subject(s)',
       .... // this all works great
});   

$('#subjects').on('change', function (e) {
        let data = $(this).val();
        @this.set('subjects', data);
});

// my event listener and it is working as well
Livewire.on('editSubject', subject => {
         console.log(subject);

         @this.set('subjects', subject);
         $('#subjects').val(subject);
         $('#subjects').trigger('change');   //the public view doesn't get updated
}) 
</script>
@endpush

I so far tried with browser dispatch event as well. Nothing works. What would be the workaround for this? Any help is greatly appreciated.

Upvotes: 2

Views: 4060

Answers (2)

Wcan
Wcan

Reputation: 878

Note: If some face the problem of real time validaiton while implementing the above mentioned solution as i have commented in the accepted answer above.

My Comments:

hey, I have implemented your solution its working great but there is one problem, here is the scenario, I submit empty form and all the validations gets triggered, when i start filling the form the error starts to disappear but as soon as i change the select2 the validation part $this-update($key, $value) function does not work. Can you please tell me why real time validation is not working ? and how to fix it please. thankyou – Wcan

Solution:

Use syncInput() function instead of assigning the value to country property. updated lifecycle hook will be trigerred automatically.

public function setCountry($countryValue)
{
    // $this->country = $countryValue;
    $this->syncInput('country', $countryValue);
}

Upvotes: 1

Prospero
Prospero

Reputation: 2352

in blade

<div class="col d-flex display-inline-block">
  <label for="contact_devices">{{ __('Select Device') }}</label>
  <select id="contact_devices" wire:model="selectedDevice" class="form-control contact_devices_multiple" multiple="multiple" data-placeholder="{{ __('Select') }}">
    @foreach($devices as $device)
      <option value="{{ $device->id }}">{{ $device->alias }}</option>
    @endforeach
  </select>
</div>

<script>
  window.loadContactDeviceSelect2 = () => {
    $('.contact_devices_multiple').select2({
      // any other option
    }).on('change',function () {
      livewire.emitTo('tenant.contact-component','devicesSelect',$(this).val());
    });
  }
  loadContactDeviceSelect2();
  window.livewire.on('loadContactDeviceSelect2',()=>{
    loadContactDeviceSelect2();
  });

</script>

in component

public $selectedDevice;

protected $listeners = [
  'devicesSelect'
];

public function devicesSelect($data)
{
   dd($data);
   $this->selectedDevice = $data;
}

public function hydrate()
{
  $this->emit('loadContactDeviceSelect2');
}

Upvotes: 3

Related Questions