Using textangular functions in angular controller? - angularjs

I am new to angular and am trying to alter the default behavior of a textangular text input field on my site's backend (I am a guitarist, not a web developer, but can usually figure out what I need to do...). The field has an option to specify a youtube url and then textangular converts that to an image for purposes of editing in the backend. Then in front end textangular has means to have a youtube url displayed correctly as an iframe.
However, on the front end I am not using angular and I read that in my case, to get a youtube embed to show up in front end as iframe you have to use the taApplyCustomRenderers function.
For example, see here:
how to strip placeholder img in textAngular editor in scope var?
In my angular app, here are some of the relevant lines:
angular.module('dashboard')
.controller('EditController', ['$scope', '$http', '$location', '$routeParams', function ($scope, $http, $location, $routeParams) {
$scope.save = function () {
$scope.busy = true;
// I thoguht I could do this:
$scope.somefield = taApplyCustomRenderers($scope.somefield);
// then I would save to model
});
I am getting error that taApplyCustomRenderers is undefined. I thought based on what I read that taApplyCustomRenderers is an available function when using textangular but being new to this I suppose I am missing some key step about injecting the function into the controller or something.
Hoping someone can shed some light.
Thanks in advance!
Brian

TLDR; When you try to access taApplyCustomRenderers you are recieving an error since it is not given to this current function, Inject the function and it will work.
The Problem
While I have never actually tried using textAngular, let me explain what the problem is, and from there it should be easy to find the solution.
Your EditController is just a regular javascript function that gets run and attached to the relevant DOM element, so it only has access to functions that are declared in its own scope (or globally).
Here is your exact code just indented differently so you can understand better:
angular.module('dashboard').controller(
'EditController',
[
'$scope',
'$http',
'$location',
'$routeParams',
function ($scope, $http, $location, $routeParams) {
...
$scope.somefield = taApplyCustomRenderers($scope.somefield);
}
]
);
As you can see, the controller function has two parameters, the first being a string and the second an array, and the last element in the array is just a regular function.
The solution
Checking the textAngular documentation I saw that the taApplyCustomRenderers is a factory, which means you can inject it into your controller function as so:
angular.module('dashboard').controller('EditController',
['$scope', '$http', '$location', '$routeParams', 'taApplyCustomRenderers',
function ($scope, $http, $location, $routeParams, taApplyCustomRenderers) {
taApplyCustomRenderers(); // is now Available.
}
]);

Related

Angularjs - Refresh Control

I am a novice, and don't fully understand functions and how/where they are called but I want to refresh a control that has buttons on it that can be enabled/disabled based on state of something else.
The state is determined when the html for that ctrl is loading.
Question is:
For this control, will the reload() command reload only the TaskCtrl, or the entire web page containing all controls? I don't want to reload the entire page.
var mainCtrl = angular.module('MyCtrl', []);
mainCtrl.controller('TaskCtrl', ['$scope', '$routeParams', '$window', '$location', '$rootScope', '$log',
function($scope, $routeParams,
$window, $location, $rootScope, $log)
{
$scope.loadStuff = function() {
.......
$scope.studyToken = ret.studyToken;
$scope.studies = ret.studies;
$window.location.reload();
}
I notice that "loadStuff" function is in another control so I'm assuming that this is a "scope" function that when it executes it can be local in other controls and perform other functions in that control when it executes?
Any suggestions on references for learning these concepts are welcome.

How to make a generic close button for angular ui-views?

I need a function where I can use $window.history.back() to be called from every view regardless of what controller is controlling that page.
.run(['$rootScope', '$state', 'CommonUserModel', 'InitialiseService','$window', function($rootScope, $state, $window, commonUserModel, initialiseService) {
$rootScope.link = function(){
$window.history.back();
};
So I have this function put in the app module. Injected window object because it complained about it. But now it also complains that it "Cannot read property 'back' of undefined".
I am calling this function with $rootScope from other controllers as I read through StackOverflow. I had to inject $rootScope to other controllers like this.
homeViewModule.controller("simDetailsController", [ '$rootScope','$scope', 'ModalDialogService', 'CommonTagModel', '$location','$window',
function($scope, modalDialogService, commonTagModel, $location, $window,$rootScope) {
self.link = function(){
$rootScope.link();};
Can you give me an advice?
Keep in mind that I am pretty newbie on AngularJS I still don't get this messy, complex framework.
The order in which you have injected $window & $rootScope in the parameters list does not match the string array list.
You have mentioned '$window' as the 5th element in the string array, while, it is the 3rd element in the parameters list.
Also, in your code, '$rootScope' is the 1st element in the string array, while, it is the 6th element in the parameters list.
Replace the first lines in both of your code snippets with these:
.run(['$rootScope', '$state', 'CommonUserModel', 'InitialiseService','$window', function($rootScope, $state, commonUserModel, initialiseService, $window) {
homeViewModule.controller("simDetailsController", [ '$rootScope','$scope', 'ModalDialogService', 'CommonTagModel', '$location','$window',
function($rootScope, $scope, modalDialogService, commonTagModel, $location, $window) {
You should use routes:
https://docs.angularjs.org/api/ngRoute/service/$route

Different ways to initialize AngularJS Controllers? [duplicate]

I see the following angularjs controller syntax structure all the time.
angular.module('7minWorkout').controller('WorkoutController',
['$scope', '$interval', '$location',
function ($scope, $interval, $location)
{
}]);
Why the repetition in the parameter names? Why not just like this
angular.module('7minWorkout').controller('WorkoutController',
['$scope', '$interval', '$location',
function ()
{
}]);
or
angular.module('7minWorkout').controller('WorkoutController',
[
function ($scope, $interval, $location)
{
}]);
The array syntax will help you with minification/uglify of your js code.
angular.module('7minWorkout').controller('WorkoutController',
function ($scope, $interval, $location) {
// code here
});
Will be minified and mangled as:
angular.module('7minWorkout').controller('WorkoutController',
function (a, b, c) {
// code here
});
So Angular won't be able to figure out which dependencies to inject
On the other hand, using the array declaration:
angular.module('7minWorkout').controller('WorkoutController',
['$scope', '$interval', '$location', function ($scope, $interval, $location) {
// code here
}]);
Will be minified as :
angular.module('7minWorkout').controller('WorkoutController',
['$scope', '$interval', '$location', function (a, b, c) {
// code here
}]);
So Angular will know what a, b and c represent.
There's also another way to inject variables if you use your first example code like below:
WorkoutController.$inject = ['$scope', '$interval', '$location'];
or
angular.module('7minWorkout').controller('WorkoutController', /* #ngInject */
function ($scope, $interval, $location) {
// code here
});
which will create the $inject method mentioned above when the code is annotated.
So, there are mainly four kinds of annotation:
Implicit Annotation - the first example code
Inline Array Annotation - the second example code
$inject Property Annotation - the $inject method
$ngInject Comment Annotation - the #ngInject method
ng-annotate
Tools like ng-annotate let you use implicit dependency annotations in your app and automatically add inline array annotations prior to minifying. If you decide to take this approach, you probably want to use ng-strict-di.
For more information, see AngularJS Developer Guide - Using Strict Dependency Injection.
This "repetion" is to make it safe for minification:
AngularJS - Controllers, Dependencies, and Minification
or you can use following syntax, according to popular angular-styleguide https://github.com/johnpapa/angular-styleguide
angular.module('7minWorkout')
.controller('WorkoutController', WorkoutController);
WorkoutController.$inject = ['$scope', '$interval', '$location'];
function WorkoutController($scope, $interval, $location) {
}
You could write the first version since it just omits the parameters of the function which are also accesible via arguments inside the function. So you would avoid the repition but slicing the arguments property is also not really efficient (compared to just type out the parameters).
As the others answers stated the repition is to make it safe for minification.
The first controller syntax makes it possible to minify/uglify the javascript code with the use of tools like ngmin. I'm not quite sure if the 2nd and 3rd options you have provided are viable options to create a controller, but in any case they will not be minified correctly since the tools will not now what the providers are. I would either suggest to use option 1 or option 3 (without the brackets) to create a controller. Note that option 3 will not be minified correctly by automated tools.
Some Useful information about creating controllers:
AngularJS Developer Guide - Controllers
option3 without brackets
angular.module('7minWorkout').controller('WorkoutController', function ($scope, $interval, $location)
{
//Your Code
});

$timeout is not a function error

Hey guys got a little problem that i cant seem to see the problem for. Im building an angular application and im getting the error stated in the question title. Ive injected the $timeout to the controller but im still getting an error with this bit of code can some one tell me where i may be going wrong?
cheers
(function() {
'use strict';
angular
.module('my.module')
.controller('NewSearchController', NewSearchController);
NewSearchController.$inject = ['$rootScope', '$scope', '$location','UserService',
'SearchService', '$window', '$controller', '$mdDialog', 'ModalService', '$routeParams', '$timeout'];
/**
* #namespace ContactController
*/
function NewSearchController($rootScope, $scope, $location, UserService, SearchService, $window, $controller, $mdDialog, $routeParams, $timeout)
Timeout code:
var timerMax = false;
$scope.$watch(NewSearchController.searchObject.maxDayRate, function(){
if(timerMax) {
$timeout.cancel(timerMax);
}
timerMax= $timeout(function() {
NewSearchController.updateSearchFilters();
}, 5000);
});
The problem is in your injection: 'ModalService' listed as injectable but not one of the parameters so angular will inject 'ModalService' and the values you get for parameters later in the list are all wrong.
If you use something like gulp to build your app then use gulp-ng-annotate to build the injection list automatically. That way it won't go wrong and you never have to worry about it.
'$mdDialog', 'ModalService', '$routeParams', '$timeout']
$mdDialog, $routeParams, $timeout
these two dnt match Change it to
$mdDialog,ModalService, $routeParams, $timeout
you have injected $timeout at position 11th position in controller but in function it is at 10th position as u have missed ModalService in function.So the error is just because of this . You need to inject and add the dependcies at same position otherwise it wont work.

Why does an Angular controller that is a function work, but a controller in a package does not?

In a recent question, I was having an issue with a simple modal dialog implemented using Angular UI for Bootstrap.
I started with this fiddle, and the person who answered came up with this result.
However, one thing immediately caught my attention!
Old Controller Implementation
var controllers = angular.module('app.controllers', []);
controllers.controller('ModalController', ['$scope', '$modal', '$log',
function ($scope, $modal, $log) {
// Overarching controller code...
}
]);
controllers.controller('ModalInstanceController', ['$scope', '$modalInstance',
function ($scope, $modalInstance, params) {
// ...Modal Instance Code...
}
]);
This code does not work with the Angular UI for Bootstrap Modal, but for some reason, this code does:
var ModalController = function($scope, $modal, $log) {
// Overarching controller code...
};
var ModalInstanceController = function($scope, $modalInstance, params) {
// Modal Instance Code...
};
...The problem being, that AngularJS code is usually modularized like the first example to avoid cluttering the global namespace.
So far none of my experiments have been able to get a modularized setup to succeed in the first place. I attempted some simple substitutions, where I would make one controller or the other be a modularized controller, in hopes that it was only one controller preventing the params from being passed between controllers; this turned out not to be the case. Implementing $scope.params = []; before declaring the $scope.open() function, and populating $scope.params in the open function similarly had no effect.
Question: In the context of the AngularUI for Bootstrap system, why does the modularized approach fail? And more importantly, how can I make it work?
Here is your fixed plnkr (http://jsfiddle.net/pEmXt/4/), it had several problems:
You defined your modules in the wrong order.
You had the ui DI in the wrong place.
Your resolve syntax was wrong.
The DI in your modal instance controller was missing an item in the list of dependencies.
The resolve method is used like this:
resolve: {
objectName: function(){
return myObject;
}
}
OK...so I recently ran into same issue and was perplexed also. I just never bothered to dig into it. A quick trip to angular-ui github repo and I found out in the issue tracker.
Angular-Ui demos are passing a function reference as controller. For a modular controller it needs to be a string
var modalInstance = $modal.open({
templateUrl: 'myModalContent.html',
controller: 'ModalInstanceCtrl', /* use string for modular controller */
/* OR */
controller: ModalInstanceCtrl, /* use reference for controller as function*/
});
Issue tracker reference: https://github.com/angular-ui/bootstrap/issues/2330
Working demo from issue tracker: http://plnkr.co/edit/38vBcPalBBNMgYis4cZX?p=preview
In the first example, the module 'app.controllers' has to be added to the list of dependencies for the main app.
var app = angular.module('app', ['app.controllers']);
In the second instance the controllers are global functions and therefore are visible without being explicitly added as a dependency.

Resources