Work with $ionicSlideBoxDelegate and ng-repeat in beta6

Hi everyone,

I’m getting trouble to get the $ionicSlideBoxDelegate working with ng-repeat.
I created a CodePen to show my problem : http://codepen.io/anon/pen/ekDjt

The delegate-handle seems to not work so I can’t set the wanted slide on slider start.
Any idea ?

Thanks a lot

Hi,

I updated with beta7 but it didn’t fix the problem.
I made a dirty hack to get it working ( http://codepen.io/anon/pen/Ckygn ) but it’s not ideal and I can’t access to $ionicSlideBoxDelegate…

If anyone has an idea, I will be really glad.

You’re not injecting IonSlideBoxDelegate in your controller:

.controller('MyCtrl', function($scope) {

should be:

.controller('MyCtrl', function($scope, $ionSlideBoxDelegate) {

Thanks for your response.

But I don’t understand why $ionicSlideBoxDelegate is needed in controller. It’s only used in directive…
Anyway, it didn’t seems to sole the problem :frowning:

Please read up on http://ionicframework.com/docs/api/service/$ionicSlideBoxDelegate/

If you want to update a slidebox after the page is compiled, you need to run $ionicSlideBoxDelegate.update(); from your controller.

If you don’t inject $ionicSlideBoxDelegate in your controller, all the methods that that delegate provides (stop(), update(), slideTo(), etc.) won’t work.

I read the doc but I can’t figure out how to get it working (even with update()).

Can you correct this CodePen : http://codepen.io/anon/pen/wepsd ?

Thanks a lot for helping.

Just noticed you’re calling the slideTo function from your directive, instead of the controller.

Also, not quite sure why you would want to create a directive for this, seems the vanilla IonSlideBox would suit your needs just fine. I’ll see if I can fix your example.

The code is the simplest example for demonstrating my problem.
In my app, this slidebox is a bit more complicated and I made the directive because I want to create a reusable component…

Do you think there is a scope problem in the directive ?

I was having this issue as well, the problem is I am generating the slide boxes dynamically, which means the delegate-handles are supposed to be generated by angular, when I logged the $ionicSlideBoxDelegate, I could see that it had six instances but their delegate-handles weren’t being interpolated, they had the angular code as a string: “slider-{{id}}”, and I kept getting this error:

Delegate for handle “slider-4” could not find a corresponding element with delegate-handle=“slider-4”! enableSlide() was not called!
Possible cause: If you are calling enableSlide() immediately, and your element with delegate-handle=“slider-4” is a child of your controller, then your element may not be compiled yet. Put a $timeout around your call to enableSlide() and try again.

For this to work, I had to modify the slidebox source code, what I did was to add the delegateHandle attribute in the scope, so this way it is interpolated.

Like this:

scope: {
    ...,
    delegateHandle: '@'
}

and then I changed this line of code:

var deregisterInstance = $ionicSlideBoxDelegate._registerInstance(slider, $attrs.delegateHandle);

to:

var deregisterInstance = $ionicSlideBoxDelegate._registerInstance(slider, $scope.delegateHandle);

My delegate-handles are now being interpolated and I can also access the handles correctly.

Not sure if this is a “good” solution, hope it helps![quote=“loicknuchel, post:1, topic:5587, full:true”]
Hi everyone,

I’m getting trouble to get the $ionicSlideBoxDelegate working with ng-repeat.
I created a CodePen to show my problem : http://codepen.io/anon/pen/ekDjt

The delegate-handle seems to not work so I can’t set the wanted slide on slider start.
Any idea ?

Thanks a lot
[/quote]

1 Like

I also had to follow @mlv’s strategy. I defined my own ionSlideBox directive with a higher priority, that was almost identical to the regular ionSlideBox directive, but included @mlv’s overrides.

angular.module('ion-slide-box-override', [

])
.config(function($provide){
    $provide.decorator('ionSlideBoxDirective', ['$delegate', function($delegate) {
        //$delegate is array of all ng-click directive
        //in this case first one is angular buildin ng-click
        //so we remove it.
        $delegate.shift();
        return $delegate;
    }]);
})
.directive('ionSlideBox', function($timeout, $compile, $ionicSlideBoxDelegate, $ionicHistory) {
  return {
    restrict: 'E',
    replace: true,
    transclude: true,
    prioriy: 10000000,
    scope: {
      autoPlay: '=',
      doesContinue: '@',
      slideInterval: '@',
      showPager: '@',
      pagerClick: '&',
      disableScroll: '@',
      onSlideChanged: '&',
      delegateHandle: '@',
      activeSlide: '=?'
    },
    controller: ['$scope', '$element', '$attrs', function($scope, $element, $attrs) {
      var _this = this;
      function isDefined(value) {return typeof value !== 'undefined';}
      var continuous = $scope.$eval($scope.doesContinue) === true;
      var shouldAutoPlay = isDefined($attrs.autoPlay) ? !!$scope.autoPlay : false;
      var slideInterval = shouldAutoPlay ? $scope.$eval($scope.slideInterval) || 4000 : 0;

      var slider = new ionic.views.Slider({
        el: $element[0],
        auto: slideInterval,
        continuous: continuous,
        startSlide: $scope.activeSlide,
        slidesChanged: function() {
          $scope.currentSlide = slider.currentIndex();

          // Try to trigger a digest
          $timeout(function() {});
        },
        callback: function(slideIndex) {
          $scope.currentSlide = slideIndex;
          $scope.onSlideChanged({ index: $scope.currentSlide, $index: $scope.currentSlide});
          $scope.$parent.$broadcast('slideBox.slideChanged', slideIndex);
          $scope.activeSlide = slideIndex;
          // Try to trigger a digest
          $timeout(function() {});
        }
      });

      slider.enableSlide($scope.$eval($attrs.disableScroll) !== true);

      $scope.$watch('activeSlide', function(nv) {
        if(angular.isDefined(nv)){
          slider.slide(nv);
        }
      });

      $scope.$on('slideBox.nextSlide', function() {
        slider.next();
      });

      $scope.$on('slideBox.prevSlide', function() {
        slider.prev();
      });

      $scope.$on('slideBox.setSlide', function(e, index) {
        slider.slide(index);
      });

      //Exposed for testing
      this.__slider = slider;

      var deregisterInstance = $ionicSlideBoxDelegate._registerInstance(
        slider, $scope.delegateHandle, function() {
          return $ionicHistory.isActiveScope($scope);
        }
      );
      $scope.$on('$destroy', deregisterInstance);

      this.slidesCount = function() {
        return slider.slidesCount();
      };

      this.onPagerClick = function(index) {
        void 0;
        $scope.pagerClick({index: index});
      };

      $timeout(function() {
        slider.load();
      });
    }],
    template: '<div class="slider">' +
      '<div class="slider-slides" ng-transclude>' +
      '</div>' +
    '</div>',

    link: function($scope, $element, $attr, slideBoxCtrl) {
      // If the pager should show, append it to the slide box
      if($scope.$eval($scope.showPager) !== false) {
        var childScope = $scope.$new();
        var pager = jqLite('<ion-pager></ion-pager>');
        $element.append(pager);
        $compile(pager)(childScope);
      }
    }
  };}
)

I am having the same issue, I will use the custom directive until a formal solution is found. Thanks.