Reputation: 1056
I am discovering php, laravel, vuejs at the same time and I guess there are some things I didn't get well yet ;)
I made a new component "tableau" which is a basic table and would like to use it at many places in my app, where I would just specify its title, columns and data. FootballerController is the place where I get all my data.
Here is what is working now:
app.js
const tableau = new Vue({
components:{tableau:Tableau
},
data: function() {
return {
title: "the best footballers",
searchQuery: '',
gridColumns: ['footballer', 'cote', 'nationalite'],
gridData: [
{ footballer: 'Remond', cote: 951, nationalite:'USA' },
{ footballer: 'Marcel', cote: 935, nationalite:'ESP' },
{ footballer: 'Stian', cote: 923, nationalite:'NOR' },
{ footballer: 'Martin', cote: 923, nationalite:'USA' },
{ footballer: 'Pierre', cote: 918, nationalite:'ESP' },
]
}
}
}).$mount('#tableau');
footballer.blade.php
<tableau
v-bind:titre="title"
:rows="gridData"
:columns="gridColumns "
:filter-key="searchQuery" >
</tableau>
TableauComponent
<template>
<div >
<h1 >{{titre}}</h1>
<table >
<thead>
<tr>
<th v-for="key in columns"
{{ key | capitalize }}
</th>
</tr>
</thead>
<tbody>
<tr v-for="entry in rows">
<td v-for="key in columns">
{{entry[key]}}
</td>
</tr>
</tbody>
</table>
</div>
</template>
<script>
export default {
name:'tableau',
props: {
rows: Array,
columns: Array,
titre: String
}
}
</script>
This works.
Then, here is what I would like: being able to put my values from the controller into footballer.blade.php, which is using TableauComponent.vue
FootballerController
public function footballer($id){
//process to get all this data in DB ($footballer, $gridData, $gridColumns, $title)
$footballer= (Footballer::select(SOME REQUEST)->where('id', '=', $id)->get())[0];
return view('footballers/footballer', ['footballer' => $footballer,
'gridData' => $gridData,
'gridColumns' => $gridColumns,
'title' => $title] );
}
And in footballer.blade.php
<tableau
v-bind:titre="{{ $title }}"
:rows="{{ $gridData }}"
:columns="{{ $gridColumns }}" >
</tableau>
Then in app.js I wouldn't need data anymore
const tableau = new Vue({
components:{tableau:Tableau
}
}).$mount('#tableau');
But this doesn't work and tells me "Property or method is not defined on the instance but referenced during render"
I don't manage at all and am worndering is I have the good way of doing: Should I not get my data in FootballerController? If not, where can I get it then?
Thanks a lot in advance.
Upvotes: 1
Views: 6123
Reputation: 751
Your are using ':' symbol before your attributes in your blade, which means 'v-bind' as the doc says : VueJS Shorthands. So first, for assigning a String to a props, you don't need ':' before 'titre'.
Then, to solve your problem you could try to add a default value to your props, for example :
props: {
rows: {
default: []
},
columns: {
default: []
},
titre: {
default: ''
}
}
I didn't try but I think it should works.
Upvotes: 2
Reputation: 1056
Thanks a lot, indeed the php array to javascript array was the issue.
In the php controller, I parse my data into json
'gridData' =>json_encode($gridData),
In the php view footballer.blade.php
<tableau
titre="{{ $title }}"
rows="{{ $gridData }}">
</tableau>
And in my Vue view, I was getting an array, and changed the code for this:
rows: {
type: String,
default: ""
}
var rowsArray = JSON.parse(this.rows)
Now it seems like the data I get after my request isn't properly parsed, but that's another point :)
Upvotes: 0
Reputation: 1512
When you use {{ value }}
in both Blade & javascript framework at the same time. You need to use @{{ value }}
to avoid collision between Blade & Vue.
try
<tableau
v-bind:titre="@{{ $title }}"
:rows="@{{ $gridData }}"
:columns="@{{ $gridColumns }}" >
</tableau>
Besides that, when you use :rows="value"
, the value
must be javascript syntax, otherwise when rows="value"
, the value
would be treated as string
.
You might need to use json_encode
to format your data from the Laravel, or use @json
if you're using Laravel 5.5^.
Upvotes: 5