问题描述
我已经看到了一些角国际化插件,但我不想重新发明轮子。 i18next是一个好的图书馆,因此,我打算使用它。
I have seen some i18n plugins for Angular but I don't want to re-invent the wheel. i18next is a good library and so, I intend to use it.
我创建了一个国际化的指令而只是调用国际化库:
I have created a directive i18n which just calls i18n library:
define(['app', 'jquery', 'i18n'], function(app, $, i18n) {'use strict';
app.directive('i18n', function() {
return function($scope, elm, attrs) {
attrs.$observe('i18n', function(value) {
if ($.fn.i18n) {// for some reason, it isn't loaded quickly enough and first directives process fails
$(elm).i18n();
}
});
};
});
});
在我的网页,我可以在飞行中改变语言:
On my page, I can change language on the fly:
<a ng-repeat="l in languages"> <img ng-src="images/{{l.id}}.png" title="{{l.label}}" ng-click="setLanguage(l.id)" /> </a>
现在,我的主控制器上的HTML标记定义的:
Now, my main controller defined on html tag:
define(['app', 'i18n', 'jquery'], function(app, i18n, $) {'use strict';
return app.controller('BuilderController', ['$scope', '$location',
function BuilderController($scope, $location) {
/* Catch url changes */
$scope.$watch(function() {
return $location.path();
}, function() {
$scope.setLanguage(($location.search()).lang || 'en');
});
/* Language */
$scope.languages = [{
id : "en",
label : "English"
}, {
id : "fr",
label : "Français"
}];
$scope.$watch('language', function() {
$location.search('lang', $scope.language);
i18n.init({
resGetPath : 'i18n/__lng__/__ns__.json',
lng : $scope.language,
getAsync : false,
sendMissing : true,
fallbackLng : 'en',
debug : true
});
$(document).i18n();
});
$scope.setLanguage = function(id) {
$scope.language = id;
};
}]);
});
工作原理:在语言观察家初始化i18n的对象,新的语言环境,然后使用jQuery的国际化扩展更新所有DOM。这个特殊的活动之外,我只是指令(用国际化指令模板,并在以后时刻渲染)做的工作完全为所有其他任务。
How it works: watcher on language initialize i18n object with new locale and then update all DOM using i18n jquery extension. Outside of this special event, my directive just does the work perfectly for all other tasks (templates using i18n directive and rendered at a later moment).
虽然它工作正常,我知道我不应该操作DOM控制器内部,而是因为没有到底发生什么,我还没有找到一个更好的解决方案。
While it is working fine, I know I shouldn't manipulate DOM inside a controller but since nothing happens in the end, I haven't found a better solution.
在理想情况下,我想角度重新编译所有的DOM,解析所有指令更新标签,但我想不出如何做到这一点。
我曾尝试$ $范围适用():在这一点上不工作,因为已经消化
我已经使用Scope.onReady插件没有更好的效果。
Ideally, I want Angular to re-compile all DOM, parsing all directives to update labels but I can't figure how to do it.I have tried $scope.$apply() : not working because already in digest at this pointI have used Scope.onReady plugin without better results.
显然,我是很新的角度,它是相当困难的我了解的东西究竟是如何工作的。
Obviously, I'm very new to Angular and it's quite difficult for me to understand exactly how things work.
推荐答案
据我可以说,最好不要使用jQuery在所有的,因为它不是必需的。您可以使用i18next没有jQuery的,只需使用 window.i18n.t(YourStringToTranslate)
。 ;)
As far as I can say, it is better not to use jQuery at all, since it isn't required. You can use i18next without jQuery, by simply using window.i18n.t("YourStringToTranslate")
. ;)
由于您可以编写自己的指令,你也不需要使用的$(document).i18n中的();
。
为了这个目的我写了一个简单的指令来棱角分明。
Because you can write your own directive you also do not need to use $(document).i18n();
.For that purpose I have written a simple directive for Angular.
正如你所看到的,您不必使用jQuery,你在你的指令,也能更好初始化i18next而不是你的控制器。
As you can see, you don't have to use jQuery and you also better initialize i18next in your directive instead of your controller.
您可以通过simlpy使用它添加 NG-i18next =
属性为你想要的任何元素。
通过你的选项, $ rootScope.i18nextOptions
在code的任何地方(例如,在您的控制器)。然后,它会自动更新所有翻译内容。
You can use it by simlpy adding a ng-i18next=""
attribute to any element you want.Pass your options to $rootScope.i18nextOptions
anywhere in your code (for example in your controller). It then will automatically update all translated elements.
我编辑你的code,所以它与我的指令工作。
I edited your code, so it works with my directive.
define(['app', 'i18n', 'jquery'], function(app, i18n, $) {
'use strict';
return app.controller('BuilderController', ['$rootScope', '$scope', '$location',
function BuilderController($rootScope, $scope, $location) {
/* Catch url changes */
$scope.$watch(function() {
return $location.path();
}, function() {
$scope.setLanguage(($location.search()).lang || 'en');
});
/* Language */
$scope.languages = [{
id : "en",
label : "English"
}, {
id : "fr",
label : "Français"
}];
// This has changed
$scope.$watch('language', function() {
$location.search('lang', $scope.language);
$rootScope.i18nextOptions = {
resGetPath : 'i18n/__lng__/__ns__.json',
lng : $scope.language,
getAsync : false,
sendMissing : true,
fallbackLng : 'en',
debug : true
};
});
$scope.setLanguage = function(id) {
$scope.language = id;
};
}]);
});
请注意,你必须设定的指令为您的应用程序的依赖性。还包括无AMD +的jQuery的i18next版本。
如果你需要更多的细节,他们在精神可用。 ;)
Please note that you have to set the directive as a dependence of your app. Also include the i18next version without AMD+jQuery.If you need more details, they are available in the gist. ;)
现在有一个 i18next
角
在GitHub上可用的模块:的
There is now an i18next
angular
module available on GitHub: https://github.com/archer96/ng-i18next/
这篇关于角和i18next的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!