added typeaheead and introspetion

This commit is contained in:
Mark Gregory
2026-10-19 09:32:16 +01:00
parent 23513d3f2e
commit 66e1845fc6
+26 -5
View File
@@ -29,6 +29,7 @@ struct DBSynSchemaDiagramView: View {
@State private var showViews = true
@State private var showingObjects = true
@State private var includedObjects: Set<String> = []
@State private var selectionRevision = 0
@State private var theme = "Ocean"
@State private var showAllColumns = false
@State private var relatedOnly = false
@@ -168,8 +169,8 @@ struct DBSynSchemaDiagramView: View {
.font(.caption.monospacedDigit()).foregroundStyle(.secondary)
}
HStack {
Button("All") { includedObjects = Set(allObjects); saveOptions() }
Button("None") { includedObjects.removeAll(); saveOptions() }
Button("All") { updateIncludedObjects(Set(allObjects)) }
Button("None") { updateIncludedObjects([]) }
Spacer()
}.buttonStyle(.link)
ScrollView {
@@ -178,9 +179,10 @@ struct DBSynSchemaDiagramView: View {
Toggle(isOn: Binding(
get: { includedObjects.contains(name) },
set: { enabled in
if enabled { includedObjects.insert(name) }
else { includedObjects.remove(name) }
saveOptions()
var updated = includedObjects
if enabled { updated.insert(name) }
else { updated.remove(name) }
updateIncludedObjects(updated)
})) {
Label(name, systemImage: snapshot?.views.contains(name) == true ? "eye" : "tablecells")
.lineLimit(1).font(.system(size: 12))
@@ -227,6 +229,7 @@ struct DBSynSchemaDiagramView: View {
.frame(width: canvasWidth * zoom, height: canvasHeight * zoom, alignment: .topLeading)
}
.background(Color(nsColor: .textBackgroundColor))
.id(selectionRevision)
.onChange(of: snapshot?.loadedAt) { _, _ in
if UserDefaults.standard.stringArray(forKey: selectionKey) == nil {
includedObjects = Set(allObjects)
@@ -327,6 +330,24 @@ struct DBSynSchemaDiagramView: View {
}
@State private var dragOrigins: [String: CGPoint] = [:]
// Rebuild the visible canvas whenever the selected objects change. The
// previous implementation only saved the checkboxes, leaving the diagram
// scrolled to stale positions after None / All / individual selections.
private func updateIncludedObjects(_ updated: Set<String>) {
let valid = updated.intersection(Set(allObjects))
guard valid != includedObjects else { return }
includedObjects = valid
if let selectedObject, !valid.contains(selectedObject) {
self.selectedObject = nil
}
// Keep the selected subset compact, rather than retaining the old
// coordinates of objects from a much larger diagram.
arrange()
savePositions()
saveOptions()
selectionRevision += 1
}
private func arrange() {
let names = allObjects.filter { includedObjects.contains($0) }
let countPerRow = max(1, Int(ceil(sqrt(Double(max(1, names.count))))))