WIP: Updates to login / signup forms, rearranges some view routes.
This commit is contained in:
@@ -5,6 +5,8 @@ extension ViewController.Request {
|
||||
|
||||
func render() async throws -> AnySendableHTML {
|
||||
switch route {
|
||||
case .login(let route):
|
||||
return try await route.renderView(isHtmxRequest: isHtmxRequest)
|
||||
case .project(let route):
|
||||
return try await route.renderView(isHtmxRequest: isHtmxRequest)
|
||||
case .room(let route):
|
||||
@@ -17,23 +19,24 @@ extension ViewController.Request {
|
||||
return try await route.renderView(isHtmxRequest: isHtmxRequest)
|
||||
default:
|
||||
// FIX: FIX
|
||||
return mainPage
|
||||
return _render(isHtmxRequest: false) {
|
||||
div { "Fix me!" }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extension SiteRoute.View.ProjectRoute {
|
||||
func renderView(isHtmxRequest: Bool) async throws -> AnySendableHTML {
|
||||
switch self {
|
||||
case .index:
|
||||
return MainPage(active: .projects) {
|
||||
_render(isHtmxRequest: isHtmxRequest) {
|
||||
switch self {
|
||||
case .index:
|
||||
ProjectView(project: .mock)
|
||||
case .form(let dismiss):
|
||||
ProjectForm(dismiss: dismiss)
|
||||
case .create:
|
||||
div { "Fix me!" }
|
||||
}
|
||||
case .form(let dismiss):
|
||||
return ProjectForm(dismiss: dismiss)
|
||||
|
||||
case .create:
|
||||
return mainPage
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -44,7 +47,7 @@ extension SiteRoute.View.RoomRoute {
|
||||
case .form(let dismiss):
|
||||
return RoomForm(dismiss: dismiss)
|
||||
case .index:
|
||||
return MainPage(active: .rooms) {
|
||||
return _render(isHtmxRequest: isHtmxRequest, active: .rooms) {
|
||||
RoomsView(rooms: Room.mocks)
|
||||
}
|
||||
}
|
||||
@@ -55,7 +58,7 @@ extension SiteRoute.View.FrictionRateRoute {
|
||||
func renderView(isHtmxRequest: Bool) async throws -> AnySendableHTML {
|
||||
switch self {
|
||||
case .index:
|
||||
return MainPage(active: .frictionRate) {
|
||||
return _render(isHtmxRequest: isHtmxRequest, active: .frictionRate) {
|
||||
FrictionRateView()
|
||||
}
|
||||
case .form(let type, let dismiss):
|
||||
@@ -86,7 +89,7 @@ extension SiteRoute.View.EffectiveLengthRoute {
|
||||
func renderView(isHtmxRequest: Bool) async throws -> AnySendableHTML {
|
||||
switch self {
|
||||
case .index:
|
||||
return MainPage(active: .effectiveLength) {
|
||||
return _render(isHtmxRequest: isHtmxRequest, active: .effectiveLength) {
|
||||
EffectiveLengthsView(effectiveLengths: EffectiveLength.mocks)
|
||||
}
|
||||
case .form(let dismiss):
|
||||
@@ -107,12 +110,12 @@ extension SiteRoute.View.UserRoute {
|
||||
|
||||
func renderView(isHtmxRequest: Bool) async throws -> AnySendableHTML {
|
||||
switch self {
|
||||
case .login(.index):
|
||||
return MainPage(active: .projects, showSidebar: false) {
|
||||
LoginForm()
|
||||
}
|
||||
// case .login(.index):
|
||||
// return _render(isHtmxRequest: isHtmxRequest, showSidebar: false) {
|
||||
// LoginForm()
|
||||
// }
|
||||
case .signup(.index):
|
||||
return MainPage(active: .projects, showSidebar: false) {
|
||||
return _render(isHtmxRequest: isHtmxRequest, showSidebar: false) {
|
||||
LoginForm(style: .signup)
|
||||
}
|
||||
default:
|
||||
@@ -121,31 +124,33 @@ extension SiteRoute.View.UserRoute {
|
||||
}
|
||||
}
|
||||
|
||||
private let mainPage: AnySendableHTML = {
|
||||
MainPage(active: .projects) {
|
||||
div {
|
||||
h1 { "It works!" }
|
||||
extension SiteRoute.View.LoginRoute {
|
||||
func renderView(isHtmxRequest: Bool) async throws -> AnySendableHTML {
|
||||
_render(isHtmxRequest: isHtmxRequest, showSidebar: false) {
|
||||
switch self {
|
||||
case .index:
|
||||
LoginForm()
|
||||
case .submit:
|
||||
// FIX:
|
||||
div { "Fix me!" }
|
||||
}
|
||||
}
|
||||
}
|
||||
}()
|
||||
}
|
||||
|
||||
@Sendable
|
||||
private func render<C: HTML>(
|
||||
_ mainPage: (C) async throws -> AnySendableHTML,
|
||||
_ isHtmxRequest: Bool,
|
||||
@HTMLBuilder html: () -> C
|
||||
) async rethrows -> AnySendableHTML where C: Sendable {
|
||||
guard isHtmxRequest else {
|
||||
return try await mainPage(html())
|
||||
private func _render<C: HTML>(
|
||||
isHtmxRequest: Bool,
|
||||
active activeTab: Sidebar.ActiveTab = .projects,
|
||||
showSidebar: Bool = true,
|
||||
@HTMLBuilder inner: () -> C
|
||||
) -> AnySendableHTML where C: Sendable {
|
||||
if isHtmxRequest {
|
||||
return inner()
|
||||
}
|
||||
return MainPage(
|
||||
active: activeTab,
|
||||
showSidebar: showSidebar
|
||||
) {
|
||||
inner()
|
||||
}
|
||||
return html()
|
||||
}
|
||||
|
||||
@Sendable
|
||||
private func render<C: HTML>(
|
||||
_ mainPage: (C) async throws -> AnySendableHTML,
|
||||
_ isHtmxRequest: Bool,
|
||||
_ html: @autoclosure @escaping () -> C
|
||||
) async rethrows -> AnySendableHTML where C: Sendable {
|
||||
try await render(mainPage, isHtmxRequest) { html() }
|
||||
}
|
||||
|
||||
@@ -11,135 +11,77 @@ struct LoginForm: HTML, Sendable {
|
||||
}
|
||||
|
||||
var body: some HTML {
|
||||
form {
|
||||
fieldset(.class("fieldset bg-base-200 border-base-300 rounded-box w-xl border p-4")) {
|
||||
legend(.class("fieldset-legend")) { style.title }
|
||||
div(
|
||||
.id("loginForm"),
|
||||
.class("flex items-center justify-center")
|
||||
) {
|
||||
form {
|
||||
fieldset(.class("fieldset bg-base-200 border-base-300 rounded-box w-xl border p-4")) {
|
||||
legend(.class("fieldset-legend")) { style.title }
|
||||
|
||||
if style == .signup {
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.user)
|
||||
input(
|
||||
.type(.text), .required, .placeholder("Username"),
|
||||
.minlength("3"), .pattern(.username)
|
||||
)
|
||||
}
|
||||
div(.class("validator-hint hidden")) {
|
||||
"Enter valid username"
|
||||
br()
|
||||
"Must be at least 3 characters"
|
||||
}
|
||||
}
|
||||
|
||||
if style == .signup {
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.user)
|
||||
SVG(.email)
|
||||
input(
|
||||
.type(.text), .required, .placeholder("Username"),
|
||||
.minlength("3"), .pattern(.username)
|
||||
.type(.email), .placeholder("Email"), .required
|
||||
)
|
||||
}
|
||||
div(.class("validator-hint hidden")) {
|
||||
"Enter valid username"
|
||||
br()
|
||||
"Must be at least 3 characters"
|
||||
}
|
||||
}
|
||||
div(.class("validator-hint hidden")) { "Enter valid email address." }
|
||||
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.email)
|
||||
input(
|
||||
.type(.email), .placeholder("Email"), .required
|
||||
)
|
||||
}
|
||||
div(.class("validator-hint hidden")) { "Enter valid email address." }
|
||||
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.key)
|
||||
input(
|
||||
.type(.password), .placeholder("Password"), .required,
|
||||
.pattern(.password), .minlength("8")
|
||||
)
|
||||
}
|
||||
|
||||
if style == .signup {
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.key)
|
||||
input(
|
||||
.type(.password), .placeholder("Confirm Password"), .required,
|
||||
.type(.password), .placeholder("Password"), .required,
|
||||
.pattern(.password), .minlength("8")
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
div(.class("validator-hint hidden")) {
|
||||
p {
|
||||
"Must be more than 8 characters, including"
|
||||
br()
|
||||
"At least one number"
|
||||
br()
|
||||
"At least one lowercase letter"
|
||||
br()
|
||||
"At least one uppercase letter"
|
||||
if style == .signup {
|
||||
label(.class("input validator w-full")) {
|
||||
SVG(.key)
|
||||
input(
|
||||
.type(.password), .placeholder("Confirm Password"), .required,
|
||||
.pattern(.password), .minlength("8")
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
div(.class("validator-hint hidden")) {
|
||||
p {
|
||||
"Must be more than 8 characters, including"
|
||||
br()
|
||||
"At least one number"
|
||||
br()
|
||||
"At least one lowercase letter"
|
||||
br()
|
||||
"At least one uppercase letter"
|
||||
}
|
||||
}
|
||||
|
||||
button(.class("btn btn-secondary mt-4")) { style.title }
|
||||
a(
|
||||
.class("btn btn-link mt-4"),
|
||||
.href(route: style == .signup ? .login(.index) : .user(.signup(.index)))
|
||||
) {
|
||||
style == .login ? "Sign Up" : "Login"
|
||||
}
|
||||
}
|
||||
|
||||
button(.class("btn btn-neutral mt-4")) { style.title }
|
||||
}
|
||||
}
|
||||
// div(.class("flex items-center justify-center")) {
|
||||
// div(.class("w-full mx-auto")) {
|
||||
// h1(.class("text-2xl font-bold")) { style.title }
|
||||
// form(
|
||||
// .class("w-full h-screen")
|
||||
// ) {
|
||||
// fieldset(.class("fieldset w-full")) {
|
||||
// legend(.class("fieldset-legend")) { "Email" }
|
||||
// label(.class("input validator")) {
|
||||
// SVG(.email)
|
||||
// input(
|
||||
// .type(.email), .placeholder("mail@site.com"), .required,
|
||||
// .autofocus
|
||||
// )
|
||||
// }
|
||||
// div(.class("validator-hint hidden")) { "Enter valid email address." }
|
||||
// }
|
||||
//
|
||||
// if style == .signup {
|
||||
// fieldset(.class("fieldset")) {
|
||||
// legend(.class("fieldset-legend")) { "Name" }
|
||||
// label(.class("input validator")) {
|
||||
// input(
|
||||
// .type(.text), .placeholder("Username"), .required,
|
||||
// .init(name: "pattern", value: "[A-Za-z][A-Za-z0-9\\-]*"),
|
||||
// .init(name: "minlength", value: "3")
|
||||
// )
|
||||
// }
|
||||
// div(.class("validator-hint hidden")) { "Enter valid email address." }
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// fieldset(.class("fieldset")) {
|
||||
// legend(.class("fieldset-legend")) { "Password" }
|
||||
// label(.class("input validator")) {
|
||||
// SVG(.key)
|
||||
// input(
|
||||
// .type(.password), .placeholder("Password"), .required,
|
||||
// .init(name: "pattern", value: "(?=.*\\d)(?=.*[a-z])(?=.*[A-Z]).{8,}"),
|
||||
// .init(name: "minlength", value: "8")
|
||||
// )
|
||||
// }
|
||||
// if style == .signup {
|
||||
// label(.class("input validator")) {
|
||||
// SVG(.key)
|
||||
// input(
|
||||
// .type(.password), .placeholder("Confirm Password"), .required,
|
||||
// .init(name: "pattern", value: "(?=.*\\d)(?=.*[a-z])(?=.*[A-Z]).{8,}"),
|
||||
// .init(name: "minlength", value: "8")
|
||||
// )
|
||||
// }
|
||||
// }
|
||||
// div(.class("validator-hint hidden")) {
|
||||
// p {
|
||||
// "Must be more than 8 characters, including"
|
||||
// br()
|
||||
// "At least one number"
|
||||
// br()
|
||||
// "At least one lowercase letter"
|
||||
// br()
|
||||
// "At least one uppercase letter"
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// SubmitButton(title: style.title)
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user