selector.js 1.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. var utils = require('../utils');
  2. /**
  3. * Return the current selector or compile
  4. * selector from a string or a list.
  5. *
  6. * @param {String|Expression}
  7. * @return {String}
  8. * @api public
  9. */
  10. (module.exports = function selector(){
  11. var stack = this.selectorStack
  12. , args = [].slice.call(arguments);
  13. if (1 == args.length) {
  14. var expr = utils.unwrap(args[0])
  15. , len = expr.nodes.length;
  16. // selector('.a')
  17. if (1 == len) {
  18. utils.assertString(expr.first, 'selector');
  19. var SelectorParser = require('../selector-parser')
  20. , val = expr.first.string
  21. , parsed = new SelectorParser(val).parse().val;
  22. if (parsed == val) return val;
  23. stack.push(parse(val));
  24. } else if (len > 1) {
  25. // selector-list = '.a', '.b', '.c'
  26. // selector(selector-list)
  27. if (expr.isList) {
  28. pushToStack(expr.nodes, stack);
  29. // selector('.a' '.b' '.c')
  30. } else {
  31. stack.push(parse(expr.nodes.map(function(node){
  32. utils.assertString(node, 'selector');
  33. return node.string;
  34. }).join(' ')));
  35. }
  36. }
  37. // selector('.a', '.b', '.c')
  38. } else if (args.length > 1) {
  39. pushToStack(args, stack);
  40. }
  41. return stack.length ? utils.compileSelectors(stack).join(',') : '&';
  42. }).raw = true;
  43. function pushToStack(selectors, stack) {
  44. selectors.forEach(function(sel) {
  45. sel = sel.first;
  46. utils.assertString(sel, 'selector');
  47. stack.push(parse(sel.string));
  48. });
  49. }
  50. function parse(selector) {
  51. var Parser = new require('../parser')
  52. , parser = new Parser(selector)
  53. , nodes;
  54. parser.state.push('selector-parts');
  55. nodes = parser.selector();
  56. nodes.forEach(function(node) {
  57. node.val = node.segments.map(function(seg){
  58. return seg.toString();
  59. }).join('');
  60. });
  61. return nodes;
  62. }