【问题标题】:SwiftUI gestures in the toolbar area ignored工具栏区域中的 SwiftUI 手势被忽略
【发布时间】:2022-06-18 00:08:01
【问题描述】:

我想实现一个自定义滑块 SwiftUI 组件并将其放在 SwiftUI Mac 应用程序的工具栏区域。然而,控件的手势被忽略,因为系统的窗口移动手势具有优先权。系统 UI 控件不会出现此问题,例如 SliderButton

如何修复下面的代码,使滑块也可以在工具栏区域中工作,而不仅仅是在类似于默认 SwiftUI 组件的窗口内?

struct MySlider: View {
    @State var offset: CGFloat = 0.0
    var body: some View {
        GeometryReader { gr in
            let thumbSize = gr.size.height
            let maxValue = (gr.size.width - thumbSize) / 2.0
            let gesture = DragGesture(minimumDistance: 0).onChanged { v in
                self.offset = max(min(v.translation.width, maxValue), -maxValue)
            }
            ZStack {
                Capsule()
                Circle()
                    .foregroundColor(Color.yellow)
                    .frame(width: thumbSize, height: thumbSize)
                    .offset(x: offset)
                    .highPriorityGesture(gesture)
            }
        }.frame(width: 100, height: 20)
    }
}
struct ContentView: View {
    @State var value = 0.5
    var body: some View {
        MySlider()
        .toolbar {
            MySlider()
            Slider(value: $value).frame(width: 100, height: 20)
        }.frame(width: 500, height: 100)
    }
}

【问题讨论】:

    标签: swift macos swiftui


    【解决方案1】:

    看起来像设计限制(或尚未实现的功能 - Apple 不认为这种视图是支持用户交互的项目)。

    一种可能的解决方法是将您的活动元素包装成按钮样式。作为容器的按钮被解释为用户可交互区域,但所有绘图和处理都在您的代码中。

    使用 Xcode 13.2 / macOS 12.2 测试

    注意:滑块逻辑没有变化

    struct MySlider: View {
    
        var body: some View {
            Button("") {}.buttonStyle(SliderButtonStyle())
        }
    
        struct SliderButtonStyle: ButtonStyle {
            func makeBody(configuration: Configuration) -> some View {
                MySliderContent()
            }
    
            struct MySliderContent: View {
                @State var offset: CGFloat = 0.0
                var body: some View {
                    GeometryReader { gr in
                        let thumbSize = gr.size.height
                        let maxValue = (gr.size.width - thumbSize) / 2.0
                        let gesture = DragGesture(minimumDistance: 0).onChanged { v in
                            self.offset = max(min(v.translation.width, maxValue), -maxValue)
                        }
                        ZStack {
                            Capsule()
                            Circle()
                                .foregroundColor(Color.yellow)
                                .frame(width: thumbSize, height: thumbSize)
                                .offset(x: offset)
                                .highPriorityGesture(gesture)
                        }
                    }.frame(width: 100, height: 20)
                }
            }
        }
    }
    

    backup

    【讨论】:

    • 添加.contentShape(Circle()).gesture(TapGesture().onEnded{})的目的是什么?它们似乎是多余的。
    • 是的,从测试结果中留下的 - 只需删除它们
    猜你喜欢
    • 2020-07-19
    • 1970-01-01
    • 2022-08-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-06-23
    • 2021-01-26
    • 1970-01-01
    相关资源
    最近更新 更多