diff --git a/Sources/Plot/API/HTML.swift b/Sources/Plot/API/HTML.swift
index 14f86fb..2c9d7d3 100644
--- a/Sources/Plot/API/HTML.swift
+++ b/Sources/Plot/API/HTML.swift
@@ -140,6 +140,8 @@ public extension HTML {
enum TableContext: HTMLStylableContext {}
/// The context within an HTML `
` element.
enum TableRowContext: HTMLStylableContext {}
+ /// The context within an HTML `` element.
+ final class TimeContext: BodyContext {}
/// The context within an HTML `` element.
enum VideoContext: HTMLMediaContext {
public typealias SourceContext = VideoSourceContext
diff --git a/Sources/Plot/API/HTMLAttributes.swift b/Sources/Plot/API/HTMLAttributes.swift
index dd39350..f33fc82 100644
--- a/Sources/Plot/API/HTMLAttributes.swift
+++ b/Sources/Plot/API/HTMLAttributes.swift
@@ -217,6 +217,19 @@ public extension Node where Context == HTML.AnchorContext {
}
}
+// MARK: - DateTime
+
+public extension Node where Context == HTML.TimeContext {
+ /// Attach a datetime to the time element, to translate the element into
+ /// a machine readable format for browsers.
+ /// - parameter datetime: The datetime string to attach. See
+ /// [datetime reference](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/time#valid_datetime_values)
+ /// for more info
+ static func datetime(_ datetime: String) -> Node {
+ .attribute(named: "datetime", value: datetime)
+ }
+}
+
// MARK: - Interactive elements
public extension Node where Context == HTML.DetailsContext {
diff --git a/Sources/Plot/API/HTMLComponents.swift b/Sources/Plot/API/HTMLComponents.swift
index 1348eea..6487d94 100644
--- a/Sources/Plot/API/HTMLComponents.swift
+++ b/Sources/Plot/API/HTMLComponents.swift
@@ -867,3 +867,28 @@ public struct TextArea: InputComponent {
)
}
}
+
+/// Component that represents a datetime instance
+public struct Time: Component {
+ /// The datetime that the element represents
+ public var datetime: String?
+ /// A closure that provides the contained content.
+ @ComponentBuilder public var content: ContentProvider
+
+ /// Initialize a time component.
+ /// - parameters:
+ /// - datetime: An optional, machine-readable, datetime string to describe the time represented.
+ /// - content: A closure that provides the contained content.
+ public init(datetime: String? = nil,
+ @ComponentBuilder content: @escaping ContentProvider) {
+ self.datetime = datetime
+ self.content = content
+ }
+
+ public var body: Component {
+ Node.time(
+ .unwrap(datetime, Node.datetime),
+ .component(content())
+ )
+ }
+}
diff --git a/Sources/Plot/API/HTMLElements.swift b/Sources/Plot/API/HTMLElements.swift
index ab5beb7..8aa1c9c 100644
--- a/Sources/Plot/API/HTMLElements.swift
+++ b/Sources/Plot/API/HTMLElements.swift
@@ -382,6 +382,12 @@ public extension Node where Context: HTML.BodyContext {
static func textarea(_ nodes: Node...) -> Node {
.element(named: "textarea", nodes: nodes)
}
+
+ /// Add a `` HTML element within the current context.
+ /// - parameter nodes: The element's attributes and nodes.
+ static func time(_ nodes: Node...) -> Node {
+ .element(named: "time", nodes: nodes)
+ }
/// Add a `` HTML element within the current context.
/// - parameter nodes: The element's attributes and child elements.
diff --git a/Tests/PlotTests/HTMLComponentTests.swift b/Tests/PlotTests/HTMLComponentTests.swift
index f2157ab..d416b57 100644
--- a/Tests/PlotTests/HTMLComponentTests.swift
+++ b/Tests/PlotTests/HTMLComponentTests.swift
@@ -434,6 +434,15 @@ final class HTMLComponentTests: XCTestCase {
XCTAssertEqual(html, "One Two ")
}
+
+ func testTime() {
+ let html = Time(datetime: "2011-11-18T14:54:39Z") {
+ Paragraph("Hello World")
+ }
+ .render()
+
+ XCTAssertEqual(html, #"Hello World
"#)
+ }
func testOrderedListWithExplicitItems() {
struct SeventhComponent: Component {
diff --git a/Tests/PlotTests/HTMLTests.swift b/Tests/PlotTests/HTMLTests.swift
index c4c6cc8..f1a8feb 100644
--- a/Tests/PlotTests/HTMLTests.swift
+++ b/Tests/PlotTests/HTMLTests.swift
@@ -932,6 +932,19 @@ final class HTMLTests: XCTestCase {
""")
}
+ func testTime() {
+ let html = HTML(.body(.time(
+ .text("Hello World!"),
+ .datetime("2011-11-18T14:54:39Z")
+ )))
+
+ assertEqualHTMLContent(html, """
+ \
+ Hello World!\
+
+ """)
+ }
+
func testObject() {
let html = HTML(.body(.object(
.data("vector.svg"),