Самый простой способ построить html-элементы в jQuery
Я видел много разных стилей (и несколько разных методов) создания элементов в jQuery. Мне было любопытно, о clearest способ их построения, а также если какой-либо конкретный метод объективно лучше другого по какой-либо причине. Ниже приведены некоторые примеры из стилей и методов, которые я видел.
var title = "Title";
var content = "Lorem ipsum";
// escaping endlines for a multi-line string
// (aligning the slashes is marginally prettier but can add a lot of whitespace)
var $element1 = $("
<div><h1>" + title + "</h1>
<div class='content'>
" + content + "
</div>
</div>
");
// all in one
// obviously deficient
var $element2 = $("<div><h1>" + title + "</h1><div class='content'>" + content + "</div></div>");
// broken on concatenation
var $element3 = $("<div><h1>" +
title +
"</h1><div class='content'>" +
content +
"</div></div>");
// constructed piecewise
// (I've seen this with nested function calls instead of temp variables)
var $element4 = $("<div></div>");
var $title = $("<h1></h1>").html(title);
var $content = $("<div class='content'></div>").html(content);
$element4.append($title, $content);
$("body").append($element1, $element2, $element3, $element4);
пожалуйста, не стесняйтесь демонстрировать какие-то другие методы/стили, которые вы можете использовать.
9 ответов:
Шаблоны отличные, и если у вас есть доступ к ним в вашем проекте, я предлагаю вам использовать их. Если вы используете подчеркивание или Лодашь он встроен. Однако в некоторых случаях вам нужно будет построить HTML в своем коде, будь то рефакторинг или тестирование. Я обнаружил, что приведенный ниже формат является самым четким для чтения, когда это требование.
Примечание: HTML spec позволяет одинарные или двойные кавычки для атрибутов в разметке, так что не потрудитесь со всеми сумасшедшими побегами.
this.$fixture = $([ "<div>", " <div class='js-alert-box'></div>", " <form id='my-form-to-validate'>", " <input id='login-username' name='login-username'>", " </form>", "</div>" ].join("\n"));
осмотревшись некоторое время, я нашел стиль, который я, наконец, остановился. Во-первых, я скажу, что я использовал усы для шаблонов, и это сработало хорошо. Иногда, однако, вам просто нужно построить элемент один раз, не используя его повторно, или иметь какую-то другую мотивацию, чтобы не вводить другую библиотеку. В этой ситуации я взял на использование:
$("body") .append( $("<div>") .append( $("<div>") .append( $("<h1>").text(title) ) ) .append( $("<div>").text(content) ) );
это работает, потому что
append()
возвращает ссылку на объект ты добавление до, так прикованappend()
s прикрепить к тому же объекту. При правильном отступе структура разметки очевидна, и таким образом ее легко изменить. Очевидно, что это медленнее, чем использование шаблонов (все это должно быть построено по частям), но если вы используете его только для инициализации или что-то подобное, то это отличный компромисс.есть много способов отформатировать такую конструкцию, но я выбрал способ, чтобы понять, что происходит. Правило я использовал это в каждой строке должно быть не более одной открывающей и/или закрывающей скобок. Кроме того, листья этих деревьев добавления не нужно передавать в конструктор jQuery, но я сделал это здесь для визуального повторения.
когда дело доходит до построения DOM, я стараюсь избегать конкатенаций строк, поскольку они могут привести к тонким ошибкам и не правильно закодированным выводам.
мне нравится этот:
$('<div/>', { html: $('<h1/>', { html: title }).after( $('<div/>', { 'text': content, 'class': 'content' }) ) }).appendTo('body');
выдает:
... <div><h1>some title</h1><div class="content">some content</div></div> </body>
и это обеспечивает правильное кодирование HTML и построение дерева DOM с соответствующими открывающими и закрывающими тегами.
мой совет: не пытайтесь создавать html-элементы с помощью jQuery, это не его ответственность.
используйте систему шаблонов Javascript, например ус или HandlebarJs.
С очень ограниченным количеством строк вы можете создавать свои html-элементы непосредственно из объекта Javascript. Это не сложно, только 2 функции и шаблона.
<div class="entry"> <h1>{{title}}</h1> <div class="body"> {{body}} </div> </div> var context = {title: "My New Post", body: "This is my first post!"} var template = Handlebars.compile($("#template-skeleton")); var html = template(context);
Edit:
Еще один пример без html, чистый Javascript (от ICanHaz):var skeleton = '<div><h1>{{title}}</h1><div class="content">{{content}}</div></div>'; var data = { title: "Some title", content: "Some content" }; var html = Mustache.to_html(skeleton, data);
Он гораздо более ремонтопригоден, чем серия конкатенации.
ответ 2015: для более старых браузеров используйте multiline.
var str = multiline(function(){/* <!doctype html> <html> <body> <h1>❤ unicorns</h1> </body> </html> */});
для ES6 используйте строки шаблона JavaScript
var str = ` <!doctype html> <html> <body> <h1>❤ unicorns</h1> </body> </html>`
это адаптировано из ответа Баера. Я нахожу его более читаемым, нет необходимости создавать и присоединять массив, нет необходимости ставить кавычки вокруг каждой строки:
var html = ' \ <div> \ <div class="js-alert-box"></div> \ <form id="my-form-to-validate"> \ <input id="login-username" name="login-username"> \ </form> \ </div> \ ' // using jQuery: // var dom = $( html ) // or if you need performance, don't use jQuery // for the parsing. // http://jsperf.com/create-dom-innerhtml-vs-jquery // var div = document.createElement( 'div' ) div.innerHTML = html var dom = $( div )
FYI, когда производительность не является проблемой, а элементы содержат много динамических данных, я иногда просто пишу такой код (обратите внимание, что компилятор закрытия будет выдавать предупреждение о свойстве некотируемого класса, но в современных браузерах это работает отлично):
$( '<a></a>' , { text : this.fileName , href : this.fileUrl , target : '_blank' , class : 'file-link' , appendTo : this.container } )
вы могли бы заглянуть в шаблоны представлений javascript:
http://jupiterjs.com/news/jquery-view-client-side-templates-for-jquery
Я нахожу функциональный подход очень удобным. Например,
// reusable generics TABLE constructor helpers var TD = function(content) { return $('<td>', { html: content }) } var TH = function(content) { return $('<th>', { html: content }) } var TR = function(cell, cells) { // note the kind of cell is a 2^order parameter return $('<tr>', { html: $.map(cells, cell) }) } // application example THEAD = $('<thead>', {html: TR(TH, [1,2,3,4])}) TBODY = $('<tbody>', {html: [ TR(TD, ['a','b','c','d']), TR(TD, ['a','b','c','d']), ]})
сейчас позвоню
$('#table').append($('<table>', {html: [THEAD, TBODY]}))
доходность
<table><thead><tr><th>1</th><th>2</th><th>3</th><th>4</th></tr></thead><tbody><tr><td>a</td><td>b</td><td>c</td><td>d</td></tr><tr><td>a</td><td>b</td><td>c</td><td>d</td></tr></tbody></table>
edit
я усовершенствовал свой подход, теперь доступный, например, как html_uty.js
вот пример, который использует $(htmlString) и имитирует стандартный макет HTML-кода:
function getPage(title, contents) { return ( $("<div>", {id: "container", class: "box"}).append( $("<div>", {class: "title"}).append( $("<h1>").text(title) ), $("<div>").html(contents) ) ); }