Pregunta

Tengo algunos botones de navegación en una aplicación web estilo asistente de Angular.Por razones estéticas, es necesario eliminarlos de cada parcial y agregarlos a la raíz "index.html":

<!-- Global navigation buttons for all partials -->
<div class="navbar navbar-fixed-top">
    <button class="btn btn-default" back-action>Back</button>
    <button class="btn btn-default" next-action>Next</button>
</div>

<div class="container ng-view ng-cloak">
     <!-- Partials rendered in here, managed by $routeProvider-->
</div>

Intenté aislar esta lógica usando directivas y variables de alcance para vincular el evento de clic y aplicar destinos de destino para cada parcial:

.directive('nextAction', ['$location', function($location) {
    return {
        restrict: 'A',
        link: function(scope, elm) {
            elm.on('click', function () {
               var nextUrl = scope.nextUrl;
               $location.url(nextUrl);
            });
        }
    };
}])

Luego, las URL se definen en cada controlador:

.controller('FirstStepCtrl', ['$scope', function ($scope) {
        $scope.backUrl = '/';
        $scope.nextUrl = '/first/second';
        ...

El problema es ese scope.nextUrl es indefinido ya que el alcance de la directiva no hereda el alcance del controlador.

Además del hecho de que actualmente no funciona, este enfoque también me parece un poco frágil ya que se basa en la lógica de navegación integrada en el código del controlador.

¿Cómo podría crear mejores botones globales de retroceso/siguiente que redireccionen dinámicamente en función de la "página" actual?

¿Fue útil?

Solución

Utilice un administrador de estado para manejar las URL anteriores y siguientes.Relevar a los responsables del tratamiento de esta responsabilidad.Luego inyéctelo en las directivas que manejan los botones Atrás y Siguiente.

.factory('stateMgr', ['$rootScope', function ($rootScope) {
    var stateMgr = {
        backUrl: '',
        nextUrl: ''
    };

    $rootScope.$on('$routeChangeSuccess', function (nextRoute, lastRoute) {
        // logic in here will look at nextRoute and then set back and next urls
        // based on new route   
        // e.g. stateMgr.backUrl = '/'; stateMgr.nextUrl = '/whatever';
    });

    return stateMgr;
}]);

entonces

.controller('FirstStepCtrl', ['$scope', function ($scope) {
    // do not need to do anything with back/next urls in here
    ...

y

.directive('nextAction', ['$location', 'stateMgr', function($location, stateMgr) {
    return {
        restrict: 'A',
        link: function(scope, elm) {
            elm.on('click', function () {
                $location.url(stateMgr.nextUrl);
            });
        }
    };
}])
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top