How to mark selected items as checked in laravel multiselect dropdown - php

I am using this multiselect dropdown plugin . I can get all the ids of the selected items in the dropdown during the store method. However during the edit method when ever i am trying to load the entity that has multiple values , i am unable to mark the items as checked in the dropdown.
so for example -
Suppose I am working with Contacts. Each contact can belong to many categories. There is a belongsToMany relationship between the contacts and the categories. Whenever I am adding a new contact (and if the user has selected many categories) i get the id of all the categories and assign it to the contact. Now when I am trying to load the contact again, i have to display the list of categories that were selected for this contact - which i have ben unable to do so till now.

Travis answers really helped me a lot. Hence I am marking this as the correct answer. However there were some updates that I had to do . Following is what I had to do ..
#if(isset($contact))
<?= Form::select(
'category_ids[]',
Category::lists("name", "id"),
$contact->categories()->select('categories.id AS id')->lists('id'),
[
'class' => 'form-control multiselect',
'multiple'
]
)?>
#else
{{ Form::select("category_ids[]", Category::lists("name", "id"), Input::old("category_id"), array( "class" => "form-control multiselect" , "multiple" => "multiple" )) }}
#endif
I am using the same form for the create and edit operations , so in the create form , it was throwing me an error on the contact->categories line which is true because in the create method the contact is null. Hence the check.

Here's how I accomplish multi-selects in Laravel 4:
<?= Form::select(
'category_ids[]',
App::make('Category')->lists('name', 'id'),
$contact->categories()->select('categories.id AS id')->lists('id'),
[
'class' => 'form-control',
'multiple'
]
)?>
The resulting select markup looks like this:
<select class="form-control" multiple="multiple" name="category_ids[]">
<option value="1" selected="selected">category 1</option>
<option value="2">category 2</option>
</select>
And then, when you update, you'll need to add this line after validating your model:
$contact->categories()->sync(Input::get('category_ids'));
Use this in both your create and edit forms. In your create action,
$contact->categories() will be empty, so the select will not be populated, but in the edit action, you will get the properly selected values.
Edit: In order to share the form like this, you'll need to pass in a new instance of the contact model in your create action like so:
public function create()
{
$contact = App::make('Contact');
return View::make('contact.create', concat('contact'));
}
In your shared form, $contact will always be available even if it's not yet persisted.

Related

Laravel Select Box

I'm trying to figure out how I can structure my Laravel select menu so that it shows up as this for a final render. Has anyone done such a thing.
The location is a property of the arena object.
<option value="arena_id">Arena Name - Location</option>
{{ Form::select('arena_id', [ null => 'Please Select'] + $arenas, null, ['id' => 'arena_id']) }}
I asssume $arenas comes from something like Arena::where('foo', bar)->get(), but with get() you will get an instance of Illuminate\Database\Eloquent\Collection instead of an actual array which is what you want in Form::select.
So what you need to do is to use lists($field, $key), it will fetch you rows and return it as an array.
$arenas = Arena::where('foo', bar)->lists('name', 'id');
There is a code example here with some comments from users if you want to learn more.
You can use pluck function for getting the results as array
refer https://laravel.com/docs/5.1/collections#method-pluck
$select = $this->all()->pluck('title', 'id');
Then you can use below sample code for creating select box with selected option in blade template
{{ Form::select('name',$select,'selected option id',['class' => 'form-control']) }}

Laravel/Blade Drop Down List - For more than one field

I'm trying to use blade to display a dropdown list from table data. The problem I have, is that I want to display the results of two fields in the table concatenated, not just one.
So I want something to render something like;
<select id="agreement_type" name="agreement_type">
<option value="1">Agreement Field 1 - Agreement Field 2</option>
<option value="2">Agreement Field 1 - Agreement Field 2</option>
<option value="4">Agreement Field 1 - Agreement Field 2</option>
</select>
My controller currently looks like this;
$agreements = Agreement::lists('agreement_type','id');
return View::make('client_agreements.create')
->with('agreements', $agreements);
My blade view currently looks like this;
<div class="form-group">
{{ Form::label('agreement_type', 'Agreement type') }}
{{ Form::select('agreement_type', $agreements) }}
</div>
I have tried to amend the view and controller in various ways to get the desired output. But can't get it to work.
I want to display agreement_type and level and have the id set as the value so I tried;
$agreements = Agreement::lists('agreement_type'.'level','id');
But this just displays level as the value and completely ignores id.
This is the simplest method. Just use a foreach loop to build the options array:
$agreements = Agreement::all();
$agreementOptions = array();
foreach($agreements as $agreement){
$agreementOptions[$agreement->id] = $agreement->agreement_type.' '.$agreement->level;
}
return View::make('client_agreements.create')
->with('agreements', $agreementOptions);
However you can also define an attribute accessor in your model. You can use that to create new properties that can be accessed normal, but you can run logic to generate them (like combining to attributes)
public function getSelectOptionAttribute(){
return $this->attributes['agreement_type'].' '.$this->attributes['level'];
}
And then you can use lists:
$agreements = Agreement::all()->lists('select_option', 'id');
(Laravel converts SelectOption (studly case) from the method name to select_option (snake case) for the attribute, so don't get confused by that)

Laravel update form - get correct selected state

Within my update profile form, I have a select list for title. Admittedly, the items should be derived from the database however for the moment, I would like this particular select list to do the following..
Show the selected item on initial page load. So, if the $user['title'] is a 'Mrs', this is displayed.
Should laravel validation bring up errors on other form fields, and the user has changed the title to 'Mr', the selected state should be on the item 'Mr'.
I have the following so far, but it isn't working correctly.
<select name="title" id="title">
<option value="Mr" #if(($user['title']) == 'Mr') selected #else #if((Input::old('title')) == 'Mr') selected #endif #endif>Mr</option>
<option value="Mrs" #if(($user['title']) == 'Mrs') selected #else #if((Input::old('title')) == 'Mrs') selected #endif #endif>Mrs</option>
....
</select>
You should pass the data for the select from your Controller and also uset the Form component to build the select in the View, for example:
In Controller method:
$users = User::lists('title', 'id');
return View::make('user')->with('users', $user);
In the View:
// By default, item with id 1 (the first item) will be selected
echo Form::select('title', $users, Input::old('title', 1), ['id'=>title]);
If you are using Blade then:
// By default, item with id 1 (the first item) will be selected
{{ Form::select('title', $users, Input::old('title', 1), ['id'=>title]) }}
Read the documentation properly. You are using Laravel with old school PHP coding.

Laravel dropdown list

I'm using Laravel framework and i have two dropdown lists of which both are reading data from the database tables,
the first one it read all the records from the table and populate it on the select list
here is my code:
<div class="form-group">
{{Form::select('advertiserName', Advertiser::all()->lists('advertiserName', 'advertiserId'))}}
</div>
it display the advertiser name and also passes the id on the advertiser.
The second dropdown i want it to display all the Brands related to the above selected advertiser.
here is my code:
<div class="form-group">
{{Form::select('brandName', Brand::where('advertiserId', '=', '3')->lists('brandName', 'id'))}}
</div>
The advertiserId is the foreign key of the advertiser and 3 must be replaced by the the advertiserId you selected on the first dropdown list, basically i want to pass variable from the first select list to the second one
Thank you
Basically you need to use AJAX to get data for Second Dropdown based on option selected from first dropdown.
Create Second Dropdown inside specific div and After ajax Call replace contect of div from ajax response.
As stated, the best way to achieve this is via an AJAX request. Here is an example of how you can achieve this functionality.
Firstly create a view partial that renders the select box for brands. Something like this (this code is based on Bootstrap 3):
{{ Form::label('brandName', 'Brand', ['class' => 'control-label col-sm-2']) }}
<div class="col-sm-10">
{{ Form::select('brandName', $brands, null, ['class' => 'form-control']) }}
</div>
Now, in your routes.php file add the following route:
Route::get('brand-list/{id}', ['as' => 'brands', 'uses' => 'BrandsController#brandList']);
In your BrandsController.php file (or whatever controller your using to handle this) add a method called brandList();
public function brandList($id)
{
// Return an array of brands for the selected advertiser name ID if available
$brands = $this->brand->where('advertiserId', $id)->lists('brandName', 'id'); // I'm using dependency injection here so you'll need to assign your Brand model to the $this->brand property of this classes constructor method
if ( ! isset($brands))
{
$brands = ['No brands available' => null]; // return a generic array containing 1 item with a value of null so you can handle it in your view. You could also return something else here such a boolean of false and then handle that in your AJAX request to return an error or info message
}
return View::make('brands.partials.select', compact('brands'));
}
Now for the AJAX:
$('#advertiserName').change(function(e) {
var advertiserId = $(this).val();
var url = '/brand-list/' + advertiserId;
$.get(url, function(data) {
$('.brands').html(data); // The returned view with the brand select input
});
});
Then in your initial form view you'll want to create an empty div with a class of .brands that we'll use to populate with the HTML returned via our AJAX request. Something like this if you're using Bootstrap 3 for example:
<div class="form-group brands"></div>
This should work as you need but I haven't tested this code, so if you have any issues let me know. Obviously this is generic code based on the info available and there are many ways to skin a cat.

validator rules for a database select / dropdownmenu (in a form) laravel 4.1

I have a problem with laravel, and my form.
In my form (createBand.blade.php), i made a form with a dropdownlist wich call a database table: musicalGenre.
It should be noted that the dropdownmenu/list (select form) calls to another table in the database called MusicalGenre, and the form where I want the dropdownlist is to register a band in the database table Bands.
The select form works, i could choose in a dropdownlist all musicalGenre_name in my table after seeding them. Here's the blade page code (of course i have open, close the form and the section like laravel requires):
<p>
{{Form::label('name','Name of the Band: ')}}
{{Form::text('name',Input::old('name'))}}
</p>
#if ($errors->has('name'))
<p class='error'> {{ $errors->first('name')}}</p>
#endif
<br>
<br>
<p>
{{Form::label('email','Band Email: ')}}
{{Form::text('email',Input::old('email'))}}
</p>
#if ($errors->has('email'))
<p class='error'> {{ $errors->first('email')}}</p>
#endif
<br>
<br>
<p>
{{Form::label('musicalGenre','your style: ')}}
{{Form::select('musicalGenre_name', $genre_options = array('' => 'select your style') + musicalGenre::lists('name'), Input::old('musicalGenre_name')) }}
</p>
#if ($errors->has('musicalGenre'))
<p class='error'> {{ $errors->first('musicalGenre_name')}}</p>
#endif
<br>
<br>
I have a controller named createBandController, where i made some rules for validators for the blade form. The poblem is:
i can't pass the validators, that is to say, even if i choose a musical genre in my dropdownlist, for laravel there no choice made.
I have the error "musical genre is required". I don't understand the validator rules for a select form in my controller, or i don't know what i'm suposed to input in the rules for musical genre. Here's the controller code:
public function createBand() {
$result = MusicalGenre::all();
$genre = $result->lists('name');
$inputs = Input::all();
$rules = array(
'name' => 'required|between:1,64|unique:bands,name',
'email' => 'between:1,128|email|unique:bands,email',
'musicalGenre' => 'integer|required|in:musicalGenre'
);
$validation = Validator::make($inputs, $rules);
if ($validation->fails()) {
return Redirect::to('createBand')->withInput()->withErrors($validation)
->with('alert_error', 'you have some mistakes');
Don't pay attention to the names, (i'm french, i changed them in order to be clear for you), and i'm sure that is the validator of my dropdownlist who make problems when i fill out my form, because i can't pass it. In my original project code, there are no spelling mistakes.
All my validators and variable names work. I think i need to find the correct rules for a select form input and validators in order to laravel knows i made a choice when i choose in my dropdownlist.
At first i thought to specify that the dropdownlist use the database table musicalGenre. Like i specified that some fields are in the database table Bands, like this:
'name' => 'required|between:1,64|unique:bands,name'
Here, "name" is a field of the database table Bands. But it didn't work too.
If anyone have a solutions or wants to help, i'm interested.
Thank you (and sorry if my english seems so bad).
The validation rule in: on the field musicalGenre won't work the way that you have implemented it. It expects a comma delimited list of strings which the field value is scrubbed against.
For example if the field was 'Gender' the validation would be:
'gender' => 'in:male,female'
To validate against musicalGenre against a model you will need to write a custom Validator. See http://laravel.com/docs/validation#custom-validation-rules
I am currently writing a custom validator for this 'belongs_to' validation and when I have it working I'll post it here.
UPDATE
I have written a custom validation rule that should help. Firstly create a validators.php file and include it in global.php
require app_path().'/validators.php';
Within validators.php create the custom rule:
Validator::extend('exists_in', function($attribute, $value, $parameters)
{
$result = $parameters[0]::find($value);
return ($result == null) ? FALSE : TRUE;
});
In your validations you could now have:
'musicalGenre' => 'integer|required|exists_in:musicalGenre'
The exists_in validation takes a parameter of the Model Class name
And to give this validation an error message, add the following to the array in app/lang/en/validation.php:
"exists_in" => "The selected :attribute is invalid."
Does exists:musicalGenre instead of in:musicalGenre help?

Categories