Pat*_*eck 106 javascript jquery json
我有一个我正在循环的数组.每次条件为真时,我都想将HTML下面代码的副本附加到带有一些值的容器元素.
我可以在哪里以智能方式重复使用此HTML?
<a href="#" class="list-group-item">
<div class="image">
<img src="" />
</div>
<p class="list-group-item-text"></p>
</a>
Run Code Online (Sandbox Code Playgroud)
JQuery的
$('.search').keyup(function() {
$('.list-items').html(null);
$.each(items, function(index) {
// APPENDING CODE HERE
});
});
Run Code Online (Sandbox Code Playgroud)
Mat*_*tra 147
您可以决定在项目中使用模板引擎,例如:
如果您不想包含其他库,John Resig提供了一个jQuery解决方案,类似于下面的解决方案.
浏览器和屏幕阅读器忽略无法识别的脚本类型:
<script id="hidden-template" type="text/x-custom-template">
<tr>
<td>Foo</td>
<td>Bar</td>
<tr>
</script>
Run Code Online (Sandbox Code Playgroud)
使用jQuery,基于模板添加行将类似于:
var template = $('#hidden-template').html();
$('button.addRow').click(function() {
$('#targetTable').append(template);
});
Run Code Online (Sandbox Code Playgroud)
Jos*_*bou 144
老问题,但由于问题是"使用jQuery",我想我会提供一个选项,让你可以在不引入任何供应商依赖的情况下执行此操作.
虽然那里有许多模板引擎,但它们的许多功能最近都不受欢迎,其中iteration(<% for),conditionals(<% if)和transforms(<%= myString | uppercase %>)最多被视为微语言,而最坏的反模式被视为反模式.现代模板实践鼓励简单地将对象映射到其DOM(或其他)表示,例如我们看到的映射到ReactJS中的组件的属性(尤其是无状态组件).
您可以依赖的一个属性是将模板的HTML保留在HTML的其余部分旁边<script> type,例如使用非执行的属性<script type="text/template">.对于你的情况:
<script type="text/template" data-template="listitem">
<a href="${url}" class="list-group-item">
<table>
<tr>
<td><img src="${img}"></td>
<td><p class="list-group-item-text">${title}</p></td>
</tr>
</table>
</a>
</script>
Run Code Online (Sandbox Code Playgroud)
在文档加载时,阅读您的模板并使用简单的标记 String#split
var itemTpl = $('script[data-template="listitem"]').text().split(/\$\{(.+?)\}/g);
Run Code Online (Sandbox Code Playgroud)
请注意,使用我们的令牌,您可以以交替[text, property, text, property]格式获取它.这让我们可以使用Array#map带有映射函数的映射来很好地映射它:
function render(props) {
return function(tok, i) { return (i % 2) ? props[tok] : tok; };
}
Run Code Online (Sandbox Code Playgroud)
哪里props可以看起来像{ url: 'http://foo.com', img: '/images/bar.png', title: 'Lorem Ipsum' }.
假设您已经解析并加载itemTpl了上面的内容,并且您有一个items范围内的数组:
$('.search').keyup(function () {
$('.list-items').append(items.map(function (item) {
return itemTpl.map(render(item)).join('');
}));
});
Run Code Online (Sandbox Code Playgroud)
这种方法也仅是勉强的jQuery -你应该能够采取使用香草的JavaScript用同样的方法document.querySelector和.innerHTML.
问自己的一个问题是:你真的想要/需要将模板定义为HTML文件吗?您可以使用与重复使用模板相同的方式对组件进行组件化和重复使用:使用函数.
在es7-land中,使用解构,模板字符串和箭头函数,您可以编写完全漂亮的组件函数,可以使用上述$.fn.html方法轻松加载.
const Item = ({ url, img, title }) => `
<a href="${url}" class="list-group-item">
<div class="image">
<img src="${img}" />
</div>
<p class="list-group-item-text">${title}</p>
</a>
`;
Run Code Online (Sandbox Code Playgroud)
然后你可以轻松渲染它,甚至可以从数组映射,如下所示:
$('.list-items').html([
{ url: '/foo', img: 'foo.png', title: 'Foo item' },
{ url: '/bar', img: 'bar.png', title: 'Bar item' },
].map(Item).join(''));
Run Code Online (Sandbox Code Playgroud)
哦,最后注意:不要忘记清理传递给模板的属性,如果它们是从数据库中读取的,或者有人可以从您的页面传入HTML(然后运行脚本等).
Dev*_*vWL 34
由于接受的答案将代表重载脚本方法,我想建议另一个,在我看来,由于重载脚本带来的XSS风险,它更清洁,更安全.
我做了一个演示,向您展示如何在一个动作中使用它以及如何将一个模板注入另一个模板,编辑然后添加到文档DOM.
<template id="mytemplate">
<style>
.image{
width: 100%;
height: auto;
}
</style>
<a href="#" class="list-group-item">
<div class="image">
<img src="" />
</div>
<p class="list-group-item-text"></p>
</a>
</template>
Run Code Online (Sandbox Code Playgroud)
// select
var t = document.querySelector('#mytemplate');
// set
t.content.querySelector('img').src = 'demo.png';
t.content.querySelector('p').textContent= 'demo text';
// add to document DOM
var clone = document.importNode(t.content, true); // where true means deep copy
document.body.appendChild(clone);
Run Code Online (Sandbox Code Playgroud)
+其含量在激活前有效惰性.从本质上讲,您的标记是隐藏的DOM,不会呈现.
+模板中的任何内容都不会产生副作用.在使用模板之前,脚本不运行,图像不加载,音频不播放...
+内容被视为不在文档中.在主页面中使用document.getElementById()或querySelector()不会返回模板的子节点.
+模板可放置在任何地方内的<head>,<body>或<frameset>与可以包含任何类型的被允许在这些元素的含量.请注意,"任何地方"意味着<template>可以安全地在HTML解析器不允许的位置使用.
浏览器支持应该不是问题,但如果您想要涵盖所有可能性,您可以轻松检查:
要进行功能检测
<template>,请创建DOM元素并检查.content属性是否存在:
function supportsTemplate() {
return 'content' in document.createElement('template');
}
if (supportsTemplate()) {
// Good to go!
} else {
// Use old templating techniques or libraries.
}
Run Code Online (Sandbox Code Playgroud)
<script>标记具有display:none."text/javascript"..innerHTML.用户提供的数据的运行时字符串解析很容易导致XSS漏洞.全文:https://www.html5rocks.com/en/tutorials/webcomponents/template/#toc-old
有用的参考:https : //developer.mozilla.org/en-US/docs/Web/API/Document/importNode http://caniuse.com/#feat=queryselector
Mat*_*wak 13
添加到身体的某个地方
<div class="hide">
<a href="#" class="list-group-item">
<table>
<tr>
<td><img src=""></td>
<td><p class="list-group-item-text"></p></td>
</tr>
</table>
</a>
</div>
Run Code Online (Sandbox Code Playgroud)
然后创建CSS
.hide { display: none; }
Run Code Online (Sandbox Code Playgroud)
并添加到您的js
$('#output').append( $('.hide').html() );
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
170527 次 |
| 最近记录: |