From 5c05fb4ed54320ab363a11cbc1e30f5f6c8a2190 Mon Sep 17 00:00:00 2001
From: Julian Leucker <leuckerj@gmail.com>
Date: Wed, 26 Oct 2022 18:19:37 +0200
Subject: [PATCH] Create functionality to specify a Layout for forms

---
 django_forms_as_jsonschema/layout.py | 72 ++++++++++++++++++++++++++++
 1 file changed, 72 insertions(+)
 create mode 100644 django_forms_as_jsonschema/layout.py

diff --git a/django_forms_as_jsonschema/layout.py b/django_forms_as_jsonschema/layout.py
new file mode 100644
index 0000000..db7cb3b
--- /dev/null
+++ b/django_forms_as_jsonschema/layout.py
@@ -0,0 +1,72 @@
+import uuid
+from abc import ABC
+from dataclasses import dataclass
+from typing import Union
+
+from django.utils.text import slugify
+
+
+class LayoutNode(ABC):
+    def __init__(self, *elements):
+        self.elements = elements
+
+    def build_schema(self, schema, form_fields) -> dict:
+        props = {}
+        for field in self.elements:
+            if isinstance(field, LayoutNode):
+                built_schema = field.build_schema(schema, form_fields)
+                props.update(built_schema["properties"])
+            else:
+                props[field] = schema.generate_field(form_fields[field])
+        return {"properties": props}
+
+
+@dataclass
+class _Section:
+    codename: str
+    title: str
+    description: str = None
+
+
+class Row(LayoutNode):
+    def build_schema(self, schema, form_fields):
+        row_name = "row-" + str(uuid.uuid4())
+        fields = super().build_schema(schema, form_fields)["properties"]
+        for k in fields.keys():
+            fields[k]["x-options"] = {
+                "fieldColProps": {
+                    "cols": 12,
+                    "md": ""
+                }
+            }
+        return {
+            "properties": {
+                row_name: {
+                    "x-cols": 12,
+                    "properties": fields
+                }
+            }
+        }
+
+
+class Fieldset(LayoutNode):
+    def __init__(self, name: Union[tuple[str, str], str], *elements):
+        super().__init__(*elements)
+        codename = str(slugify(name))
+        if type(name) == tuple:
+            self.section = _Section(codename, *map(str, name))
+        else:
+            self.section = _Section(codename, str(name))
+
+    def build_schema(self, schema, form_fields) -> dict:
+        section = schema.generate_section(self.section)
+        section["properties"].update(super().build_schema(schema, form_fields)["properties"])
+        return {
+            "properties": {
+                self.section.codename: section
+            }
+        }
+
+
+class Layout(LayoutNode):
+    ...
-- 
GitLab