srctree

Robin Linden parent 9e94c859 e7e5e062
Render the dom in a terminal ui

inlinesplit
WORKSPACE added: 81, removed: 5, total 76
@@ -23,6 +23,14 @@ http_archive(
urls = ["https://github.com/catchorg/Catch2/archive/v2.13.4.tar.gz"],
)
 
http_archive(
name = "ftxui",
sha256 = "a56359a73a98bc05631d2952b286478ac89f1df3178fc63d52d7b1217ee5e527",
build_file = "//bazel:ftxui.BUILD",
strip_prefix = "FTXUI-d0eab413442d084d15a328c53fb132814daa58f3",
urls = ["https://github.com/ArthurSonzogni/FTXUI/archive/d0eab413442d084d15a328c53fb132814daa58f3.tar.gz"],
)
 
http_archive(
name = "platforms",
sha256 = "460caee0fa583b908c622913334ec3c1b842572b9c23cf0d3da0c2543a1a157d",
 
filename was Deleted added: 81, removed: 5, total 76
@@ -0,0 +1,23 @@
load("@rules_cc//cc:defs.bzl", "cc_library")
 
cc_library(
name = "ftxui",
srcs = glob(
include = ["src/**"],
exclude = ["src/**/*_test.cpp"],
),
hdrs = glob(["include/**/*.hpp"]),
copts = ["-Iexternal/ftxui/src"] + select({
"@platforms//os:linux": [],
"@platforms//os:windows": ["-utf-8"],
}),
local_defines = select({
"@platforms//os:linux": [],
"@platforms//os:windows": [
"_UNICODE",
"UNICODE",
],
}),
strip_include_prefix = "include",
visibility = ["//visibility:public"],
)
 
browser/BUILD added: 81, removed: 5, total 76
@@ -10,5 +10,6 @@ cc_binary(
deps = [
"//parser",
"@asio",
"@ftxui",
],
)
 
browser/main.cpp added: 81, removed: 5, total 76
@@ -1,9 +1,13 @@
#include "parser/parser.h"
 
#include <asio.hpp>
#include <ftxui/dom/elements.hpp>
#include <ftxui/screen/screen.hpp>
#include <ftxui/screen/string.hpp>
#include <asio.hpp> // Needs to be after ftxui due to pulling in macros that break their headers.
 
#include <cassert>
#include <iostream>
#include <optional>
#include <sstream>
#include <string>
 
@@ -37,6 +41,45 @@ std::string drop_http_headers(std::string html) {
return html;
}
 
std::optional<ftxui::Element> create_ftxui_ui(dom::Node const &node) {
ftxui::Elements children;
for (auto const &child : node.children) {
if (auto n = create_ftxui_ui(child); n) {
children.push_back(*n);
}
};
 
return std::visit(overloaded {
[](std::monostate) -> std::optional<ftxui::Element> { return std::nullopt; },
[&](dom::Doctype const &) -> std::optional<ftxui::Element> { return std::nullopt; },
[&](dom::Element const &node) -> std::optional<ftxui::Element> {
if (node.name == "html") { return border(children[0]); }
else if (node.name == "body") { return vbox(children); }
else if (node.name == "div") { return vbox(children); }
else if (node.name == "h1") { return underlined(vbox(children)); }
else if (node.name == "p") { return vbox(children); }
else if (node.name == "a") { return bold(vbox(children)); }
else {
std::cout << "Unhandled node: " << node.name << '\n';
return std::nullopt;
}
},
[&](dom::Text const &node) -> std::optional<ftxui::Element> {
return hflow(ftxui::paragraph(ftxui::to_wstring(node.text)));
},
}, node.data);
}
 
void ftxui_test(dom::Node root) {
std::cout << "\nBuilding TUI\n";
auto document = *create_ftxui_ui(root);
if (!document) { return; }
document = document | ftxui::size(ftxui::WIDTH, ftxui::LESS_THAN, 80);
auto screen = ftxui::Screen::Create(ftxui::Dimension::Full(), ftxui::Dimension::Fit(document));
ftxui::Render(screen, document);
std::cout << screen.ToString() << std::endl;
}
 
} // namespace
 
int main(int argc, char **argv) {
@@ -55,4 +98,5 @@ int main(int argc, char **argv) {
 
auto nodes = parser::Parser{buffer}.parse_nodes();
for (auto const &node : nodes) { print_node(node); }
for (auto const &node : nodes) { ftxui_test(node); }
}