Steffi
Steffi

Reputation: 7087

Scope not updated in AngularJS

I have just started using AngularJS. I've done the tutorial from the official site. I tried to start my own web application.

I would like to "resize" and "cut" a div.

I started by trying resize div but the problem is the scope is never updated on mouse move. When I mousedown on div.tool (red div). I created a directive named resize direct.

I don't understand why my scope is not updated.

Edit : My scope is updated in the console.log(...), but not in the view index.html

Thanks

enter image description here

Here is my code :

index.html :

<div class="roadmap" ng-app="dragApp" ng-controller="dragCtrl">
<div class="time">
  <div class="duree" resizedirect ng-style="{ width: myWidth }">
     <div class="tool"></div>
  </div>
</div>
</div>

js/directives.js :

'use strict';

var dragDirectives = angular.module('dragDirectives', []);

dragDirectives.directive('resizedirect', function() {
return {
restrict: 'A',
link: function(scope, element, attr) {
  scope.name = "Third ";
  scope.myWidth = "100px";

  var resizer = element.find(".tool")[0];
  console.log(resizer);
  resizer.addEventListener('mousedown', scope.initDrag, false);

  var startX, startY, startWidth, startHeight;

  scope.initDrag = function(e) {
     startX = e.clientX;
     startY = e.clientY;
     startWidth = parseInt(element.css("width"), 10);
     resizer.addEventListener('mousemove', scope.doDrag, false);
     resizer.addEventListener('mouseup', scope.stopDrag, false);
  }

  scope.doDrag = function(e) {
     //console.log( (startWidth + e.clientX - startX) + 'px' );
     startWidth = parseInt(element.css("width"), 10);
     scope.myWidth = (startWidth + e.clientX - startX) + 'px';
     scope.myWidth = "200px";
     console.log(scope.myWidth);
  }

  scope.stopDrag = function(e) {
      resizer.removeEventListener('mousemove', scope.doDrag, false);    
      resizer.removeEventListener('mouseup', scope.stopDrag, false);
  }

}

}
})

js/app.js :

'use strict';

var dragApp = angular.module('dragApp', [
  'ngRoute',
  'dragDirectives'
]);

Upvotes: 2

Views: 673

Answers (2)

a better oliver
a better oliver

Reputation: 26848

Expressions like { width: myWidth } are evaluated whenever the scope is updated. When you update the scope within an event listener, then you know, but angular does not know that the scope has been changed.

In order to tell angular that the scope has been changed you need to call scope.$apply() after the change. This tells angular that something has changed and the expressions might need to be evaluated again.

scope.doDrag = function(e) {
  //console.log( (startWidth + e.clientX - startX) + 'px' );
  startWidth = parseInt(element.css("width"), 10);
  scope.myWidth = (startWidth + e.clientX - startX) + 'px';
  scope.myWidth = "200px";
  scope.$apply();

Upvotes: 2

Mosho
Mosho

Reputation: 7078

var resizer = element.find(".tool")[0];

This doesn't work. From the docs:

find() - Limited to lookups by tag name

You can use this instead:

var resizer = element.children()[0]

But I think it would be best if you create the div in the directive:

var resizer = angular.element('<div class="tool" />');
element.append(resizer);

Upvotes: 0

Related Questions