I guess you can't because you can't execute PHP in your .vue file. You could create a method that will send a xhr request to get a translation but that would result in many requests.
Use trans in vue.js
Hi,
Atm i'm using vue.js component with vueify compiler. How can I translate something in template using Laravel trans methods
Thanks,
Shu
Thanks for your suggestion, I moved the template to my blade ;)
That's what I do too :).
Yes, laravel (PHP) is server side, and you can't use it directly into javascript You can create own trans() function in vuejs and import translations in json format
Yes, it is partially possible, just converting the translation array to Json and save this in js variable, afther that you can use this variable (Json transalations) in vue js.
For example :
wellcome.blade.php { var transJson = {!! json_encode(trans('categories')) !!}; var translations = JSON.stringify(transJson);
}
master.js (vue script) {
console.log(translations); }
In case someone is still interested, I have solved the problem this way:
Open your base app template (probably resources/views/layouts/app.blade.php) and add this to the header:
<script>
window.trans = <?php
// copy all translations from /resources/lang/CURRENT_LOCALE/* to global JS variable
$lang_files = File::files(resource_path() . '/lang/' . App::getLocale());
$trans = [];
foreach ($lang_files as $f) {
$filename = pathinfo($f)['filename'];
$trans[$filename] = trans($filename);
}
echo json_encode($trans);
?>;
</script>
Then, extend the Vue prototype by the following to method (in your app.js):
Vue.prototype.trans = (key) => {
return _.get(window.trans, key, key);
};
Then, you can use trans() function in your Vue templates!
{{ trans('orders.add') }}
sorry, I would like to use your technique with this
'gte' => [ 'numeric' => 'The :attribute must be greater than or equal :value.', 'file' => 'The :attribute must be greater than or equal :value kilobytes.', 'string' => 'The :attribute must be greater than or equal :value characters.', 'array' => 'The :attribute must have :value items or more.', ],
it's possible?
br Max
@tomasbedrich, interesting approach. I was thinking to use the laracast Javascript package to send the translations to the view. I'm also using Vuex now. I'm not sure what the best approach is yet.
I make translation bundles and send them to my components. Something like this:
<auth-block
:lang="{{ transB('auth-block')->toJson() }}"
></auth-block>
@Quezler, ask @tomasbedrich
did you check if lodash is in your bootstrap.js or app.js?
@tomasbedrich, that's a pretty smart approach. thank you!
Very simple way to use the different language in vue component
Thanks for your solution
@tomasbedrich I use this
{{ trans('menus.about') }}
in my vue component.
But It doesn't display the content, it dispalys menus.about intead. How to fix it?
Depends on how your template looks, but maybe you could give inline-templates a go?
https://laracasts.com/series/learn-vue-2-step-by-step/episodes/15
@beestream Do you know how to implement it with database?
You may have a look at this Demo Application which uses the Laravel trans Feature in Vue:
Thanks @tomasbedrich for the solution. Works perfectly for me. I have to add a little method in my Vue script in order to translate strings inside the javascript (as opposed to the template)
translate(key) { return _.get(trans, key, key); }
I've used Lang.get('reminder.user') from the package https://github.com/andywer/laravel-js-localization
Also added some trans filter:
Vue.filter('trans', (key) => {
return Lang.get(key);
});
Been facing that requirement too.
Although several solutions offered worked fine, I wonder if it's not easier to have both the JS and PHP (lang) files statically generated by some code server-side each time messages are updated.
Two benefits: less time/cpu-consuming + you can generate everything from easier to update files for non-technical people (plus avoid the risk of someone putting harmful stuff in the files).
Going to go that way, possibly feeding JS+PHP from PO files...
I have a different approach. Since in most of the cases we are talking about static transaltions while using VueJS the simplest thing is to move what has to be translated outside of Vue script into blade template. Here is the example of my original code:
Vue.component('vue-google-autocomplete', {
template: `
<input
ref="autocomplete"
name="locality"
type="text"
required="required"
:class="classname"
:id="id"
:placeholder="Start typing name or postal code..."
v-model="autocompleteText"
@focus="onFocus()"
@blur="onBlur()"
@change="onChange"
@keypress.enter.prevent="onKeyPress"
>
`,
and in blade
<vue-google-autocomplete></vue-google-autocomplete>
Then I figured out that the simplest thing to do will be to move placeholder outside of vue like so:
Vue.component('vue-google-autocomplete', {
template: `
<input
ref="autocomplete"
name="locality"
type="text"
required="required"
:class="classname"
:id="id"
v-model="autocompleteText"
@focus="onFocus()"
@blur="onBlur()"
@change="onChange"
@keypress.enter.prevent="onKeyPress"
>
`,
and blade will then look like this including transaltion:
<vue-google-autocomplete placeholder="{{__('Start typing name or postal code...')}}"></vue-google-autocomplete>
As you can see i'm using strings as keys for translation. Simple solution and it works.
Maybe this package is perfect for you:
I use this simple method.. it works like blade..
var appMenu = new Vue({
el: '#app-menu',
data: {
menuitems:{!! $menuitems !!}},
lang:{
menu:{!! json_encode(__('menu')) !!},
something:{!! json_encode(__('something')) !!}
}
},
methods:{
__:function(key)
{
if (key.match(/\./))
{
var str = key.split(".")
if (typeof this.lang[str[0]] !== "undefined" && typeof this.lang[str[0]][str[1]] !== "undefined")
return this.lang[str[0]][str[1]]
else
return key
}
else
return key;
}
}
});
I can use it like this:
<li v-for="item in menuitems">
@{{__(item.name)}}
</li>
Of course we can seperate __() function to use every where..
I have done this by using props: ['lang'].
And while using component,
<register lang="{{ json_encode(__('register')) }}"> </register>
I have used this package (https://github.com/rmariuzzo/Laravel-JS-Localization) and it has worked really well for me.
Regarding:
TypeError: _.get is not a function
You may need to import _ from 'lodash'; above the Vue.prototype.trans code
@codebyjeff Thanks for the solution
Not sure if this is still a thing, but in my case I used
Vue.prototype.trans = (key) => {
return window.trans[_.findKey(window.trans,key)][key];
};
to first get which file included the key pair and then return the correct key.
We have our keywords nested with dots
like in our keyword.php
we have
'product-page.title' => 'Product :test',
'product-page.action.share' => 'Share',
hence the trans('keyword.product-page.action.share') wouldnt work
just wanna share my two cents of how i made this work:
Vue.prototype.trans = (key) => {
let file_prefix = key.substr(0,key.indexOf('.'));
let keyword_suffix = key.substr(key.indexOf('.')+1);
let result = window.trans[file_prefix][keyword_suffix];
if (result === undefined){
return key;
} else {
return result;
}
};
@tomasbedrich I have set it as it is like you have commented on your answer but getting this error on
Vue.prototype.trans = (key) => { return _.get(window.trans, key, key); };
Cannot set properties of undefined (setting 'trans')
Please or to participate in this conversation.