Làm cách nào để phát hiện nhấp chuột phải trong SwiftUI?


10

Tôi đang viết một ứng dụng Mines đơn giản để giúp tôi làm quen với SwiftUI. Như vậy, tôi muốn nhấp chuột chính (thường là LMB) để "đào" (tiết lộ xem có mỏ nào ở đó không) và nhấp chuột phụ (thường là RMB) để đặt cờ.

Tôi có công việc đào! Nhưng tôi không thể tìm ra cách đặt cờ, vì tôi không thể tìm ra cách phát hiện nhấp chuột phụ.

Đây là những gì tôi đang cố gắng :

BoardSquareView(
    style: self.style(for: square),
    model: square
)
.gesture(TapGesture().modifiers(.control).onEnded(self.handleUserDidAltTap(square)))
.gesture(TapGesture().onEnded(self.handleUserDidTap(square)))

Như tôi đã ngụ ý trước đó, hàm được trả về handleUserDidTapđược gọi đúng khi nhấp, nhưng hàm được trả về handleUserDidAltTapchỉ được gọi khi tôi giữ phím Control. Điều đó có ý nghĩa bởi vì đó là những gì mã nói ... nhưng tôi không thấy bất kỳ API nào có thể khiến nó đăng ký các nhấp chuột thứ cấp, vì vậy tôi không biết phải làm gì khác.

Tôi cũng đã thử điều này, nhưng hành vi có vẻ giống hệt nhau:

BoardSquareView(
    style: self.style(for: square),
    model: square
)
.gesture(TapGesture().modifiers(.control).onEnded(self.handleUserDidAltTap(square)))
.onTapGesture(self.handleUserDidTap(square))

1
Liên kết đầu tiên của bạn bị hỏng. Repo tư nhân?
Gil Birman

.onTapGesture() kiểm tra nó
Raymond

Rất tiếc, bạn đã đúng @GilBirman! Đã sửa; xin lỗi về điều đó
Ben Leggiero 11/12/19

@Raymond Mình đã thử trước. Trừ khi tôi thiếu một cái gì đó lớn, nó dường như cư xử giống hệt.gesture(TapGesture().onEnded(.......))
Ben Leggiero

Câu trả lời:


4

Vì mọi thứ đang diễn ra với SwiftUI ngay bây giờ, điều này không thể trực tiếp. Tôi chắc chắn rằng nó sẽ có trong tương lai, nhưng hiện tại, TapGesturerõ ràng tập trung chủ yếu vào các trường hợp sử dụng iOS không có khái niệm "nhấp chuột phải" vì vậy tôi nghĩ đó là lý do tại sao điều này bị bỏ qua. Lưu ý khái niệm "báo chí dài" là một công dân hạng nhất ở dạng LongPressGesturevà hầu như chỉ được sử dụng trong bối cảnh iOS, hỗ trợ lý thuyết này.

Điều đó nói rằng, tôi đã tìm ra một cách để làm cho công việc này. Những gì bạn phải làm là quay trở lại với công nghệ cũ hơn và nhúng nó vào chế độ xem SwiftUI của bạn.

struct RightClickableSwiftUIView: NSViewRepresentable {
    func updateNSView(_ nsView: RightClickableView, context: NSViewRepresentableContext<RightClickableSwiftUIView>) {
        print("Update")
    }

    func makeNSView(context: Context) -> RightClickableView {
        RightClickableView()
    }

}

class RightClickableView : NSView {
    override func mouseDown(with theEvent: NSEvent) {
        print("left mouse")
    }

    override func rightMouseDown(with theEvent: NSEvent) {
        print("right mouse")
    }
}

Tôi đã thử nghiệm điều này và nó hoạt động với tôi trong một ứng dụng SwiftUI khá phức tạp. Cách tiếp cận cơ bản ở đây là:

  1. Tạo thành phần nghe của bạn như một NSView.
  2. Bao bọc nó với một khung nhìn SwiftUI thực hiện NSViewRepresentable.
  3. Đưa triển khai của bạn vào UI nơi bạn muốn, giống như bạn sẽ làm với bất kỳ chế độ xem SwiftUI nào khác.

Không phải là một giải pháp lý tưởng, nhưng nó có thể đủ tốt cho ngay bây giờ. Tôi hy vọng điều này sẽ giải quyết vấn đề của bạn cho đến khi Apple mở rộng khả năng của SwiftUI hơn nữa.


Cảm ơn bạn. Đây là những gì tôi đã làm bây giờ . Thực sự buồn vì đây là ấn tượng đầu tiên của họ với khuôn khổ. Tôi sẽ đánh dấu điều này là được chấp nhận cho đến khi (hy vọng) một giải pháp tốt hơn xuất hiện
Ben Leggiero

1
Welp; Có vẻ như đây là câu trả lời tốt nhất hiện nay. Tiền thưởng là của bạn! Hy vọng một ngày nào đó chúng ta sẽ có một giải pháp chính thức.
Ben Leggiero
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.