feat-WIP: Adds update to trunk-size form, currently height / width is not working though.
This commit is contained in:
@@ -5231,6 +5231,9 @@
|
|||||||
.m-1 {
|
.m-1 {
|
||||||
margin: calc(var(--spacing) * 1);
|
margin: calc(var(--spacing) * 1);
|
||||||
}
|
}
|
||||||
|
.m-4 {
|
||||||
|
margin: calc(var(--spacing) * 4);
|
||||||
|
}
|
||||||
.m-6 {
|
.m-6 {
|
||||||
margin: calc(var(--spacing) * 6);
|
margin: calc(var(--spacing) * 6);
|
||||||
}
|
}
|
||||||
@@ -5374,6 +5377,9 @@
|
|||||||
.-my-2 {
|
.-my-2 {
|
||||||
margin-block: calc(var(--spacing) * -2);
|
margin-block: calc(var(--spacing) * -2);
|
||||||
}
|
}
|
||||||
|
.-my-4 {
|
||||||
|
margin-block: calc(var(--spacing) * -4);
|
||||||
|
}
|
||||||
.my-1 {
|
.my-1 {
|
||||||
margin-block: calc(var(--spacing) * 1);
|
margin-block: calc(var(--spacing) * 1);
|
||||||
}
|
}
|
||||||
@@ -5646,6 +5652,9 @@
|
|||||||
.mt-1 {
|
.mt-1 {
|
||||||
margin-top: calc(var(--spacing) * 1);
|
margin-top: calc(var(--spacing) * 1);
|
||||||
}
|
}
|
||||||
|
.mt-2 {
|
||||||
|
margin-top: calc(var(--spacing) * 2);
|
||||||
|
}
|
||||||
.mt-4 {
|
.mt-4 {
|
||||||
margin-top: calc(var(--spacing) * 4);
|
margin-top: calc(var(--spacing) * 4);
|
||||||
}
|
}
|
||||||
@@ -6604,9 +6613,6 @@
|
|||||||
.max-w-1\/3 {
|
.max-w-1\/3 {
|
||||||
max-width: calc(1/3 * 100%);
|
max-width: calc(1/3 * 100%);
|
||||||
}
|
}
|
||||||
.max-w-\[300px\] {
|
|
||||||
max-width: 300px;
|
|
||||||
}
|
|
||||||
.flex-1 {
|
.flex-1 {
|
||||||
flex: 1;
|
flex: 1;
|
||||||
}
|
}
|
||||||
@@ -6812,6 +6818,9 @@
|
|||||||
.flex-col {
|
.flex-col {
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
}
|
}
|
||||||
|
.flex-row {
|
||||||
|
flex-direction: row;
|
||||||
|
}
|
||||||
.flex-wrap {
|
.flex-wrap {
|
||||||
flex-wrap: wrap;
|
flex-wrap: wrap;
|
||||||
}
|
}
|
||||||
@@ -7905,6 +7914,12 @@
|
|||||||
.py-2 {
|
.py-2 {
|
||||||
padding-block: calc(var(--spacing) * 2);
|
padding-block: calc(var(--spacing) * 2);
|
||||||
}
|
}
|
||||||
|
.py-4 {
|
||||||
|
padding-block: calc(var(--spacing) * 4);
|
||||||
|
}
|
||||||
|
.py-6 {
|
||||||
|
padding-block: calc(var(--spacing) * 6);
|
||||||
|
}
|
||||||
.ps-2 {
|
.ps-2 {
|
||||||
padding-inline-start: calc(var(--spacing) * 2);
|
padding-inline-start: calc(var(--spacing) * 2);
|
||||||
}
|
}
|
||||||
@@ -7982,6 +7997,14 @@
|
|||||||
font-size: var(--text-3xl);
|
font-size: var(--text-3xl);
|
||||||
line-height: var(--tw-leading, var(--text-3xl--line-height));
|
line-height: var(--tw-leading, var(--text-3xl--line-height));
|
||||||
}
|
}
|
||||||
|
.text-4xl {
|
||||||
|
font-size: var(--text-4xl);
|
||||||
|
line-height: var(--tw-leading, var(--text-4xl--line-height));
|
||||||
|
}
|
||||||
|
.text-base {
|
||||||
|
font-size: var(--text-base);
|
||||||
|
line-height: var(--tw-leading, var(--text-base--line-height));
|
||||||
|
}
|
||||||
.text-lg {
|
.text-lg {
|
||||||
font-size: var(--text-lg);
|
font-size: var(--text-lg);
|
||||||
line-height: var(--tw-leading, var(--text-lg--line-height));
|
line-height: var(--tw-leading, var(--text-lg--line-height));
|
||||||
|
|||||||
@@ -11,6 +11,9 @@ extension DatabaseClient {
|
|||||||
public var delete: @Sendable (DuctSizing.TrunkSize.ID) async throws -> Void
|
public var delete: @Sendable (DuctSizing.TrunkSize.ID) async throws -> Void
|
||||||
public var fetch: @Sendable (Project.ID) async throws -> [DuctSizing.TrunkSize]
|
public var fetch: @Sendable (Project.ID) async throws -> [DuctSizing.TrunkSize]
|
||||||
public var get: @Sendable (DuctSizing.TrunkSize.ID) async throws -> DuctSizing.TrunkSize?
|
public var get: @Sendable (DuctSizing.TrunkSize.ID) async throws -> DuctSizing.TrunkSize?
|
||||||
|
public var update:
|
||||||
|
@Sendable (DuctSizing.TrunkSize.ID, DuctSizing.TrunkSize.Update) async throws ->
|
||||||
|
DuctSizing.TrunkSize
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -82,6 +85,21 @@ extension DatabaseClient.TrunkSizes: TestDependencyKey {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
return try await model.toDTO(on: database)
|
return try await model.toDTO(on: database)
|
||||||
|
},
|
||||||
|
update: { id, updates in
|
||||||
|
guard
|
||||||
|
let model =
|
||||||
|
try await TrunkModel
|
||||||
|
.query(on: database)
|
||||||
|
.with(\.$rooms)
|
||||||
|
.filter(\.$id == id)
|
||||||
|
.first()
|
||||||
|
else {
|
||||||
|
throw NotFoundError()
|
||||||
|
}
|
||||||
|
try updates.validate()
|
||||||
|
try await model.applyUpdates(updates, on: database)
|
||||||
|
return try await model.toDTO(on: database)
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@@ -107,7 +125,21 @@ extension DuctSizing.TrunkSize.Create {
|
|||||||
height: height
|
height: height
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
extension DuctSizing.TrunkSize.Update {
|
||||||
|
func validate() throws(ValidationError) {
|
||||||
|
if let rooms {
|
||||||
|
guard rooms.count > 0 else {
|
||||||
|
throw ValidationError("Trunk size should have associated rooms / registers.")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if let height {
|
||||||
|
guard height > 0 else {
|
||||||
|
throw ValidationError("Trunk size height should be greater than 0.")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
extension DuctSizing.TrunkSize {
|
extension DuctSizing.TrunkSize {
|
||||||
@@ -250,4 +282,62 @@ final class TrunkModel: Model, @unchecked Sendable {
|
|||||||
)
|
)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func applyUpdates(
|
||||||
|
_ updates: DuctSizing.TrunkSize.Update,
|
||||||
|
on database: any Database
|
||||||
|
) async throws {
|
||||||
|
if let type = updates.type, type.rawValue != self.type {
|
||||||
|
self.type = type.rawValue
|
||||||
|
}
|
||||||
|
if let height = updates.height, height != self.height {
|
||||||
|
self.height = height
|
||||||
|
}
|
||||||
|
if hasChanges {
|
||||||
|
try await self.save(on: database)
|
||||||
|
}
|
||||||
|
|
||||||
|
guard let updateRooms = updates.rooms else {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// Update rooms.
|
||||||
|
let rooms = try await TrunkRoomModel.query(on: database)
|
||||||
|
.with(\.$room)
|
||||||
|
.filter(\.$trunk.$id == requireID())
|
||||||
|
.all()
|
||||||
|
|
||||||
|
for (roomID, registers) in updateRooms {
|
||||||
|
if let currRoom = rooms.first(where: { $0.$room.id == roomID }) {
|
||||||
|
database.logger.debug("CURRENT ROOM: \(currRoom.room.name)")
|
||||||
|
if registers != currRoom.registers {
|
||||||
|
database.logger.debug("Updating registers for: \(currRoom.room.name)")
|
||||||
|
currRoom.registers = registers
|
||||||
|
}
|
||||||
|
if currRoom.hasChanges {
|
||||||
|
try await currRoom.save(on: database)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
database.logger.debug("CREATING NEW TrunkRoomModel")
|
||||||
|
let newModel = try TrunkRoomModel(
|
||||||
|
trunkID: requireID(),
|
||||||
|
roomID: roomID,
|
||||||
|
registers: registers,
|
||||||
|
type: .init(rawValue: type)!
|
||||||
|
)
|
||||||
|
try await newModel.save(on: database)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let roomsToDelete = rooms.filter {
|
||||||
|
!updateRooms.keys.contains($0.$room.id)
|
||||||
|
}
|
||||||
|
|
||||||
|
for room in roomsToDelete {
|
||||||
|
try await room.delete(on: database)
|
||||||
|
}
|
||||||
|
|
||||||
|
database.logger.debug("DONE WITH UPDATES")
|
||||||
|
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -126,6 +126,8 @@ public enum DuctSizing {
|
|||||||
|
|
||||||
extension DuctSizing {
|
extension DuctSizing {
|
||||||
|
|
||||||
|
// Represents the database model that the duct sizes have been calculated
|
||||||
|
// for.
|
||||||
public struct TrunkContainer: Codable, Equatable, Identifiable, Sendable {
|
public struct TrunkContainer: Codable, Equatable, Identifiable, Sendable {
|
||||||
public var id: TrunkSize.ID { trunk.id }
|
public var id: TrunkSize.ID { trunk.id }
|
||||||
|
|
||||||
@@ -141,6 +143,7 @@ extension DuctSizing {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Represents the database model.
|
||||||
public struct TrunkSize: Codable, Equatable, Identifiable, Sendable {
|
public struct TrunkSize: Codable, Equatable, Identifiable, Sendable {
|
||||||
|
|
||||||
public let id: UUID
|
public let id: UUID
|
||||||
@@ -187,6 +190,23 @@ extension DuctSizing.TrunkSize {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public struct Update: Codable, Equatable, Sendable {
|
||||||
|
|
||||||
|
public let type: TrunkType?
|
||||||
|
public let rooms: [Room.ID: [Int]]?
|
||||||
|
public let height: Int?
|
||||||
|
|
||||||
|
public init(
|
||||||
|
type: DuctSizing.TrunkSize.TrunkType? = nil,
|
||||||
|
rooms: [Room.ID: [Int]]? = nil,
|
||||||
|
height: Int? = nil
|
||||||
|
) {
|
||||||
|
self.type = type
|
||||||
|
self.rooms = rooms
|
||||||
|
self.height = height
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// TODO: Make registers non-optional
|
// TODO: Make registers non-optional
|
||||||
public struct RoomProxy: Codable, Equatable, Identifiable, Sendable {
|
public struct RoomProxy: Codable, Equatable, Identifiable, Sendable {
|
||||||
|
|
||||||
|
|||||||
@@ -13,6 +13,14 @@ extension SiteRoute.View.ProjectRoute.DuctSizingRoute.TrunkSizeForm {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func toUpdate(logger: Logger? = nil) throws -> DuctSizing.TrunkSize.Update {
|
||||||
|
try .init(
|
||||||
|
type: type,
|
||||||
|
rooms: makeRooms(logger: logger),
|
||||||
|
height: height
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
func makeRooms(logger: Logger?) throws -> [Room.ID: [Int]] {
|
func makeRooms(logger: Logger?) throws -> [Room.ID: [Int]] {
|
||||||
var retval = [Room.ID: [Int]]()
|
var retval = [Room.ID: [Int]]()
|
||||||
for room in rooms {
|
for room in rooms {
|
||||||
|
|||||||
@@ -581,8 +581,9 @@ extension SiteRoute.View.ProjectRoute.DuctSizingRoute {
|
|||||||
}
|
}
|
||||||
|
|
||||||
case .update(let id, let form):
|
case .update(let id, let form):
|
||||||
// FIX:
|
return await view(on: request, projectID: projectID) {
|
||||||
fatalError()
|
_ = try await database.trunkSizes.update(id, form.toUpdate())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -176,6 +176,7 @@ struct DuctSizingView: HTML, Sendable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct TrunkTable: HTML, Sendable {
|
struct TrunkTable: HTML, Sendable {
|
||||||
|
|
||||||
let trunks: [DuctSizing.TrunkContainer]
|
let trunks: [DuctSizing.TrunkContainer]
|
||||||
let rooms: [DuctSizing.RoomContainer]
|
let rooms: [DuctSizing.RoomContainer]
|
||||||
|
|
||||||
@@ -196,86 +197,89 @@ struct DuctSizingView: HTML, Sendable {
|
|||||||
}
|
}
|
||||||
tbody {
|
tbody {
|
||||||
for trunk in trunks {
|
for trunk in trunks {
|
||||||
tr {
|
TrunkRow(trunk: trunk, rooms: rooms)
|
||||||
td(.class("space-x-2")) {
|
|
||||||
// div(.class("flex flex-wrap space-x-2 max-w-1/3")) {
|
|
||||||
for id in registerIDS(trunk.trunk) {
|
|
||||||
Badge { id }
|
|
||||||
}
|
|
||||||
// }
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
Number(trunk.ductSize.designCFM.value, digits: 0)
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
Number(trunk.ductSize.roundSize, digits: 1)
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
Number(trunk.ductSize.velocity)
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
Badge(number: trunk.ductSize.finalSize)
|
|
||||||
.attributes(.class("badge-secondary"))
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
Badge(number: trunk.ductSize.flexSize)
|
|
||||||
.attributes(.class("badge-primary"))
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
if let width = trunk.ductSize.width {
|
|
||||||
Number(width)
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
td {
|
|
||||||
|
|
||||||
div(.class("flex justify-between items-center space-x-4")) {
|
|
||||||
div {
|
|
||||||
if let height = trunk.ductSize.height {
|
|
||||||
Number(height)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
div {
|
|
||||||
div(.class("join")) {
|
|
||||||
TrashButton()
|
|
||||||
.attributes(.class("join-item btn-ghost"))
|
|
||||||
.attributes(
|
|
||||||
// .hx.delete(
|
|
||||||
// route: .project(
|
|
||||||
// .detail(
|
|
||||||
// projectID,
|
|
||||||
// .ductSizing(
|
|
||||||
// .deleteRectangularSize(
|
|
||||||
// room.roomID,
|
|
||||||
// room.rectangularSize?.id ?? .init())
|
|
||||||
// )
|
|
||||||
// )
|
|
||||||
// )
|
|
||||||
// ),
|
|
||||||
.hx.target("closest tr"),
|
|
||||||
.hx.swap(.outerHTML)
|
|
||||||
// when: room.rectangularSize != nil
|
|
||||||
)
|
|
||||||
|
|
||||||
EditButton()
|
|
||||||
.attributes(
|
|
||||||
.class("join-item btn-ghost"),
|
|
||||||
// .showModal(id: RectangularSizeForm.id(room))
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// FIX: Add Trunk form.
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func registerIDS(_ trunk: DuctSizing.TrunkSize) -> [String] {
|
}
|
||||||
|
|
||||||
|
struct TrunkRow: HTML, Sendable {
|
||||||
|
|
||||||
|
@Environment(ProjectViewValue.$projectID) var projectID
|
||||||
|
|
||||||
|
let trunk: DuctSizing.TrunkContainer
|
||||||
|
let rooms: [DuctSizing.RoomContainer]
|
||||||
|
|
||||||
|
var body: some HTML<HTMLTag.tr> {
|
||||||
|
tr {
|
||||||
|
td(.class("space-x-2")) {
|
||||||
|
for id in registerIDS(trunk.trunk) {
|
||||||
|
Badge { id }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
Number(trunk.ductSize.designCFM.value, digits: 0)
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
Number(trunk.ductSize.roundSize, digits: 1)
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
Number(trunk.ductSize.velocity)
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
Badge(number: trunk.ductSize.finalSize)
|
||||||
|
.attributes(.class("badge-secondary"))
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
Badge(number: trunk.ductSize.flexSize)
|
||||||
|
.attributes(.class("badge-primary"))
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
if let width = trunk.ductSize.width {
|
||||||
|
Number(width)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
td {
|
||||||
|
|
||||||
|
div(.class("flex justify-between items-center space-x-4")) {
|
||||||
|
div {
|
||||||
|
if let height = trunk.ductSize.height {
|
||||||
|
Number(height)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
div {
|
||||||
|
div(.class("join")) {
|
||||||
|
TrashButton()
|
||||||
|
.attributes(.class("join-item btn-ghost"))
|
||||||
|
.attributes(
|
||||||
|
.hx.delete(route: deleteRoute),
|
||||||
|
.hx.target("closest tr"),
|
||||||
|
.hx.swap(.outerHTML)
|
||||||
|
)
|
||||||
|
|
||||||
|
EditButton()
|
||||||
|
.attributes(
|
||||||
|
.class("join-item btn-ghost"),
|
||||||
|
.showModal(id: TrunkSizeForm.id(trunk))
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TrunkSizeForm(trunk: trunk, rooms: rooms, dismiss: true)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private var deleteRoute: SiteRoute.View {
|
||||||
|
.project(.detail(projectID, .ductSizing(.trunk(.delete(trunk.id)))))
|
||||||
|
}
|
||||||
|
|
||||||
|
private func registerIDS(_ trunk: DuctSizing.TrunkSize) -> [String] {
|
||||||
trunk.rooms.reduce(into: []) { array, room in
|
trunk.rooms.reduce(into: []) { array, room in
|
||||||
array = room.registers.reduce(into: array) { array, register in
|
array = room.registers.reduce(into: array) { array, register in
|
||||||
if let room =
|
if let room =
|
||||||
|
|||||||
@@ -5,27 +5,47 @@ import Styleguide
|
|||||||
|
|
||||||
struct TrunkSizeForm: HTML, Sendable {
|
struct TrunkSizeForm: HTML, Sendable {
|
||||||
|
|
||||||
static func id() -> String {
|
static func id(_ trunk: DuctSizing.TrunkContainer? = nil) -> String {
|
||||||
"trunkSizeForm"
|
let base = "trunkSizeForm"
|
||||||
|
guard let trunk else { return base }
|
||||||
|
return "\(base)_\(trunk.id.idString)"
|
||||||
}
|
}
|
||||||
|
|
||||||
@Environment(ProjectViewValue.$projectID) var projectID
|
@Environment(ProjectViewValue.$projectID) var projectID
|
||||||
|
|
||||||
|
let container: DuctSizing.TrunkContainer?
|
||||||
let rooms: [DuctSizing.RoomContainer]
|
let rooms: [DuctSizing.RoomContainer]
|
||||||
let dismiss: Bool
|
let dismiss: Bool
|
||||||
|
|
||||||
|
var trunk: DuctSizing.TrunkSize? {
|
||||||
|
container?.trunk
|
||||||
|
}
|
||||||
|
|
||||||
|
init(
|
||||||
|
trunk: DuctSizing.TrunkContainer? = nil,
|
||||||
|
rooms: [DuctSizing.RoomContainer],
|
||||||
|
dismiss: Bool = true
|
||||||
|
) {
|
||||||
|
self.container = trunk
|
||||||
|
self.rooms = rooms
|
||||||
|
self.dismiss = dismiss
|
||||||
|
}
|
||||||
|
|
||||||
var route: String {
|
var route: String {
|
||||||
SiteRoute.View.router
|
SiteRoute.View.router
|
||||||
.path(for: .project(.detail(projectID, .ductSizing(.index))))
|
.path(for: .project(.detail(projectID, .ductSizing(.index))))
|
||||||
.appendingPath(SiteRoute.View.ProjectRoute.DuctSizingRoute.TrunkRoute.rootPath)
|
.appendingPath(SiteRoute.View.ProjectRoute.DuctSizingRoute.TrunkRoute.rootPath)
|
||||||
|
.appendingPath(trunk?.id)
|
||||||
}
|
}
|
||||||
|
|
||||||
var body: some HTML {
|
var body: some HTML {
|
||||||
ModalForm(id: Self.id(), dismiss: dismiss) {
|
ModalForm(id: Self.id(container), dismiss: dismiss) {
|
||||||
h1(.class("text-lg font-bold mb-4")) { "Trunk Size" }
|
h1(.class("text-lg font-bold mb-4")) { "Trunk Size" }
|
||||||
form(
|
form(
|
||||||
.class("space-y-4"),
|
.class("space-y-4"),
|
||||||
.hx.post(route),
|
trunk == nil
|
||||||
|
? .hx.post(route)
|
||||||
|
: .hx.patch(route),
|
||||||
.hx.target("body"),
|
.hx.target("body"),
|
||||||
.hx.swap(.outerHTML)
|
.hx.swap(.outerHTML)
|
||||||
) {
|
) {
|
||||||
@@ -38,6 +58,7 @@ struct TrunkSizeForm: HTML, Sendable {
|
|||||||
select(.name("type")) {
|
select(.name("type")) {
|
||||||
for type in DuctSizing.TrunkSize.TrunkType.allCases {
|
for type in DuctSizing.TrunkSize.TrunkType.allCases {
|
||||||
option(.value(type.rawValue)) { type.rawValue.capitalized }
|
option(.value(type.rawValue)) { type.rawValue.capitalized }
|
||||||
|
.attributes(.selected, when: trunk?.type == type)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -46,6 +67,7 @@ struct TrunkSizeForm: HTML, Sendable {
|
|||||||
"Height",
|
"Height",
|
||||||
.type(.text),
|
.type(.text),
|
||||||
.name("height"),
|
.name("height"),
|
||||||
|
.value(trunk?.height),
|
||||||
.placeholder("8 (Optional)"),
|
.placeholder("8 (Optional)"),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@@ -63,6 +85,10 @@ struct TrunkSizeForm: HTML, Sendable {
|
|||||||
.name("rooms"),
|
.name("rooms"),
|
||||||
.value("\(room.roomID)_\(room.roomRegister)")
|
.value("\(room.roomID)_\(room.roomRegister)")
|
||||||
)
|
)
|
||||||
|
.attributes(
|
||||||
|
.checked,
|
||||||
|
when: trunk == nil ? false : trunk!.rooms.hasRoom(room)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -75,3 +101,12 @@ struct TrunkSizeForm: HTML, Sendable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
extension Array where Element == DuctSizing.TrunkSize.RoomProxy {
|
||||||
|
func hasRoom(_ room: DuctSizing.RoomContainer) -> Bool {
|
||||||
|
first {
|
||||||
|
$0.id == room.roomID
|
||||||
|
&& $0.registers.contains(room.roomRegister)
|
||||||
|
} != nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user