Skip to content
Open
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions Examples/Sources/ControlsExample/ControlsApp.swift
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ struct ControlsApp: App {
@State var text = ""
@State var flavor: String? = nil
@State var enabled = true
@State var progressViewSize: Int = 10
@State var isProgressViewResizable = true

var body: some Scene {
WindowGroup("ControlsApp") {
Expand Down Expand Up @@ -69,6 +71,12 @@ struct ControlsApp: App {
Text("Value: \(text)")
}

Toggle("Enable ProgressView resizability", active: $isProgressViewResizable)
Slider($progressViewSize, minimum: 10, maximum: 100)
ProgressView()
.resizable(isProgressViewResizable)
.frame(width: progressViewSize, height: progressViewSize)

VStack {
Text("Drop down")
HStack {
Expand All @@ -82,6 +90,7 @@ struct ControlsApp: App {
Toggle(enabled ? "Disable all" : "Enable all", active: $enabled)
.padding()
}

}.defaultSize(width: 400, height: 600)
}
}
45 changes: 41 additions & 4 deletions Sources/SwiftCrossUI/Views/ProgressView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ public struct ProgressView<Label: View>: View {
private var label: Label
private var progress: Double?
private var kind: Kind
private var isSpinnerResizable: Bool = false

private enum Kind {
case spinner
Expand All @@ -23,7 +24,7 @@ public struct ProgressView<Label: View>: View {
private var progressIndicator: some View {
switch kind {
case .spinner:
ProgressSpinnerView()
ProgressSpinnerView(isResizable: isSpinnerResizable)
case .bar:
ProgressBarView(value: progress)
}
Expand All @@ -50,6 +51,14 @@ public struct ProgressView<Label: View>: View {
self.kind = .bar
self.progress = value.map(Double.init)
}

/// Makes the ProgressView resize to fit the available space.
/// Only affects `Kind.spinner`.
public func resizable(_ isResizable: Bool = true) -> Self {
var progressView = self
progressView.isSpinnerResizable = isResizable
return progressView
}
}

extension ProgressView where Label == EmptyView {
Expand Down Expand Up @@ -101,7 +110,10 @@ extension ProgressView where Label == Text {
}

struct ProgressSpinnerView: ElementaryView {
init() {}
let isResizable: Bool
init(isResizable: Bool = false) {
self.isResizable = isResizable
}

func asWidget<Backend: AppBackend>(backend: Backend) -> Backend.Widget {
backend.createProgressSpinner()
Expand All @@ -114,8 +126,33 @@ struct ProgressSpinnerView: ElementaryView {
backend: Backend,
dryRun: Bool
) -> ViewUpdateResult {
ViewUpdateResult.leafView(
size: ViewSize(fixedSize: backend.naturalSize(of: widget))
let naturalSize = backend.naturalSize(of: widget)
guard isResizable else {
// Required to reset its size when resizability
// gets changed at runtime
backend.setSize(of: widget, to: naturalSize)
return ViewUpdateResult.leafView(size: ViewSize(fixedSize: naturalSize))
}
let min = max(min(proposedSize.x, proposedSize.y), 10)
let size = SIMD2(
min,
min
)
if !dryRun {
// Doesn't change the rendered size of ProgressSpinner
// on UIKitBackend, but still sets container size to
// (width: n, height: n) n = min(proposedSize.x, proposedSize.y)
backend.setSize(of: widget, to: size)
}
return ViewUpdateResult.leafView(
size: ViewSize(
size: size,
idealSize: naturalSize,
minimumWidth: 10,
minimumHeight: 10,
maximumWidth: nil,
maximumHeight: nil
)
)
}
}
Expand Down
Loading