How to define an onclick function on Laravel Collectives? - laravel

I have implemented a drop down using Laravel collectives. I need to call function setMaterialValue(let x){ console.log(x)} on each time I select a material. This should be specific to each material as cotton-10, wetlook-20, crocodile-30 etc. Without Laravel collective this can be performed as
<option onclick="setMaterialValue(10);">Cotton</option>
How to perform this using Laravel collectives?
My code is as follows:
<div class="card">
<div class="card-header"><h2 class="card-title m-0">Feature Selector</h2></div>
<div class="card-body">
<h5 class="card-title"><b>Material Selector</b></h5>
<div class="row">
<div class="col-md-6">
Textile Material
</div>
<div class="col-md-6">
{{Form::select('material_selector', [
'10' => 'Cotton',
'20' => 'Wet Look',
'30' => 'Crocodile',
], null, ['placeholder' => 'Select Material'],['class'=>'form-control'])
}}
</div>
</div>
<hr>
</div>
</div>

FYI - Where your class declaration is add it and any other html attributes there as well:
{{ Form::select('material_selector',
[
'1' => 'Cotton',
'2' => 'Wet Look',
'3' => 'Crocodile',
],
null,
['placeholder' => 'Select Material'],
[
'class'=>'form-control',
'onclick'=>'setMaterialValue(10)' // <== ADD IT HERE
])
}}

You should probably use jQuery. Then you can address your select element as follows
$(document).ready(function() {
$('.form-control[name="material_selector"]').on('change', showSelectedValue);
function showSelectedValue(event) {
var target = $(event.target);
console.log(target.val() + " = " + target.find('option:selected').text());
}
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<select name="material_selector" class="form-control">
<option value="10">Cotton</option>
<option value="20">Wet Look</option>
<option value="30">Crocodile</option>
</select>
Another option
If you really do not want to use jQuery, then try to use the onChange attribute for the select tag like the example below
{{Form::select(
'material_selector', // name attribute of the select
['10' => 'Cotton', '20' => 'Wet Look', '30' => 'Crocodile'], // option values
null, // selected value, for example '20'
['placeholder' => 'Select Material', 'class' => 'form-control', 'onChange' => 'showSelectedValue(this)'], // attributes for <select>
)}}
function showSelectedValue(element) {
console.log(element.value + " = " + element.options[element.selectedIndex].text);
}
<select name="material_selector" class="form-control" onChange="showSelectedValue(this)">
<option value="10">Cotton</option>
<option value="20">Wet Look</option>
<option value="30">Crocodile</option>
</select>

Related

Attempt to read property "name" on array (Select with Livewire)

I'm trying to make a dependent select with Livewire.
My problem is that when I load the second select, it loads it without problems, but when I select an option from the second select, it throws me this error.
Attempt to read property "nombre" on array
select template
<div class="container">
<div class="row mb-3">
<div class="col-4">
<label class="form-label">Tipo de Inscripcion</label>
<select wire:model="selectedTipoInscripcion" class="form-select">
<option selected>Seleccionar ...</option>
#foreach($tipoInscripcion as $tipo)
<option value="{{ $tipo -> id }}">{{ $tipo -> nombre}}</option>
#endforeach()
</select>
</div>
#if(!is_null($tipoPrograma))
<div class="col-4">
<label class="form-label">Tipo de Programa</label>
<select wire:model="selectedTipoPrograma" class="form-select">
<option selected>Seleccionar ...</option>
#foreach($tipoPrograma as $tipo)
<option value="{{ $tipo -> id}}">{{ $tipo -> nombre}}</option>
#endforeach()
</select>
</div>
#endif
</div>
</div>
The problem is in
<option value="{{ $tipo -> id}}">{{ $tipo -> nombre}}</option>
My Component
<?php
namespace App\Http\Livewire;
use App\Models\Curso;
use App\Models\Programa;
use Livewire\Component;
class SelectAnidado extends Component
{
public $selectedTipoInscripcion = null, $selectedTipoPrograma = null, $SelectedProgrCur = null;
public $tipoPrograma = null, $progrCur = null, $sw = null;
public function render()
{
$programa = (object) ['id' => 1, 'nombre' => 'Programa'];
$curso = (object) ['id' => 2, 'nombre' => 'Curso'];
$ti = collect([$programa, $curso]);
return view('livewire.select-anidado', [
'tipoInscripcion' => $ti
]);
}
public function updatedselectedTipoInscripcion($id)
{
if ($id == 1) {
$doctorado = (object) ['id' => 1, 'nombre' => 'doctorado'];
$maestria = (object) ['id' => 2, 'nombre' => 'maestria'];
$especialidad = (object) ['id' => 3, 'nombre' => 'especialidad'];
$diplomado = (object) ['id' => 4, 'nombre' => 'diplomado'];
$this->tipoPrograma = collect([$doctorado, $maestria, $especialidad, $diplomado]);
}
}
}
It tells me that I am trying to access an array as if it were an object.
But then the error should also appear when the is loaded.
Why does it only appear when I make the selection?
I think problem is here :
$this->tipoPrograma = collect([$doctorado, $maestria, $especialidad, $diplomado]);
you're passing array in tipoPrograma, and each variables is array too.

Livewire quantity input field not update dynamically when change value

I've purchased pos software which is not updated the quantity input field when changed into the checkout page it's working with a button. I want to change form submit button quantity input to dynamic input field with cart total, not with a hard-coded button.
Screenshot of this problem
Blade Code
<form wire:submit.prevent="updateQuantity('{{ $cart_item->rowId }}', '{{ $cart_item->id }}')">
<div class="input-group">
<input wire:model.lazy="quantity.{{ $cart_item->id }}" style="min-width: 40px;max-width: 90px;" type="number" class="form-control" value="{{ $cart_item->qty }}" min="1">
<div class="input-group-append">
<button type="submit" class="btn btn-primary">
<i class="bi bi-check"></i>
</button>
</div>
</div>
Update function
public function updateQuantity($row_id, $product_id) {
if ($this->check_quantity[$product_id] < $this->quantity[$product_id]) {
session()->flash('message', 'The requested quantity is not available in stock.');
return;
}
Cart::instance($this->cart_instance)->update($row_id, $this->quantity[$product_id]);
$cart_item = Cart::instance($this->cart_instance)->get($row_id);
Cart::instance($this->cart_instance)->update($row_id, [
'options' => [
'sub_total' => $cart_item->price * $cart_item->qty,
'code' => $cart_item->options->code,
'stock' => $cart_item->options->stock,
'unit' => $cart_item->options->unit,
'product_tax' => $cart_item->options->product_tax,
'unit_price' => $cart_item->options->unit_price,
'product_discount' => $cart_item->options->product_discount,
'product_discount_type' => $cart_item->options->product_discount_type,
]
]);
}

Uncaught (in promise) TypeError: initialData is null - my components are wrapped in a single div but still getting the error

I am getting an initial data is null error. This has been talked about github forum, however, the answer was that the component was not wrapped in a single div. My components are. So I am still getting:
Uncaught (in promise) TypeError: initialData is null
I have a simple button that runs a function when clicked
which is produced by this code:
<div class="mx-0 col-span-1 block font-medium text-sm text-gray-700 mb-0">
<x-green-button-sm class="px-0 mx-0" title="Add a New person to the family." wire:click="createChild">
<h3 class="my-0 text-xss">Add Child</h3>
</x-green-button-sm>
#livewire('admin.shared.edit-add-child', ['showEditAddChildModal' => $showEditAddChildModal,
'editadd' => 'add', 'userid' => $user->id, 'registrantOrAdmin' => $registrantOrAdmin])
</div>
Which calls this function in the component
public function createChild(){
$this->showEditAddChildModal = true;
}
And notice that the livewire component above is passed the value of $showEditAddChildModal
The beginning of the admin.shared.edit-add-child blade component is:
<div>
<form wire:submit.prevent="save">
<x-modal.dialog wire:model="showEditAddChildModal">
......
.....
</div> // the blade component is contained in a single div as required
so the effort is to make the model visible obviously. The admin.shared.edit-add-child blade blade makes reference to models (public properties) like this
wire:model.debounce.500ms="editChild.firstname"
the EditAddChild.php component is set up like this:
<?php
namespace App\Http\Livewire\Admin\Shared;
use App\Models\Person;
use Livewire\Component;
class EditAddChild extends Component
{
public $showEditAddChildModal = false;
//(if i set the above true, the modal does show up.)
public $userid;
public $txtmsgp;
public $fullname;
public $registrantOrAdmin;
public $editadd;
public $editChild;
// (I started with public Person $editChild but the system balked at //initializing a typed variable in the mount() function)
public $dateOfBirth;
Below, note that the $this->editadd variable is passed in the #livewire call seen above. The mount() function in the EditAddChild.php component is:
public function mount(){
if($this->editadd == 'add')
$this->editChild = $this->addNewChild();
}
addNewChild() is:
public function addNewChild()
{
return Person::make(['added_by' => auth()->user()->id,
'updated_by' => null,
'family_type' => 'child',
'firstname' => '',
'lastname' => '',
'pronouns' => 'u',
'sex' => 'u',
'dob' => now(),
'age_today' => 0,
'mobile_phone' => null,
'receive_texts' => 'u',
'email' => '',
'allow_emails' => 'u',
'member' => 'u',
'allow_photos' => 'u',
'show' => 0,
]);
}
when i click on the add child button to change the x-show variable to true, the modal does not show and the console reports this:
My apologies, but I thought I would list the entire modal coponent as well. There are two parts [dialog.blade.php] :
#props(['id' => null, 'maxWidth' => null])
<x-modal :id="$id" :maxWidth="$maxWidth" {{ $attributes }}>
<div class="px-6 py-4">
<div class="text-lg">
{{ $title }}
</div>
<div class="mt-4">
{{ $content }}
</div>
</div>
<div class="px-6 py-4 bg-gray-100 text-right">
{{ $footer }}
</div>
</x-modal>
the second part being [modal.bade.php]:
#props(['id', 'maxWidth'])
#php
$id = $id ?? md5($attributes->wire('model'));
$maxWidth = [
'sm' => 'sm:max-w-sm',
'md' => 'sm:max-w-md',
'lg' => 'sm:max-w-lg',
'xl' => 'sm:max-w-xl',
'2xl' => 'sm:max-w-2xl',
'3xl' => 'sm:max-w-3xl',
'4xl' => 'sm:max-w-4xl',
'5xl' => 'sm:max-w-5xl',
'6xl' => 'sm:max-w-6xl',
'7xl' => 'sm:max-w-7xl',
][$maxWidth ?? '3xl'];
#endphp
<div
x-data="{
show: #entangle($attributes->wire('model')).defer,
focusables() {
// All focusable element types...
let selector = 'a, button, input, textarea, select, details, [tabindex]:not([tabindex=\'-1\'])'
return [...$el.querySelectorAll(selector)]
// All non-disabled elements...
.filter(el => ! el.hasAttribute('disabled'))
},
firstFocusable() { return this.focusables()[0] },
lastFocusable() { return this.focusables().slice(-1)[0] },
nextFocusable() { return this.focusables()[this.nextFocusableIndex()] || this.firstFocusable() },
prevFocusable() { return this.focusables()[this.prevFocusableIndex()] || this.lastFocusable() },
nextFocusableIndex() { return (this.focusables().indexOf(document.activeElement) + 1) % (this.focusables().length + 1) },
prevFocusableIndex() { return Math.max(0, this.focusables().indexOf(document.activeElement)) -1 },
}"
x-init="$watch('show', value => {
if (value) {
document.body.classList.add('overflow-y-hidden');
} else {
document.body.classList.remove('overflow-y-hidden');
}
})"
x-on:close.stop="show = false"
x-on:keydown.escape.window="show = false"
x-on:keydown.tab.prevent="$event.shiftKey || nextFocusable().focus()"
x-on:keydown.shift.tab.prevent="prevFocusable().focus()"
x-show="show"
id="{{ $id }}"
class="overflow-auto jetstream-modal fixed inset-0 overflow-y-auto px-4 py-6 sm:px-0 z-50"
style="display: none;"
>
<div x-show="show" class="fixed inset-0 transform transition-all" x-on:click="show = false"
x-transition:enter="ease-out duration-3000"
x-transition:enter-start="opacity-0"
x-transition:enter-end="opacity-100"
x-transition:leave="ease-in duration-3000"
x-transition:leave-start="opacity-100"
x-transition:leave-end="opacity-0">
<div class="absolute inset-0 bg-gray-500 opacity-75"></div>
</div>
<div x-show="show" class="mb-6 bg-white rounded-lg overflow-hidden shadow-xl transform transition-all sm:w-full {{ $maxWidth }} sm:mx-auto"
x-transition:enter="ease-out duration-300"
x-transition:enter-start="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95"
x-transition:enter-end="opacity-100 translate-y-0 sm:scale-100"
x-transition:leave="ease-in duration-200"
x-transition:leave-start="opacity-100 translate-y-0 sm:scale-100"
x-transition:leave-end="opacity-0 translate-y-4 sm:translate-y-0 sm:scale-95">
{{ $slot }}
</div>
</div>
Please check in here
#livewire('admin.shared.edit-add-child', ['showEditChildModal' => $showEditAddChildModal,
'editadd' => 'add', 'userid' => $user->id, 'registrantOrAdmin' => $registrantOrAdmin])
precisely at "'showEditChildModal' => $showEditAddChildModal" part. You're binding the parent property ($showEditAddChildModal) to the child ('showEditChildModal'), but in the child component that property doesn't exist, instead you have declared the property as next:
public $showEditAddChildModal = false;
It's a typo of you should fix it???

How to convert select & options to Laravel Form Elements

I have the following select section in HTML and CSS taken from ADMIN LTE
<select class="form-control select2" style="width: 100%;">
<option selected="selected">Alabama</option>
<option>Alaska</option>
<option>California</option>
<option>Delaware</option>
<option>Tennessee</option>
<option>Texas</option>
<option>Washington</option>
</select>
I need to convert it to Laravel Form Elements and I tried as follows:
{{Form::select('filter_region', [
'1' => 'Alaska',
'2' => 'California',
'3' => 'Delaware',
], null, ['placeholder' => 'Alaska'],['class'=>'form-control select2'])}}
But the views are different
How to resolve this?

Laravel Collective onclick in SELECT

How to add laravel collective onclick in "select"? My below code does not work:
{{Form::select('material_selector', [
'10' => 'Cotton',
'20' => 'Wet Look',
'30' => 'Crocodile',
], null, ['placeholder' => 'Select Material'],['class'=>'form-control','onclick'=> 'showSelectedValue()' ])
}}
You should probably use jQuery. Then you can address your select element as follows
$(document).ready(function() {
$('.form-control[name="material_selector"]').on('change', showSelectedValue);
function showSelectedValue(event) {
var target = $(event.target);
console.log(target.val() + " = " + target.find('option:selected').text());
}
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<select name="material_selector" class="form-control">
<option value="10">Cotton</option>
<option value="20">Wet Look</option>
<option value="30">Crocodile</option>
</select>
If you are really need to use the onClick attribute you can try this
{{Form::select(
'material_selector', // name attribute of the select
['10' => 'Cotton', '20' => 'Wet Look', '30' => 'Crocodile'], // option values
null, // selected value, for example '20'
['placeholder' => 'Select Material', 'class' => 'form-control'], // attributes for <select>
['onClick' => 'showSelectedValue()'] // attributes for <option>
)}}

Resources