我的脚本需要在页面部分动态创建样式表(而不是在每个元素上放置内联样式,因为我需要稍后使用媒体查询覆盖这些样式)。
守则
for (var i=0; i<theElements.length; i++){
$(theElements[i]).not('.responsive-wrap').each(function(i, elem){
var theWidth = $(this).width();
var parentWidth = $(this).parent().width();
$(this).addClass('element' + [i]);
$("#dynamicStylesheet").text('.element' + [i] + ' {max-width: ' + theWidth + 'px;}');
});
}
主要问题是:
这完全覆盖了每个循环运行#dynamicStylesheet
中的文本(所以当我加载页面时,.element22
只有一个规则)。如何在不覆盖的情况下添加文本?
奖励分的子问题:
这适用于大部分内容,但仅限于[i]
为正方形时
括号。这是为什么?
我在这里需要for loop
,还是.each(function(){})
本质上
无论如何创建for loop
? <{1}}内的each
以下的另一个for loop
函数我还没有发布以保持简洁。
答案 0 :(得分:2)
我不会在每次迭代期间添加文本。而是构建一个字符串,然后将其添加到元素中。这也提高了性能。
您不需要for循环。
var cssString = '';
$(theElements).not('.responsive-wrap').each(function(i, elem){
var theWidth = $(this).width();
var parentWidth = $(this).parent().width();
$(this).addClass('element' + [i]);
cssString += '.element' + [i] + ' {max-width: ' + theWidth + 'px;}';
});
$("#dynamicStylesheet").text(cssString);
答案 1 :(得分:1)
这是添加文本的快速方法,而不是每次都覆盖它
$("#dynamicStylesheet").text(
$("#dynamicStylesheet").text()
+ '.element' + [i] + ' {max-width: ' + theWidth + 'px;}');
至于for循环,是each
应该是你需要的全部。如果需要数字,可以添加一个计数变量。我还将$("#dynamicStylesheet")
设置为循环外的变量,因此jQuery不必每次都查找元素 - 这是为了提高性能。
var i = 0,
stylesheet = $("#dynamicStylesheet");
$(theElements).not('.responsive-wrap').each(function(){
var theWidth = $(this).width();
var parentWidth = $(this).parent().width();
var elemName = "element" + i;
$(this).addClass(elemName);
stylesheet.text(
stylesheet.text()
+ '.' + elemName + ' {max-width: ' + theWidth + 'px;}');
});
修改强>
如果theElements
是一个标记名称数组,那么这样的内容会比我原来的更好。
var i = 0,
stylesheet = $("#dynamicStylesheet");
$.each(theElements, function(){
if( !$(this).hasClass('responsive-wrap') ){
var theWidth = $(this).width();
var parentWidth = $(this).parent().width();
var elemName = "element" + i;
$(this).addClass(elemName);
stylesheet.text(
stylesheet.text()
+ '.' + elemName + ' {max-width: ' + theWidth + 'px;}');
}
});
未经测试,但应该有效..
答案 2 :(得分:1)
好的,那么,一些事情。假设theElements
是HTML元素的数组,则each
是不必要的。但情况似乎并非如此,因为您说element22
正在显示(如果element0
是一个数组,那么您编写的代码只会一次又一次地创建theElements
HTML元素)。显然theElements
是一个数组数组,或者是一个jQuery对象数组。鉴于它的名字,这是奇怪的,但让我们通过。
正如其他人所提到的,你每次迭代都会覆盖文本,这很糟糕。构建一个字符串稍微好一些,但是你仍然在做重复的字符串连接,这很慢。如果我们必须这样做,我们应该追加一个数组然后在最后将它们连接在一起(这更快,因为追加到字符串每次都会从头开始创建整个字符串。)
var css = [];
for (var i = 0; i < theElements.length; i++) {
$(theElements[i]).not('.responsive-wrap').each(function(i) {
var theWidth = $(this).width();
$(this).addClass('element' + i);
css.push('.element' + i + ' {max-width: ' + theWidth + 'px;}');
});
}
$("#dynamicStylesheet").text(css.join('\n'));
现在,这有效,并且会做你想要的。但这几乎绝对不是你做任何事情的正确方法。在客户端上动态构建CSS并不好,除非你正在编写类似CSS编辑器的东西。有更简单的方法来解决导致你走这条道路的任何问题。
如果创建客户端样式表绝对重要,那么还有更好的方法可以做到这一点。创建一个适用于theElements
元素的所有元素的CSS规则(哇,看看那个句子)。如果它们是随机选择的,那是不可能的,但是如果你通过一些逻辑查询到达它们,你可以在CSS中使用相同的那个。
就[i]
事情而言 - 我不知道该告诉你什么。由于JavaScript将数组串联化的奇怪方式,它们是等价的,如果i
不适合你,那么就会出现问题。如果我是你,我将使用i.toString()
,但i
应该可以正常工作。
如果theElements
是一个标记名称数组,可以简化为:
var tagNames = theElements; // clear variable names are important!
var css = [];
$(tagNames.join(',')).not('.responsive-wrap').each(function(i) {
var $this = $(this);
$this.addClass('element' + i.toString());
css.push('.element' + i.toString() + '{ max-width: ' + $this.width() + 'px; }');
});
$("#dynamicStylesheet").text(css.join('\n'));