зеркало из https://github.com/mozilla/gecko-dev.git
Bug 944836 - Implement nsChildView::UpdateWindowDraggingRegion. r=roc, r=smichaud
This commit is contained in:
Родитель
9035319790
Коммит
5b1c77960e
|
@ -68,6 +68,10 @@ public:
|
||||||
{
|
{
|
||||||
return IsEqual(aRgn);
|
return IsEqual(aRgn);
|
||||||
}
|
}
|
||||||
|
bool operator!=(const nsRegion& aRgn) const
|
||||||
|
{
|
||||||
|
return !(*this == aRgn);
|
||||||
|
}
|
||||||
|
|
||||||
friend std::ostream& operator<<(std::ostream& stream, const nsRegion& m);
|
friend std::ostream& operator<<(std::ostream& stream, const nsRegion& m);
|
||||||
|
|
||||||
|
@ -464,6 +468,10 @@ public:
|
||||||
{
|
{
|
||||||
return IsEqual(aRgn);
|
return IsEqual(aRgn);
|
||||||
}
|
}
|
||||||
|
bool operator!=(const nsIntRegion& aRgn) const
|
||||||
|
{
|
||||||
|
return !(*this == aRgn);
|
||||||
|
}
|
||||||
|
|
||||||
friend std::ostream& operator<<(std::ostream& stream, const nsIntRegion& m) {
|
friend std::ostream& operator<<(std::ostream& stream, const nsIntRegion& m) {
|
||||||
return stream << m.mImpl;
|
return stream << m.mImpl;
|
||||||
|
|
|
@ -310,8 +310,6 @@ typedef NSInteger NSEventGestureAxis;
|
||||||
|
|
||||||
- (void)handleMouseMoved:(NSEvent*)aEvent;
|
- (void)handleMouseMoved:(NSEvent*)aEvent;
|
||||||
|
|
||||||
- (void)updateWindowDraggableStateOnMouseMove:(NSEvent*)theEvent;
|
|
||||||
|
|
||||||
- (void)sendMouseEnterOrExitEvent:(NSEvent*)aEvent
|
- (void)sendMouseEnterOrExitEvent:(NSEvent*)aEvent
|
||||||
enter:(BOOL)aEnter
|
enter:(BOOL)aEnter
|
||||||
type:(mozilla::WidgetMouseEvent::exitType)aType;
|
type:(mozilla::WidgetMouseEvent::exitType)aType;
|
||||||
|
@ -548,6 +546,9 @@ public:
|
||||||
|
|
||||||
virtual void UpdateThemeGeometries(const nsTArray<ThemeGeometry>& aThemeGeometries);
|
virtual void UpdateThemeGeometries(const nsTArray<ThemeGeometry>& aThemeGeometries);
|
||||||
|
|
||||||
|
virtual void UpdateWindowDraggingRegion(const nsIntRegion& aRegion) MOZ_OVERRIDE;
|
||||||
|
const nsIntRegion& GetDraggableRegion() { return mDraggableRegion; }
|
||||||
|
|
||||||
void HidePlugin();
|
void HidePlugin();
|
||||||
void UpdatePluginPort();
|
void UpdatePluginPort();
|
||||||
|
|
||||||
|
@ -679,6 +680,8 @@ protected:
|
||||||
// uploaded to to mTitlebarImage. Main thread only.
|
// uploaded to to mTitlebarImage. Main thread only.
|
||||||
nsIntRegion mDirtyTitlebarRegion;
|
nsIntRegion mDirtyTitlebarRegion;
|
||||||
|
|
||||||
|
nsIntRegion mDraggableRegion;
|
||||||
|
|
||||||
// Cached value of [mView backingScaleFactor], to avoid sending two obj-c
|
// Cached value of [mView backingScaleFactor], to avoid sending two obj-c
|
||||||
// messages (respondsToSelector, backingScaleFactor) every time we need to
|
// messages (respondsToSelector, backingScaleFactor) every time we need to
|
||||||
// use it.
|
// use it.
|
||||||
|
|
|
@ -121,6 +121,7 @@ extern "C" {
|
||||||
|
|
||||||
typedef CFTypeRef CGSRegionObj;
|
typedef CFTypeRef CGSRegionObj;
|
||||||
CGError CGSNewRegionWithRect(const CGRect *rect, CGSRegionObj *outRegion);
|
CGError CGSNewRegionWithRect(const CGRect *rect, CGSRegionObj *outRegion);
|
||||||
|
CGError CGSNewRegionWithRectList(const CGRect *rects, int rectCount, CGSRegionObj *outRegion);
|
||||||
}
|
}
|
||||||
|
|
||||||
// defined in nsMenuBarX.mm
|
// defined in nsMenuBarX.mm
|
||||||
|
@ -203,6 +204,7 @@ static uint32_t gNumberOfWidgetsNeedingEventThread = 0;
|
||||||
- (APZCTreeManager*)apzctm;
|
- (APZCTreeManager*)apzctm;
|
||||||
|
|
||||||
- (BOOL)inactiveWindowAcceptsMouseEvent:(NSEvent*)aEvent;
|
- (BOOL)inactiveWindowAcceptsMouseEvent:(NSEvent*)aEvent;
|
||||||
|
- (void)updateWindowDraggableState;
|
||||||
|
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
@ -221,6 +223,10 @@ static uint32_t gNumberOfWidgetsNeedingEventThread = 0;
|
||||||
- (float)roundedCornerRadius;
|
- (float)roundedCornerRadius;
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
@interface NSView(DraggableRegion)
|
||||||
|
- (CGSRegionObj)_regionForOpaqueDescendants:(NSRect)aRect forMove:(BOOL)aForMove;
|
||||||
|
@end
|
||||||
|
|
||||||
// Starting with 10.7 the bottom corners of all windows are rounded.
|
// Starting with 10.7 the bottom corners of all windows are rounded.
|
||||||
// Unfortunately, the standard rounding that OS X applies to OpenGL views
|
// Unfortunately, the standard rounding that OS X applies to OpenGL views
|
||||||
// does not use anti-aliasing and looks very crude. Since we want a smooth,
|
// does not use anti-aliasing and looks very crude. Since we want a smooth,
|
||||||
|
@ -2387,15 +2393,15 @@ nsChildView::UpdateTitlebarCGContext()
|
||||||
|
|
||||||
CGContextSaveGState(ctx);
|
CGContextSaveGState(ctx);
|
||||||
|
|
||||||
std::vector<CGRect> rects;
|
nsTArray<CGRect> rects;
|
||||||
nsIntRegionRectIterator iter(dirtyTitlebarRegion);
|
nsIntRegionRectIterator iter(dirtyTitlebarRegion);
|
||||||
for (;;) {
|
for (;;) {
|
||||||
const nsIntRect* r = iter.Next();
|
const nsIntRect* r = iter.Next();
|
||||||
if (!r)
|
if (!r)
|
||||||
break;
|
break;
|
||||||
rects.push_back(CGRectMake(r->x, r->y, r->width, r->height));
|
rects.AppendElement(CGRectMake(r->x, r->y, r->width, r->height));
|
||||||
}
|
}
|
||||||
CGContextClipToRects(ctx, rects.data(), rects.size());
|
CGContextClipToRects(ctx, rects.Elements(), rects.Length());
|
||||||
|
|
||||||
CGContextClearRect(ctx, CGRectMake(0, 0, texSize.width, texSize.height));
|
CGContextClearRect(ctx, CGRectMake(0, 0, texSize.width, texSize.height));
|
||||||
|
|
||||||
|
@ -2748,6 +2754,15 @@ nsChildView::DoRemoteComposition(const nsIntRect& aRenderRect)
|
||||||
[(ChildView*)mView postRender:mGLPresenter->GetNSOpenGLContext()];
|
[(ChildView*)mView postRender:mGLPresenter->GetNSOpenGLContext()];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
nsChildView::UpdateWindowDraggingRegion(const nsIntRegion& aRegion)
|
||||||
|
{
|
||||||
|
if (mDraggableRegion != aRegion) {
|
||||||
|
mDraggableRegion = aRegion;
|
||||||
|
[(ChildView*)mView updateWindowDraggableState];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef ACCESSIBILITY
|
#ifdef ACCESSIBILITY
|
||||||
already_AddRefed<a11y::Accessible>
|
already_AddRefed<a11y::Accessible>
|
||||||
nsChildView::GetDocumentAccessible()
|
nsChildView::GetDocumentAccessible()
|
||||||
|
@ -3602,7 +3617,9 @@ NSEvent* gLastDragMouseDownEvent = nil;
|
||||||
|
|
||||||
- (BOOL)mouseDownCanMoveWindow
|
- (BOOL)mouseDownCanMoveWindow
|
||||||
{
|
{
|
||||||
return [[self window] isMovableByWindowBackground];
|
// Return YES so that _regionForOpaqueDescendants gets called, where the
|
||||||
|
// actual draggable region will be assembled.
|
||||||
|
return YES;
|
||||||
}
|
}
|
||||||
|
|
||||||
-(void)updateGLContext
|
-(void)updateGLContext
|
||||||
|
@ -4885,24 +4902,60 @@ NSEvent* gLastDragMouseDownEvent = nil;
|
||||||
mGeckoChild->DispatchEvent(&event, status);
|
mGeckoChild->DispatchEvent(&event, status);
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)updateWindowDraggableStateOnMouseMove:(NSEvent*)theEvent
|
- (void)updateWindowDraggableState
|
||||||
{
|
{
|
||||||
if (!theEvent || !mGeckoChild) {
|
// Trigger update to the window server.
|
||||||
return;
|
[[self window] setMovableByWindowBackground:NO];
|
||||||
|
[[self window] setMovableByWindowBackground:YES];
|
||||||
|
}
|
||||||
|
|
||||||
|
// aRect is in view coordinates relative to this NSView.
|
||||||
|
- (CGRect)convertToFlippedWindowCoordinates:(NSRect)aRect
|
||||||
|
{
|
||||||
|
// First, convert the rect to regular window coordinates...
|
||||||
|
NSRect inWindowCoords = [self convertRect:aRect toView:nil];
|
||||||
|
// ... and then flip it again because window coordinates have their origin
|
||||||
|
// in the bottom left corner, and we need it to be in the top left corner.
|
||||||
|
inWindowCoords.origin.y = [[self window] frame].size.height - NSMaxY(inWindowCoords);
|
||||||
|
return NSRectToCGRect(inWindowCoords);
|
||||||
|
}
|
||||||
|
|
||||||
|
static CGSRegionObj
|
||||||
|
NewCGSRegionFromRegion(const nsIntRegion& aRegion,
|
||||||
|
CGRect (^aRectConverter)(const nsIntRect&))
|
||||||
|
{
|
||||||
|
nsTArray<CGRect> rects;
|
||||||
|
nsIntRegionRectIterator iter(aRegion);
|
||||||
|
for (;;) {
|
||||||
|
const nsIntRect* r = iter.Next();
|
||||||
|
if (!r)
|
||||||
|
break;
|
||||||
|
rects.AppendElement(aRectConverter(*r));
|
||||||
}
|
}
|
||||||
|
|
||||||
nsCocoaWindow* windowWidget = mGeckoChild->GetXULWindowWidget();
|
CGSRegionObj region;
|
||||||
if (!windowWidget) {
|
CGSNewRegionWithRectList(rects.Elements(), rects.Length(), ®ion);
|
||||||
return;
|
return region;
|
||||||
|
}
|
||||||
|
|
||||||
|
// This function is called with forMove:YES to calculate the draggable region
|
||||||
|
// of the window which will be submitted to the window server. Window dragging
|
||||||
|
// is handled on the window server without calling back into our process, so it
|
||||||
|
// also works while our app is unresponsive.
|
||||||
|
- (CGSRegionObj)_regionForOpaqueDescendants:(NSRect)aRect forMove:(BOOL)aForMove
|
||||||
|
{
|
||||||
|
if (!aForMove || !mGeckoChild) {
|
||||||
|
return [super _regionForOpaqueDescendants:aRect forMove:aForMove];
|
||||||
}
|
}
|
||||||
|
|
||||||
// We assume later on that sending a hit test event won't cause widget destruction.
|
nsIntRect boundingRect = mGeckoChild->CocoaPointsToDevPixels(aRect);
|
||||||
WidgetMouseEvent hitTestEvent(true, NS_MOUSE_MOZHITTEST, mGeckoChild,
|
|
||||||
WidgetMouseEvent::eReal);
|
|
||||||
[self convertCocoaMouseEvent:theEvent toGeckoEvent:&hitTestEvent];
|
|
||||||
bool result = mGeckoChild->DispatchWindowEvent(hitTestEvent);
|
|
||||||
|
|
||||||
[windowWidget->GetCocoaWindow() setMovableByWindowBackground:result];
|
nsIntRegion opaqueRegion;
|
||||||
|
opaqueRegion.Sub(boundingRect, mGeckoChild->GetDraggableRegion());
|
||||||
|
|
||||||
|
return NewCGSRegionFromRegion(opaqueRegion, ^(const nsIntRect& r) {
|
||||||
|
return [self convertToFlippedWindowCoordinates:mGeckoChild->DevPixelsToCocoaPoints(r)];
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)handleMouseMoved:(NSEvent*)theEvent
|
- (void)handleMouseMoved:(NSEvent*)theEvent
|
||||||
|
|
|
@ -3269,9 +3269,6 @@ static const NSString* kStateShowsToolbarButton = @"showsToolbarButton";
|
||||||
if (delegate && [delegate isKindOfClass:[WindowDelegate class]]) {
|
if (delegate && [delegate isKindOfClass:[WindowDelegate class]]) {
|
||||||
nsCocoaWindow *widget = [(WindowDelegate *)delegate geckoWidget];
|
nsCocoaWindow *widget = [(WindowDelegate *)delegate geckoWidget];
|
||||||
if (widget) {
|
if (widget) {
|
||||||
if (type == NSMouseMoved) {
|
|
||||||
[[self mainChildView] updateWindowDraggableStateOnMouseMove:anEvent];
|
|
||||||
}
|
|
||||||
if (gGeckoAppModalWindowList && (widget != gGeckoAppModalWindowList->window))
|
if (gGeckoAppModalWindowList && (widget != gGeckoAppModalWindowList->window))
|
||||||
return;
|
return;
|
||||||
if (widget->HasModalDescendents())
|
if (widget->HasModalDescendents())
|
||||||
|
|
Загрузка…
Ссылка в новой задаче