Example #1
0
 void drawRectangles(NSWindow window, Rectangle[] rects, boolean erase) {
   NSRect frame = window.frame();
   NSGraphicsContext context = window.graphicsContext();
   NSGraphicsContext.setCurrentContext(context);
   NSAffineTransform transform = NSAffineTransform.transform();
   context.saveGraphicsState();
   transform.scaleXBy(1, -1);
   transform.translateXBy(0, -frame.height);
   transform.concat();
   Point parentOrigin;
   if (parent != null) {
     parentOrigin = display.map(parent, null, 0, 0);
   } else {
     parentOrigin = new Point(0, 0);
   }
   context.setCompositingOperation(erase ? OS.NSCompositeClear : OS.NSCompositeSourceOver);
   for (int i = 0; i < rects.length; i++) {
     Rectangle rect = rects[i];
     frame.x = rect.x + parentOrigin.x;
     frame.y = rect.y + parentOrigin.y;
     frame.width = rect.width;
     frame.height = rect.height;
     if (erase) {
       frame.width++;
       frame.height++;
       NSBezierPath.fillRect(frame);
     } else {
       frame.x += 0.5f;
       frame.y += 0.5f;
       NSBezierPath.strokeRect(frame);
     }
   }
   context.flushGraphics();
   context.restoreGraphicsState();
 }
  void drawRectangles(NSWindow window, Rectangle[] rects, boolean erase) {
    NSGraphicsContext context = window.graphicsContext();
    NSGraphicsContext.static_saveGraphicsState();
    NSGraphicsContext.setCurrentContext(context);
    context.saveGraphicsState();
    Point parentOrigin;
    if (parent != null) {
      parentOrigin = display.map(parent, null, 0, 0);
    } else {
      parentOrigin = new Point(0, 0);
    }
    context.setCompositingOperation(erase ? OS.NSCompositeClear : OS.NSCompositeSourceOver);
    NSRect rectFrame = new NSRect();
    NSPoint globalPoint = new NSPoint();
    double /*float*/ screenHeight = display.getPrimaryFrame().height;
    for (int i = 0; i < rects.length; i++) {
      Rectangle rect = rects[i];
      rectFrame.x = rect.x + parentOrigin.x;
      rectFrame.y = screenHeight - (int) ((rect.y + parentOrigin.y) + rect.height);
      rectFrame.width = rect.width;
      rectFrame.height = rect.height;
      globalPoint.x = rectFrame.x;
      globalPoint.y = rectFrame.y;
      globalPoint = window.convertScreenToBase(globalPoint);
      rectFrame.x = globalPoint.x;
      rectFrame.y = globalPoint.y;

      if (erase) {
        rectFrame.width++;
        rectFrame.height++;
        NSBezierPath.fillRect(rectFrame);
      } else {
        rectFrame.x += 0.5f;
        rectFrame.y += 0.5f;
        NSBezierPath.strokeRect(rectFrame);
      }
    }
    if (!erase) context.flushGraphics();
    context.restoreGraphicsState();
    NSGraphicsContext.static_restoreGraphicsState();
  }
  /**
   * Displays the Tracker rectangles for manipulation by the user. Returns when the user has either
   * finished manipulating the rectangles or has cancelled the Tracker.
   *
   * @return <code>true</code> if the user did not cancel the Tracker, <code>false</code> otherwise
   * @exception SWTException
   *     <ul>
   *       <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed
   *       <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver
   *     </ul>
   */
  public boolean open() {
    checkWidget();
    Display display = this.display;
    cancelled = false;
    tracking = true;
    window = (NSWindow) new NSWindow().alloc();
    NSArray screens = NSScreen.screens();
    double /*float*/ minX = Float.MAX_VALUE, maxX = Float.MIN_VALUE;
    double /*float*/ minY = Float.MAX_VALUE, maxY = Float.MIN_VALUE;
    int count = (int) /*64*/ screens.count();
    for (int i = 0; i < count; i++) {
      NSScreen screen = new NSScreen(screens.objectAtIndex(i));
      NSRect frame = screen.frame();
      double /*float*/ x1 = frame.x, x2 = frame.x + frame.width;
      double /*float*/ y1 = frame.y, y2 = frame.y + frame.height;
      if (x1 < minX) minX = x1;
      if (x2 < minX) minX = x2;
      if (x1 > maxX) maxX = x1;
      if (x2 > maxX) maxX = x2;
      if (y1 < minY) minY = y1;
      if (y2 < minY) minY = y2;
      if (y1 > maxY) maxY = y1;
      if (y2 > maxY) maxY = y2;
    }
    NSRect frame = new NSRect();
    frame.x = minX;
    frame.y = minY;
    frame.width = maxX - minX;
    frame.height = maxY - minY;
    window =
        window.initWithContentRect(
            frame, OS.NSBorderlessWindowMask, OS.NSBackingStoreBuffered, false);
    window.setOpaque(false);
    window.setLevel(OS.NSStatusWindowLevel);
    window.setContentView(null);
    window.setBackgroundColor(NSColor.clearColor());
    NSGraphicsContext context = window.graphicsContext();
    NSGraphicsContext.static_saveGraphicsState();
    NSGraphicsContext.setCurrentContext(context);
    context.setCompositingOperation(OS.NSCompositeClear);
    frame.x = frame.y = 0;
    NSBezierPath.fillRect(frame);
    NSGraphicsContext.static_restoreGraphicsState();
    window.orderFrontRegardless();

    drawRectangles(window, rectangles, false);

    /*
     * If exactly one of UP/DOWN is specified as a style then set the cursor
     * orientation accordingly (the same is done for LEFT/RIGHT styles below).
     */
    int vStyle = style & (SWT.UP | SWT.DOWN);
    if (vStyle == SWT.UP || vStyle == SWT.DOWN) {
      cursorOrientation |= vStyle;
    }
    int hStyle = style & (SWT.LEFT | SWT.RIGHT);
    if (hStyle == SWT.LEFT || hStyle == SWT.RIGHT) {
      cursorOrientation |= hStyle;
    }

    Point cursorPos;
    boolean down = false;
    NSApplication application = NSApplication.sharedApplication();
    NSEvent currentEvent = application.currentEvent();
    if (currentEvent != null) {
      switch ((int) /*64*/ currentEvent.type()) {
        case OS.NSLeftMouseDown:
        case OS.NSLeftMouseDragged:
        case OS.NSRightMouseDown:
        case OS.NSRightMouseDragged:
        case OS.NSOtherMouseDown:
        case OS.NSOtherMouseDragged:
          down = true;
      }
    }
    if (down) {
      cursorPos = display.getCursorLocation();
    } else {
      if ((style & SWT.RESIZE) != 0) {
        cursorPos = adjustResizeCursor(true);
      } else {
        cursorPos = adjustMoveCursor();
      }
    }
    if (cursorPos != null) {
      oldX = cursorPos.x;
      oldY = cursorPos.y;
    }

    Control oldTrackingControl = display.trackingControl;
    display.trackingControl = null;
    /* Tracker behaves like a Dialog with its own OS event loop. */
    while (tracking && !cancelled) {
      display.addPool();
      try {
        if (parent != null && parent.isDisposed()) break;
        display.runSkin();
        display.runDeferredLayouts();
        NSEvent event =
            application.nextEventMatchingMask(
                0, NSDate.distantFuture(), OS.NSDefaultRunLoopMode, true);
        if (event == null) continue;
        int type = (int) /*64*/ event.type();
        switch (type) {
          case OS.NSLeftMouseUp:
          case OS.NSRightMouseUp:
          case OS.NSOtherMouseUp:
          case OS.NSMouseMoved:
          case OS.NSLeftMouseDragged:
          case OS.NSRightMouseDragged:
          case OS.NSOtherMouseDragged:
            mouse(event);
            break;
          case OS.NSKeyDown:
          case OS.NSKeyUp:
          case OS.NSFlagsChanged:
            key(event);
            break;
        }
        boolean dispatch = true;
        switch (type) {
          case OS.NSLeftMouseDown:
          case OS.NSLeftMouseUp:
          case OS.NSRightMouseDown:
          case OS.NSRightMouseUp:
          case OS.NSOtherMouseDown:
          case OS.NSOtherMouseUp:
          case OS.NSMouseMoved:
          case OS.NSLeftMouseDragged:
          case OS.NSRightMouseDragged:
          case OS.NSOtherMouseDragged:
          case OS.NSMouseEntered:
          case OS.NSMouseExited:
          case OS.NSKeyDown:
          case OS.NSKeyUp:
          case OS.NSFlagsChanged:
            dispatch = false;
        }
        if (dispatch) application.sendEvent(event);
        if (clientCursor != null && resizeCursor == null) {
          display.lockCursor = false;
          clientCursor.handle.set();
          display.lockCursor = true;
        }
        display.runAsyncMessages(false);
      } finally {
        display.removePool();
      }
    }

    /*
     * Cleanup: If this tracker was resizing then the last cursor that it created
     * needs to be destroyed.
     */
    if (resizeCursor != null) resizeCursor.dispose();
    resizeCursor = null;

    if (oldTrackingControl != null && !oldTrackingControl.isDisposed()) {
      display.trackingControl = oldTrackingControl;
    }
    display.setCursor(display.findControl(true));
    if (!isDisposed()) {
      drawRectangles(window, rectangles, true);
    }
    if (window != null) window.close();
    tracking = false;
    window = null;
    return !cancelled;
  }
  /**
   * Modify the given workbench window shell bits to show the tool bar toggle button.
   *
   * @param window the window to modify
   * @since 3.2
   */
  @SuppressWarnings("restriction")
  protected void modifyWindowShell(MWindow window) {
    if (window.getWidget() == null) {
      return;
    }
    if (window.getMainMenu() == null) {
      return;
    }
    redirectHandledMenuItems(window.getMainMenu());

    // the toolbar button is not available since MacOS X 10.7
    if (OS.VERSION >= 0x1070) {
      return;
    }
    // only add the button when either the cool bar or perspective bar
    // is initially visible. This is so that RCP applications can choose to
    // use this fragment without fear that their explicitly invisible bars
    // can't be shown.
    boolean trimInitiallyVisible = false;
    if (window instanceof MTrimmedWindow && !((MTrimmedWindow) window).getTrimBars().isEmpty()) {
      for (MTrimBar tb : ((MTrimmedWindow) window).getTrimBars()) {
        if (tb.isVisible()) {
          trimInitiallyVisible = true;
        }
      }
    }

    // It would also be worth checking if there's a command defined
    // for COMMAND_ID_TOGGLE_COOLBAR
    if (trimInitiallyVisible) {
      Shell shell = ((Control) window.getWidget()).getShell();
      NSWindow nsWindow = shell.view.window();
      // Add an empty, hidden tool bar to the window. Without this the
      // tool bar button at the top right of the window will not
      // appear even when setShowsToolbarButton(true) is called.
      // Unfortunately cannot just call shell.getToolBar() as it
      // allocates a properly-sized toolbar
      NSToolbar dummyBar = new NSToolbar();
      dummyBar.alloc();
      dummyBar.initWithIdentifier(NSString.stringWith("SWTToolbar")); // $NON-NLS-1$
      dummyBar.setVisible(false);
      nsWindow.setToolbar(dummyBar);
      dummyBar.release();
      nsWindow.setShowsToolbarButton(true);

      // Override the target and action of the toolbar button so we can
      // control it.
      try {
        Object fieldValue = wrapPointer(NSWindowToolbarButton);
        NSButton toolbarButton =
            (NSButton)
                invokeMethod(
                    NSWindow.class,
                    nsWindow,
                    "standardWindowButton",
                    new Object[] {fieldValue}); // $NON-NLS-1$
        if (toolbarButton != null) {
          toolbarButton.setTarget(delegate);
          invokeMethod(
              NSControl.class,
              toolbarButton,
              "setAction", //$NON-NLS-1$
              new Object[] {wrapPointer(sel_toolbarButtonClicked_)});
        }
      } catch (Exception e) {
        // theoretically, one of
        // SecurityException,Illegal*Exception,InvocationTargetException,NoSuch*Exception
        // not expected to happen at all.
        log(e);
      }
    }
  }
Example #5
0
  /**
   * Displays the Tracker rectangles for manipulation by the user. Returns when the user has either
   * finished manipulating the rectangles or has cancelled the Tracker.
   *
   * @return <code>true</code> if the user did not cancel the Tracker, <code>false</code> otherwise
   * @exception SWTException
   *     <ul>
   *       <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed
   *       <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver
   *     </ul>
   */
  public boolean open() {
    checkWidget();
    cancelled = false;
    tracking = true;
    window = (NSWindow) new NSWindow().alloc();
    NSRect frame = NSScreen.mainScreen().frame();
    window =
        window.initWithContentRect_styleMask_backing_defer_(
            frame, OS.NSBorderlessWindowMask, OS.NSBackingStoreBuffered, false);
    window.setOpaque(false);
    window.setContentView(null);
    NSGraphicsContext context = window.graphicsContext();
    NSGraphicsContext.setCurrentContext(context);
    context.setCompositingOperation(OS.NSCompositeClear);
    NSBezierPath.fillRect(frame);
    window.orderFrontRegardless();

    drawRectangles(window, rectangles, false);

    /*
     * If exactly one of UP/DOWN is specified as a style then set the cursor
     * orientation accordingly (the same is done for LEFT/RIGHT styles below).
     */
    int vStyle = style & (SWT.UP | SWT.DOWN);
    if (vStyle == SWT.UP || vStyle == SWT.DOWN) {
      cursorOrientation |= vStyle;
    }
    int hStyle = style & (SWT.LEFT | SWT.RIGHT);
    if (hStyle == SWT.LEFT || hStyle == SWT.RIGHT) {
      cursorOrientation |= hStyle;
    }

    Point cursorPos;
    boolean down = false;
    NSApplication application = NSApplication.sharedApplication();
    NSEvent currentEvent = application.currentEvent();
    switch (currentEvent.type()) {
      case OS.NSLeftMouseDown:
      case OS.NSRightMouseDown:
      case OS.NSOtherMouseDown:
        down = true;
    }
    if (down) {
      cursorPos = display.getCursorLocation();
    } else {
      if ((style & SWT.RESIZE) != 0) {
        cursorPos = adjustResizeCursor(true);
      } else {
        cursorPos = adjustMoveCursor();
      }
    }
    if (cursorPos != null) {
      oldX = cursorPos.x;
      oldY = cursorPos.y;
    }

    /* Tracker behaves like a Dialog with its own OS event loop. */
    while (tracking && !cancelled) {
      NSAutoreleasePool pool = (NSAutoreleasePool) new NSAutoreleasePool().alloc().init();
      NSEvent event =
          application.nextEventMatchingMask(
              0, NSDate.distantFuture(), OS.NSDefaultRunLoopMode, true);
      if (event == null) continue;
      int type = event.type();
      switch (type) {
        case OS.NSLeftMouseUp:
        case OS.NSRightMouseUp:
        case OS.NSOtherMouseUp:
        case OS.NSMouseMoved:
        case OS.NSLeftMouseDragged:
        case OS.NSRightMouseDragged:
        case OS.NSOtherMouseDragged:
          mouse(event);
          break;
        case OS.NSKeyDown:
          //			case OS.NSKeyUp:
        case OS.NSFlagsChanged:
          key(event);
          break;
      }
      /*
       * Don't dispatch mouse and key events in general, EXCEPT once this
       * tracker has finished its work.
       */
      boolean dispatch = true;
      if (!(tracking && !cancelled)) {
        switch (type) {
          case OS.NSLeftMouseDown:
          case OS.NSLeftMouseUp:
          case OS.NSRightMouseDown:
          case OS.NSRightMouseUp:
          case OS.NSOtherMouseDown:
          case OS.NSOtherMouseUp:
          case OS.NSMouseMoved:
          case OS.NSLeftMouseDragged:
          case OS.NSRightMouseDragged:
          case OS.NSOtherMouseDragged:
          case OS.NSMouseEntered:
          case OS.NSMouseExited:
          case OS.NSKeyDown:
          case OS.NSKeyUp:
          case OS.NSFlagsChanged:
            dispatch = false;
        }
      }
      if (dispatch) application.sendEvent(event);
      if (clientCursor != null && resizeCursor == null) {
        clientCursor.handle.set();
      }
      pool.release();
    }
    if (!isDisposed()) {
      drawRectangles(window, rectangles, true);
    }
    if (window != null) window.close();
    tracking = false;
    window = null;
    return !cancelled;
  }
Example #6
0
 void mouse(NSEvent nsEvent) {
   NSPoint location = nsEvent.locationInWindow();
   if (parent != null) {
     location = parent.view.convertPoint_toView_(location, parent.view);
   } else {
     NSWindow eventWindow = nsEvent.window();
     location = eventWindow.convertBaseToScreen(location);
     location.y = eventWindow.screen().frame().height - location.y;
   }
   int newX = (int) location.x, newY = (int) location.y;
   if (newX != oldX || newY != oldY) {
     Rectangle[] oldRectangles = rectangles;
     Rectangle[] rectsToErase = new Rectangle[rectangles.length];
     for (int i = 0; i < rectangles.length; i++) {
       Rectangle current = rectangles[i];
       rectsToErase[i] = new Rectangle(current.x, current.y, current.width, current.height);
     }
     Event event = new Event();
     event.x = newX;
     event.y = newY;
     if ((style & SWT.RESIZE) != 0) {
       boolean orientationInit = resizeRectangles(newX - oldX, newY - oldY);
       inEvent = true;
       sendEvent(SWT.Resize, event);
       inEvent = false;
       /*
        * It is possible (but unlikely), that application
        * code could have disposed the widget in the move
        * event.  If this happens, return false to indicate
        * that the tracking has failed.
        */
       if (isDisposed()) {
         cancelled = true;
         return;
       }
       boolean draw = false;
       /*
        * It is possible that application code could have
        * changed the rectangles in the resize event.  If this
        * happens then only redraw the tracker if the rectangle
        * values have changed.
        */
       if (rectangles != oldRectangles) {
         int length = rectangles.length;
         if (length != rectsToErase.length) {
           draw = true;
         } else {
           for (int i = 0; i < length; i++) {
             if (!rectangles[i].equals(rectsToErase[i])) {
               draw = true;
               break;
             }
           }
         }
       } else {
         draw = true;
       }
       if (draw) {
         drawRectangles(window, rectsToErase, true);
         drawRectangles(window, rectangles, false);
       }
       Point cursorPos = adjustResizeCursor(orientationInit);
       if (cursorPos != null) {
         newX = cursorPos.x;
         newY = cursorPos.y;
       }
     } else {
       moveRectangles(newX - oldX, newY - oldY);
       inEvent = true;
       sendEvent(SWT.Move, event);
       inEvent = false;
       /*
        * It is possible (but unlikely), that application
        * code could have disposed the widget in the move
        * event.  If this happens, return false to indicate
        * that the tracking has failed.
        */
       if (isDisposed()) {
         cancelled = true;
         return;
       }
       boolean draw = false;
       /*
        * It is possible that application code could have
        * changed the rectangles in the move event.  If this
        * happens then only redraw the tracker if the rectangle
        * values have changed.
        */
       if (rectangles != oldRectangles) {
         int length = rectangles.length;
         if (length != rectsToErase.length) {
           draw = true;
         } else {
           for (int i = 0; i < length; i++) {
             if (!rectangles[i].equals(rectsToErase[i])) {
               draw = true;
               break;
             }
           }
         }
       } else {
         draw = true;
       }
       if (draw) {
         drawRectangles(window, rectsToErase, true);
         drawRectangles(window, rectangles, false);
       }
     }
     oldX = newX;
     oldY = newY;
   }
   switch (nsEvent.type()) {
     case OS.NSLeftMouseUp:
     case OS.NSRightMouseUp:
     case OS.NSOtherMouseUp:
       tracking = false;
   }
 }