Как создать NSEvent типа NSScrollWheel?

Я хотел бы создать (подделать) NSEvent типа NSScrollWheel. Существуют методы конструктора NSEvent для нескольких других типов событий NSEvent (mouseEvent, keyEvent, enterExitEvent, otherEvent), но ни один из них не позволяет мне установить, например, deltaX.


person smokris    schedule 25.05.2011    source источник


Ответы (4)


NSEvent не предоставляет способа сделать это, но вы можете создать CGEvent и создать вокруг него оболочку NSEvent. Событие будет автоматически использовать текущее местоположение курсора. См. CGEventCreateScrollWheelEvent. Однако публикация этого события с помощью postEvent:atStart: NSApplication не работает (вероятно, потому, что для него не определено окно). Вы можете отправить CGEvent непосредственно в поток событий или отправить NSEvent непосредственно в метод scrollWheel: представления.

CGWheelCount wheelCount = 2; // 1 for Y-only, 2 for Y-X, 3 for Y-X-Z
int32_t xScroll = −1; // Negative for right
int32_t yScroll = −2; // Negative for down
CGEventRef cgEvent = CGEventCreateScrollWheelEvent(NULL, kCGScrollEventUnitLine, wheelCount, yScroll, xScroll);

// You can post the CGEvent to the event stream to have it automatically sent to the window under the cursor
CGEventPost(kCGHIDEventTap, cgEvent);

NSEvent *theEvent = [NSEvent eventWithCGEvent:cgEvent];
CFRelease(cgEvent);

// Or you can send the NSEvent directly to a view
[theView scrollWheel:theEvent];
person ughoavgfhw    schedule 25.05.2011

Вы можете создать CGEventRef, используя CGEventCreateScrollWheelEvent и преобразовать его в NSEvent с помощью eventWithCGEvent:. Чтобы добавить информацию в CGEvent, используйте CGEventSetIntegerValueField -- среди возможных поля: kCGScrollWheelEventDeltaAxis1, ...2 и ...3.

person jscs    schedule 25.05.2011

Попробуйте следующий код:

  int scrollingDeltaX =... //custom value

//if you have some NSEvent *theEvent 
  CGEventRef cgEvent = CGEventCreateCopy(theEvent.CGEvent);

  CGEventSetIntegerValueField(cgEvent, kCGScrollWheelEventDeltaAxis2, scrollingDeltaX);

  NSEvent *newEvent = [NSEvent eventWithCGEvent:cgEvent];
  CFRelease(cgEvent);
person Ivan Androsenko    schedule 17.08.2016

Это пришло мне в голову в 2020 году. Я решил опубликовать синтаксис Swift 5 для всех, кто найдет этот ответ. Это переопределение в подклассе NSScrollView поменяет поведение прокрутки вверх/вниз вправо/влево, если клавиша ⌘ нажата:

public override func scrollWheel(with event: NSEvent) {
    guard event.modifierFlags.contains(.command) else {
        super.scrollWheel(with: event)
        return
    }

    if let cgEvent: CGEvent = event.cgEvent?.copy() {
        cgEvent.setDoubleValueField(.scrollWheelEventDeltaAxis1, value: Double(event.scrollingDeltaX))
        cgEvent.setDoubleValueField(.scrollWheelEventDeltaAxis2, value: Double(event.scrollingDeltaY))

        if let nsEvent = NSEvent(cgEvent: cgEvent) {
            super.scrollWheel(with: nsEvent)
        }
    }
}
person Ryan Francesconi    schedule 14.04.2020