我正在编写自己的函数来为伪元素分配属性,并注意到一个未知错误。属性的分配通过向样式表添加行来进行。
当我在第三种情况下调用该函数时,由于某种原因第一个元素被涂成蓝色,尽管color我没有为它设置它。
(function() {
var setPseudoElement = function(parameters) {
for (var element of parameters.elements.get()) {
if (!element.pseudoElements) element.pseudoElements = {
styleSheet: null,
before: {
index: null,
properties: null
},
after: {
index: null,
properties: null
}
};
var selector = (function() {
if (element.id) {
return '#' + element.id + '::' + parameters.pseudoElement;
} else {
var parentsList = $(element).parents().map(function() {
return this.tagName.toLowerCase();
}).get().reverse().join(' > ') + ' > ' + element.tagName.toLowerCase();
var elementClass = element.classList.length ? '.' + $(element.classList).get().join('.') : '';
var elementAttributes = element.hasAttributes() ? $(element.attributes).get().map(function(className) {
return className.nodeName !== 'class' ? className.nodeValue ? '[' + className.nodeName + '="' + className.nodeValue + '"]' : '[' + className.nodeName + '"]' : '';
}).join('') : '';
var elementNthChild = ':nth-child(' + ($(element).index() + 1) + ')';
return parentsList + elementClass + elementAttributes + elementNthChild + '::' + parameters.pseudoElement;
};
})();
if (!element.pseudoElements.styleSheet) {
if (document.styleSheets[0]) {
element.pseudoElements.styleSheet = document.styleSheets[0];
} else {
var styleSheet = document.createElement('style');
document.head.appendChild(styleSheet);
element.pseudoElements.styleSheet = styleSheet.sheet;
};
};
if (element.pseudoElements[parameters.pseudoElement].properties !== null && element.pseudoElements[parameters.pseudoElement].index !== null) {
element.pseudoElements.styleSheet.deleteRule(element.pseudoElements[parameters.pseudoElement].index);
};
if (typeof parameters.argument === 'object') {
if (!element.pseudoElements[parameters.pseudoElement].properties && !element.pseudoElements[parameters.pseudoElement].index) {
var newIndex = element.pseudoElements.styleSheet.rules.length || element.pseudoElements.styleSheet.cssRules.length || element.pseudoElements.styleSheet.length;
element.pseudoElements[parameters.pseudoElement].index = newIndex;
element.pseudoElements[parameters.pseudoElement].properties = parameters.argument;
};
var properties = '';
for (var property in parameters.argument) {
element.pseudoElements[parameters.pseudoElement].properties[property] = parameters.argument[property];
};
for (var property in element.pseudoElements[parameters.pseudoElement].properties) {
properties += property + ': ' + element.pseudoElements[parameters.pseudoElement].properties[property] + ' !important; ';
};
element.pseudoElements.styleSheet.addRule(selector, properties, element.pseudoElements[parameters.pseudoElement].index);
} else if (parameters.argument !== undefined && parameters.property !== undefined) {
} else if (parameters.argument !== undefined && parameters.property === undefined) {
} else {
console.error('Invalid values!');
return false;
};
};
};
$.fn.cssBefore = function(argument, property) {
setPseudoElement({
elements: this,
pseudoElement: 'before',
argument: argument,
property: property
});
};
})();
$(function() {
// Случай 1
$('.el0').cssBefore({
'content': '"Новый \'before\'"',
'color': 'green'
});
// Случай 2
$('.el1').cssBefore({
'content': '"Новый \'before\' №2"',
'color': 'blue'
});
// Случай 3
$('.el0').cssBefore({
'content': '"Новый \'before\' №3"'
});
});
.element {
width: 480px;
margin: 0 auto;
border: 2px solid red;
}
.element:before {
content: "Старый 'before'";
color: orange;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<div class="element el0" name="MyName"></div>
<div class="element el0 el1" id="elem"></div>
<div>
<div class="element el1"></div>
</div>
为什么在第三种情况下第一个元素被涂成蓝色?如何解决?
更新:
如果在每次赋值后将元素的值打印到控制台,那么就会出现非常奇怪的值:
(function () {
var i = 1;
var setPseudoElement = function (parameters) {
for (var element of parameters.elements.get()) {
if (!element.pseudoElements) element.pseudoElements = {styleSheet: null, before: {index: null, properties: null}, after: {index: null, properties: null}};
var selector = (function () {
if (element.id) {
return '#' + element.id + '::' + parameters.pseudoElement;
} else {
var parentsList = $(element).parents().map(function () {
return this.tagName.toLowerCase();
}).get().reverse().join(' > ') + ' > ' + element.tagName.toLowerCase();
var elementClass = element.classList.length ? '.' + $(element.classList).get().join('.') : '';
var elementAttributes = element.hasAttributes() ? $(element.attributes).get().map(function (className) {
return className.nodeName !== 'class' ? className.nodeValue ? '[' + className.nodeName + '="' + className.nodeValue + '"]' : '[' + className.nodeName + '"]' : '';
}).join('') : '';
var elementNthChild = ':nth-child(' + ($(element).index() + 1) + ')';
return parentsList + elementClass + elementAttributes + elementNthChild + '::' + parameters.pseudoElement;
};
})();
if (!element.pseudoElements.styleSheet) {
if (document.styleSheets[0]) {
element.pseudoElements.styleSheet = document.styleSheets[0];
} else {
var styleSheet = document.createElement('style');
document.head.appendChild(styleSheet);
element.pseudoElements.styleSheet = styleSheet.sheet;
};
};
if (element.pseudoElements[parameters.pseudoElement].properties !== null && element.pseudoElements[parameters.pseudoElement].index !== null) {
element.pseudoElements.styleSheet.deleteRule(element.pseudoElements[parameters.pseudoElement].index);
};
if (typeof parameters.argument === 'object') {
if (!element.pseudoElements[parameters.pseudoElement].properties && !element.pseudoElements[parameters.pseudoElement].index) {
var newIndex = element.pseudoElements.styleSheet.rules.length || element.pseudoElements.styleSheet.cssRules.length || element.pseudoElements.styleSheet.length;
element.pseudoElements[parameters.pseudoElement].index = newIndex;
element.pseudoElements[parameters.pseudoElement].properties = parameters.argument;
};
var properties = '';
for (var property in parameters.argument) {
element.pseudoElements[parameters.pseudoElement].properties[property] = parameters.argument[property];
};
for (var property in element.pseudoElements[parameters.pseudoElement].properties) {
properties += property + ': ' + element.pseudoElements[parameters.pseudoElement].properties[property] + ' !important; ';
};
element.pseudoElements.styleSheet.addRule(selector, properties, element.pseudoElements[parameters.pseudoElement].index);
console.log('Номер запуска: ' + Math.round(i / 2) + '; Номер присваивания элементу: ' + i);
console.log({
'Элемент 1': $('.el0:not(.el1)').get(0).pseudoElements,
'Элемент 2': $('.el0.el1').get(0).pseudoElements,
'Элемент 3': $('.el1:not(.el0)').get(0).pseudoElements
});
i++;
} else if (parameters.argument !== undefined && parameters.property !== undefined) {
} else if (parameters.argument !== undefined && parameters.property === undefined) {
} else {
console.error('Invalid values!');
return false;
};
};
};
$.fn.cssBefore = function (argument, property) {
setPseudoElement ({
elements: this,
pseudoElement: 'before',
argument: argument,
property: property
});
};
})();
$(function() {
// Случай 1
$('.el0').cssBefore({
'content': '"Новый \'before\'"',
'color': 'green'
});
// Случай 2
$('.el1').cssBefore({
'content': '"Новый \'before\' №2"',
'color': 'blue'
});
// Случай 3
$('.el0').cssBefore({
'content': '"Новый \'before\' №3"'
});
});
.element {
width: 480px;
margin: 0 auto;
border: 2px solid red;
}
.element:before {
content: "Старый 'before'";
color: orange;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<div class="element el0" name="MyName"></div>
<div class="element el0 el1" id="elem"></div>
<div>
<div class="element el1"></div>
</div>
如果您查看控制台,那么在第一次调用该函数时,1 号元素为蓝色,3 号内容
我想我发现了问题:
哪里
parameters.argument是一个对象。当我们进行第一遍时,我们将它设置为第一个和第二个元素。在第二次传递时,我们针对第二种情况更改它,它也会针对第一种情况进行更改。这是证明和解决方案
这就是您期望的行为方式。最初的问题是什么 - 虽然我明白,但我会在半小时内添加它。setTimeouts 是为了方便调试,如果有的话。同志们,对于我的生活,我不明白它为什么有效以及首先通常是什么错误。混淆元素循环体中的滑动
parameters,因为从逻辑上讲,它不应该在循环内,工作正在用特定的循环完成element,但很可能,我只是不知道jquery。