summaryrefslogtreecommitdiff
path: root/Meta
diff options
context:
space:
mode:
authorSam Atkins <atkinssj@serenityos.org>2022-04-13 16:48:03 +0100
committerAndreas Kling <kling@serenityos.org>2022-04-14 14:54:06 +0200
commita97944e483ffcd4c21046fdc99de236e6405bc9d (patch)
tree131d6b76c0d9065a582b7f29b08f8d8024eb02ac /Meta
parent66170ff632c58f7c8689e08eda218037b63632c3 (diff)
downloadserenity-a97944e483ffcd4c21046fdc99de236e6405bc9d.zip
LibWeb: Add a new code generator for CSS enums
Alias values are represented by "alias-name=real-name". We have a lot of repetitive code for converting between ValueID and property-specific enums. Let's see if we can generate it. :^) This first step just produces the enums, from a JSON file. The values in there are a duplication of what's in Properties.json, but eventually those will go away.
Diffstat (limited to 'Meta')
-rw-r--r--Meta/Lagom/Tools/CodeGenerators/LibWeb/CMakeLists.txt1
-rw-r--r--Meta/Lagom/Tools/CodeGenerators/LibWeb/GenerateCSSEnums.cpp100
2 files changed, 101 insertions, 0 deletions
diff --git a/Meta/Lagom/Tools/CodeGenerators/LibWeb/CMakeLists.txt b/Meta/Lagom/Tools/CodeGenerators/LibWeb/CMakeLists.txt
index 5f96f85aa4..7b3e7904e7 100644
--- a/Meta/Lagom/Tools/CodeGenerators/LibWeb/CMakeLists.txt
+++ b/Meta/Lagom/Tools/CodeGenerators/LibWeb/CMakeLists.txt
@@ -1,5 +1,6 @@
set(SOURCES "") # avoid pulling SOURCES from parent scope
+lagom_tool(GenerateCSSEnums SOURCES GenerateCSSEnums.cpp LIBS LagomMain)
lagom_tool(GenerateCSSMediaFeatureID SOURCES GenerateCSSMediaFeatureID.cpp LIBS LagomMain)
lagom_tool(GenerateCSSPropertyID SOURCES GenerateCSSPropertyID.cpp LIBS LagomMain)
lagom_tool(GenerateCSSValueID SOURCES GenerateCSSValueID.cpp LIBS LagomMain)
diff --git a/Meta/Lagom/Tools/CodeGenerators/LibWeb/GenerateCSSEnums.cpp b/Meta/Lagom/Tools/CodeGenerators/LibWeb/GenerateCSSEnums.cpp
new file mode 100644
index 0000000000..5672208d19
--- /dev/null
+++ b/Meta/Lagom/Tools/CodeGenerators/LibWeb/GenerateCSSEnums.cpp
@@ -0,0 +1,100 @@
+/*
+ * Copyright (c) 2022, Sam Atkins <atkinssj@serenityos.org>
+ *
+ * SPDX-License-Identifier: BSD-2-Clause
+ */
+
+#include "GeneratorUtil.h"
+#include <AK/SourceGenerator.h>
+#include <AK/StringBuilder.h>
+#include <LibCore/ArgsParser.h>
+#include <LibMain/Main.h>
+
+ErrorOr<void> generate_header_file(JsonObject& enums_data, Core::Stream::File& file);
+ErrorOr<void> generate_implementation_file(JsonObject& enums_data, Core::Stream::File& file);
+
+ErrorOr<int> serenity_main(Main::Arguments arguments)
+{
+ StringView generated_header_path;
+ StringView generated_implementation_path;
+ StringView identifiers_json_path;
+
+ Core::ArgsParser args_parser;
+ args_parser.add_option(generated_header_path, "Path to the Enums header file to generate", "generated-header-path", 'h', "generated-header-path");
+ args_parser.add_option(generated_implementation_path, "Path to the Enums implementation file to generate", "generated-implementation-path", 'c', "generated-implementation-path");
+ args_parser.add_option(identifiers_json_path, "Path to the JSON file to read from", "json-path", 'j', "json-path");
+ args_parser.parse(arguments);
+
+ auto json = TRY(read_entire_file_as_json(identifiers_json_path));
+ VERIFY(json.is_object());
+ auto enums_data = json.as_object();
+
+ auto generated_header_file = TRY(Core::Stream::File::open(generated_header_path, Core::Stream::OpenMode::Write));
+ auto generated_implementation_file = TRY(Core::Stream::File::open(generated_implementation_path, Core::Stream::OpenMode::Write));
+
+ TRY(generate_header_file(enums_data, *generated_header_file));
+ TRY(generate_implementation_file(enums_data, *generated_implementation_file));
+
+ return 0;
+}
+
+ErrorOr<void> generate_header_file(JsonObject& enums_data, Core::Stream::File& file)
+{
+ StringBuilder builder;
+ SourceGenerator generator { builder };
+
+ generator.append(R"~~~(
+#pragma once
+
+namespace Web::CSS {
+
+enum class ValueID;
+
+)~~~");
+
+ enums_data.for_each_member([&](auto& name, auto& value) {
+ VERIFY(value.is_array());
+ auto& members = value.as_array();
+
+ auto enum_generator = generator.fork();
+ enum_generator.set("name:titlecase", title_casify(name));
+ enum_generator.appendln("enum class @name:titlecase@ {");
+
+ for (auto& member : members.values()) {
+ auto member_name = member.to_string();
+ // Don't include aliases in the enum.
+ if (member_name.contains('='))
+ continue;
+ auto member_generator = enum_generator.fork();
+ member_generator.set("member:titlecase", title_casify(member_name));
+ member_generator.appendln(" @member:titlecase@,");
+ }
+
+ enum_generator.appendln("};\n");
+ });
+
+ generator.appendln("}");
+
+ TRY(file.write(generator.as_string_view().bytes()));
+ return {};
+}
+
+ErrorOr<void> generate_implementation_file(JsonObject& enums_data, Core::Stream::File& file)
+{
+ StringBuilder builder;
+ SourceGenerator generator { builder };
+
+ generator.append(R"~~~(
+#include <LibWeb/CSS/Enums.h>
+
+namespace Web::CSS {
+)~~~");
+
+ // TODO: Generate some things!
+ (void)enums_data;
+
+ generator.appendln("}");
+
+ TRY(file.write(generator.as_string_view().bytes()));
+ return {};
+}