Update
I've put together an Angular "plugin" (module+filters+factory) called ngCss that handles this and much more - check it out!
I also have made a Vanilla Javascript (e.g. no external dependencies) version as well; CjsSS.js (GitHub).
ngCss is a tiny* Angular Module+Factory+Filters that enables binding of strings and objects (including nested objects) within CSS.
*Minified+compressed script under 1,700 bytes
Features:
- CSS can be live-bound (changes in
$scope are $watch'ed) or updated via the custom $broadcast event updateCss.
- css and cssInline Filters output Javascript/JSON
objects as CSS to enable mixins, including the ability to nest objects.
$scope can be initialized within the CSS itself, allowing for all CSS-related information to be co-located within the *.css or STYLE element.
$scope can be isolated or imported from any Angular $element (via angular.element($element).scope()).
Original
Thanks to @jonnyynnoj's code I've figured out a way to keep the {{angular_variable}} nomenclature within the style tags as well as live binding any changes. Check out the fork of @jonnyynnoj's code for a simple example or have a look below at what I'm using in my apps:
(function (ngApp) {
'use strict';
//# Live bind a <style cn-styler="{ commented: true, usingSingleQuote: true }" /> tag with {{ngVars}}
ngApp.directive('cnStyler', function () {
return {
//# .restrict the directive to attribute only (e.g.: <style cn-styler>...</style>)
restrict: "A",
link: function ($scope, $element, $attrs, controllers) {
//# .$eval the in-line .options and setup the updateCSS function
//# NOTE: The expected string value of the inline options specifies a JSON/JavaScript object, hence the `|| {}` logic
var css, regEx,
options = $scope.$eval($attrs["cnStyler"]) || {},
updateCSS = function () {
//# .$eval the css, replacing the results back into our $element's .html
$element.html($scope.$eval(css));
}
;
//# Setup the .quote and the inverse in .unquote (which we use to process the css)
//# NOTE: In theory, the .unquote should not be present within the css
options.quote = (options.usingSingleQuote !== false ? "'" : '"');
options.unquote = (options.quote === '"' ? "'" : '"');
regEx = new RegExp(options.unquote, "g");
//# Process the $element's .html into css, .replace'ing any present .unquote's with .quote's (this could cause problems), then the {{Angular}} (or /*{{Angular}}*/) variables with ' + stringified_versions + '
if (options.commented !== false) {
css = options.unquote + ($element.html() + '')
.replace(regEx, options.quote)
.replace(/\/\*{{/g, options.unquote + "+")
.replace(/}}\*\//g, "+" + options.unquote)
+ options.unquote;
} else {
css = options.unquote + ($element.html() + '')
.replace(regEx, options.quote)
.replace(/{{/g, options.unquote + "+")
.replace(/}}/g, "+" + options.unquote)
+ options.unquote;
}
//# .$watch for any changes in the $scope, calling our updateCSS function when they occur
$scope.$watch(updateCSS);
}
};
});
})(YOUR_NG_APP_VAR_HERE);
Then you use this directive like this:
<style cn-styler type="text/css">
.myClass{
color: /*{{themeColor}}*/;
}
</style>
Where you have set $scope.themeColor somewhere in your controller and you've replaced YOUR_NG_APP_VAR_HERE with your ngApp variable.
NOTES:
Make sure that your ng-controller is defined with scope to the <style> tag as <style> tag's should be in the <head> while ng-controller is generally defined on the <body> tag or below. TL;DR: Put your ng-controller on your <html> tag like so:
<html ng-app="YOUR_NG_APP_VAR_HERE" ng-controller="MyNgController">
Due to CSS parsing and auto-formatting in tools like Visual Studio I added the feature to have the {{Angular}} vars within CSS comments (e.g. /*{{Angular}}*/). This is the default behavior of the directive unless you override it like so:
<style cn-styler="{commented: false}" >...</style>
Due to the nature of this solution (the CSS is .$evaluated as a string with variables inserted within), the presence of single or double quotes within the CSS also needs to be processed. By default, the directive assumes you are using single quotes (') within your CSS which means in order to avoid any introduced errors you should only use single quotes within your CSS as any double quotes present within the CSS will be replaced with single quotes. You can override this default behavior (meaning you're using double quotes within your CSS) like so:
<style cn-styler="{usingSingleQuote: false}" >...</style>
There are edge cases where the replacing of double quotes with single quotes screws up the CSS (such as in content), so you will want to ensure that you are only using one style of quotes in your CSS (and signaling the directive accordingly) to avoid any potential issues. Thankfully quotes are rarely used in CSS so this is mostly a non-issue.
ng-classdocs.angularjs.org/api/ng.directive:ngClass . Where is this code located?