css.js 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113
  1. import { domEach, isTag } from '../utils.js';
  2. /**
  3. * Set multiple CSS properties for every matched element.
  4. *
  5. * @category CSS
  6. * @param prop - The names of the properties.
  7. * @param val - The new values.
  8. * @returns The instance itself.
  9. * @see {@link https://api.jquery.com/css/}
  10. */
  11. export function css(prop, val) {
  12. if ((prop != null && val != null) ||
  13. // When `prop` is a "plain" object
  14. (typeof prop === 'object' && !Array.isArray(prop))) {
  15. return domEach(this, (el, i) => {
  16. if (isTag(el)) {
  17. // `prop` can't be an array here anymore.
  18. setCss(el, prop, val, i);
  19. }
  20. });
  21. }
  22. if (this.length === 0) {
  23. return undefined;
  24. }
  25. return getCss(this[0], prop);
  26. }
  27. /**
  28. * Set styles of all elements.
  29. *
  30. * @private
  31. * @param el - Element to set style of.
  32. * @param prop - Name of property.
  33. * @param value - Value to set property to.
  34. * @param idx - Optional index within the selection.
  35. */
  36. function setCss(el, prop, value, idx) {
  37. if (typeof prop === 'string') {
  38. const styles = getCss(el);
  39. const val = typeof value === 'function' ? value.call(el, idx, styles[prop]) : value;
  40. if (val === '') {
  41. delete styles[prop];
  42. }
  43. else if (val != null) {
  44. styles[prop] = val;
  45. }
  46. el.attribs['style'] = stringify(styles);
  47. }
  48. else if (typeof prop === 'object') {
  49. Object.keys(prop).forEach((k, i) => {
  50. setCss(el, k, prop[k], i);
  51. });
  52. }
  53. }
  54. function getCss(el, prop) {
  55. if (!el || !isTag(el))
  56. return;
  57. const styles = parse(el.attribs['style']);
  58. if (typeof prop === 'string') {
  59. return styles[prop];
  60. }
  61. if (Array.isArray(prop)) {
  62. const newStyles = {};
  63. prop.forEach((item) => {
  64. if (styles[item] != null) {
  65. newStyles[item] = styles[item];
  66. }
  67. });
  68. return newStyles;
  69. }
  70. return styles;
  71. }
  72. /**
  73. * Stringify `obj` to styles.
  74. *
  75. * @private
  76. * @category CSS
  77. * @param obj - Object to stringify.
  78. * @returns The serialized styles.
  79. */
  80. function stringify(obj) {
  81. return Object.keys(obj).reduce((str, prop) => `${str}${str ? ' ' : ''}${prop}: ${obj[prop]};`, '');
  82. }
  83. /**
  84. * Parse `styles`.
  85. *
  86. * @private
  87. * @category CSS
  88. * @param styles - Styles to be parsed.
  89. * @returns The parsed styles.
  90. */
  91. function parse(styles) {
  92. styles = (styles || '').trim();
  93. if (!styles)
  94. return {};
  95. const obj = {};
  96. let key;
  97. for (const str of styles.split(';')) {
  98. const n = str.indexOf(':');
  99. // If there is no :, or if it is the first/last character, add to the previous item's value
  100. if (n < 1 || n === str.length - 1) {
  101. const trimmed = str.trimEnd();
  102. if (trimmed.length > 0 && key !== undefined) {
  103. obj[key] += `;${trimmed}`;
  104. }
  105. }
  106. else {
  107. key = str.slice(0, n).trim();
  108. obj[key] = str.slice(n + 1).trim();
  109. }
  110. }
  111. return obj;
  112. }
  113. //# sourceMappingURL=css.js.map