| Index: third_party/polymer/v0_8/components-chromium/polymer/src/lib/style-transformer-extracted.js
|
| diff --git a/third_party/polymer/v0_8/components-chromium/polymer/src/lib/style-transformer-extracted.js b/third_party/polymer/v0_8/components-chromium/polymer/src/lib/style-transformer-extracted.js
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..ef62f59413189370bdcc1c2f0ced594e4d4baf9d
|
| --- /dev/null
|
| +++ b/third_party/polymer/v0_8/components-chromium/polymer/src/lib/style-transformer-extracted.js
|
| @@ -0,0 +1,200 @@
|
| +
|
| +
|
| + (function() {
|
| +
|
| + /* Transforms ShadowDOM styling into ShadyDOM styling
|
| +
|
| + * scoping:
|
| +
|
| + * elements in scope get scoping selector class="x-foo-scope"
|
| + * selectors re-written as follows:
|
| +
|
| + div button -> div.x-foo-scope button.x-foo-scope
|
| +
|
| + * :host -> scopeName
|
| +
|
| + * :host(...) -> scopeName...
|
| +
|
| + * ::content -> ' ' NOTE: requires use of scoping selector and selectors
|
| + cannot otherwise be scoped:
|
| + e.g. :host ::content > .bar -> x-foo > .bar
|
| +
|
| + * ::shadow, /deep/: processed simimlar to ::content
|
| +
|
| + * :host-context(...): NOT SUPPORTED
|
| +
|
| + */
|
| +
|
| + // Given a node and scope name, add a scoping class to each node
|
| + // in the tree. This facilitates transforming css into scoped rules.
|
| + function transformDom(node, scope, useAttr, shouldRemoveScope) {
|
| + _transformDom(node, scope || '', useAttr, shouldRemoveScope);
|
| + }
|
| +
|
| + function _transformDom(node, selector, useAttr, shouldRemoveScope) {
|
| + if (node.setAttribute) {
|
| + transformElement(node, selector, useAttr, shouldRemoveScope);
|
| + }
|
| + var c$ = Polymer.dom(node).childNodes;
|
| + for (var i=0; i<c$.length; i++) {
|
| + _transformDom(c$[i], selector, useAttr, shouldRemoveScope);
|
| + }
|
| + }
|
| +
|
| + function transformElement(element, scope, useAttr, shouldRemoveScope) {
|
| + if (useAttr) {
|
| + if (shouldRemoveScope) {
|
| + element.removeAttribute(SCOPE_NAME);
|
| + } else {
|
| + element.setAttribute(SCOPE_NAME, scope);
|
| + }
|
| + } else {
|
| + // note: if using classes, we add both the general 'style-scope' class
|
| + // as well as the specific scope. This enables easy filtering of all
|
| + // `style-scope` elements
|
| + if (scope) {
|
| + if (shouldRemoveScope) {
|
| + element.classList.remove(SCOPE_NAME, scope);
|
| + } else {
|
| + element.classList.add(SCOPE_NAME, scope);
|
| + }
|
| + }
|
| + }
|
| + }
|
| +
|
| + function transformHost(host, scope) {
|
| + }
|
| +
|
| + // Given a string of cssText and a scoping string (scope), returns
|
| + // a string of scoped css where each selector is transformed to include
|
| + // a class created from the scope. ShadowDOM selectors are also transformed
|
| + // (e.g. :host) to use the scoping selector.
|
| + function transformCss(rules, scope, ext, callback, useAttr) {
|
| + var hostScope = calcHostScope(scope, ext);
|
| + scope = calcElementScope(scope, useAttr);
|
| + return Polymer.StyleUtil.toCssText(rules, function(rule) {
|
| + transformRule(rule, scope, hostScope);
|
| + if (callback) {
|
| + callback(rule, scope, hostScope);
|
| + }
|
| + });
|
| + }
|
| +
|
| + function calcElementScope(scope, useAttr) {
|
| + if (scope) {
|
| + return useAttr ?
|
| + CSS_ATTR_PREFIX + scope + CSS_ATTR_SUFFIX :
|
| + CSS_CLASS_PREFIX + scope;
|
| + } else {
|
| + return '';
|
| + }
|
| + }
|
| +
|
| + function calcHostScope(scope, ext) {
|
| + return ext ? '[is=' + scope + ']' : scope;
|
| + }
|
| +
|
| + function transformRule(rule, scope, hostScope) {
|
| + _transformRule(rule, transformComplexSelector,
|
| + scope, hostScope);
|
| + }
|
| +
|
| + // transforms a css rule to a scoped rule.
|
| + function _transformRule(rule, transformer, scope, hostScope) {
|
| + var p$ = rule.selector.split(COMPLEX_SELECTOR_SEP);
|
| + for (var i=0, l=p$.length, p; (i<l) && (p=p$[i]); i++) {
|
| + p$[i] = transformer(p, scope, hostScope);
|
| + }
|
| + rule.selector = p$.join(COMPLEX_SELECTOR_SEP);
|
| + }
|
| +
|
| + function transformComplexSelector(selector, scope, hostScope) {
|
| + var stop = false;
|
| + selector = selector.replace(SIMPLE_SELECTOR_SEP, function(m, c, s) {
|
| + if (!stop) {
|
| + var o = transformCompoundSelector(s, c, scope, hostScope);
|
| + if (o.stop) {
|
| + stop = true;
|
| + }
|
| + c = o.combinator;
|
| + s = o.value;
|
| + }
|
| + return c + s;
|
| + });
|
| + return selector;
|
| + }
|
| +
|
| + function transformCompoundSelector(selector, combinator, scope, hostScope) {
|
| + // replace :host with host scoping class
|
| + var jumpIndex = selector.search(SCOPE_JUMP);
|
| + if (selector.indexOf(HOST) >=0) {
|
| + // :host(...)
|
| + selector = selector.replace(HOST_PAREN, function(m, host, paren) {
|
| + return hostScope + paren;
|
| + });
|
| + // now normal :host
|
| + selector = selector.replace(HOST, hostScope);
|
| + // replace other selectors with scoping class
|
| + } else if (jumpIndex !== 0) {
|
| + selector = scope ? transformSimpleSelector(selector, scope) : selector;
|
| + }
|
| + // remove left-side combinator when dealing with ::content.
|
| + if (selector.indexOf(CONTENT) >= 0) {
|
| + combinator = '';
|
| + }
|
| + // process scope jumping selectors up to the scope jump and then stop
|
| + // e.g. .zonk ::content > .foo ==> .zonk.scope > .foo
|
| + var stop;
|
| + if (jumpIndex >= 0) {
|
| + selector = selector.replace(SCOPE_JUMP, ' ');
|
| + stop = true;
|
| + }
|
| + return {value: selector, combinator: combinator, stop: stop};
|
| + }
|
| +
|
| + function transformSimpleSelector(selector, scope) {
|
| + var p$ = selector.split(PSEUDO_PREFIX);
|
| + p$[0] += scope;
|
| + return p$.join(PSEUDO_PREFIX);
|
| + }
|
| +
|
| + function transformRootRule(rule) {
|
| + _transformRule(rule, transformRootSelector);
|
| + }
|
| +
|
| + function transformRootSelector(selector) {
|
| + return selector.match(SCOPE_JUMP) ?
|
| + transformComplexSelector(selector) :
|
| + selector.trim() + SCOPE_ROOT_SELECTOR;
|
| + }
|
| +
|
| + var SCOPE_NAME = 'style-scope';
|
| + var SCOPE_ROOT_SELECTOR = ':not([' + SCOPE_NAME + '])' +
|
| + ':not(.' + SCOPE_NAME + ')';
|
| + var COMPLEX_SELECTOR_SEP = ',';
|
| + var SIMPLE_SELECTOR_SEP = /(^|[\s>+~]+)([^\s>+~]+)/g;
|
| + var HOST = ':host';
|
| + // NOTE: this supports 1 nested () pair for things like
|
| + // :host(:not([selected]), more general support requires
|
| + // parsing which seems like overkill
|
| + var HOST_PAREN = /(\:host)(?:\(((?:\([^)(]*\)|[^)(]*)+?)\))/g;
|
| + var CONTENT = '::content';
|
| + var SCOPE_JUMP = /\:\:content|\:\:shadow|\/deep\//;
|
| + var CSS_CLASS_PREFIX = '.';
|
| + var CSS_ATTR_PREFIX = '[' + SCOPE_NAME + '~=';
|
| + var CSS_ATTR_SUFFIX = ']';
|
| + var PSEUDO_PREFIX = ':';
|
| +
|
| + // exports
|
| + Polymer.StyleTransformer = {
|
| + element: transformElement,
|
| + dom: transformDom,
|
| + host: transformHost,
|
| + css: transformCss,
|
| + rule: transformRule,
|
| + rootRule: transformRootRule,
|
| + SCOPE_NAME: SCOPE_NAME
|
| + };
|
| +
|
| + })();
|
| +
|
|
|