[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
master ad2567f: Fix child frame restacking on NS (bug#41422)
From: |
Alan Third |
Subject: |
master ad2567f: Fix child frame restacking on NS (bug#41422) |
Date: |
Sun, 3 Jan 2021 11:26:46 -0500 (EST) |
branch: master
commit ad2567fb1efced752352096f345c69f88e1ff405
Author: Alan Third <alan@idiocy.org>
Commit: Alan Third <alan@idiocy.org>
Fix child frame restacking on NS (bug#41422)
* src/nsfns.m (Fns_frame_restack): Use new restackWindow method.
* src/nsterm.m ([EmacsWindow orderFront:]):
([EmacsWindow makeKeyAndOrderFront:]):
(nswindow_orderedIndex_sort):
([EmacsWindow orderBack:]):
([EmacsWindow restackWindow:above:]): Override superclass methods to
handle child windows the way we want.
---
src/nsfns.m | 14 ++++----
src/nsterm.h | 1 +
src/nsterm.m | 106 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 114 insertions(+), 7 deletions(-)
diff --git a/src/nsfns.m b/src/nsfns.m
index ee2daea..ae114f8 100644
--- a/src/nsfns.m
+++ b/src/nsfns.m
@@ -1485,14 +1485,14 @@ Some window managers may refuse to restack windows. */)
if (FRAME_NS_VIEW (f1) && FRAME_NS_VIEW (f2))
{
- NSWindow *window = [FRAME_NS_VIEW (f1) window];
- NSInteger window2 = [[FRAME_NS_VIEW (f2) window] windowNumber];
- NSWindowOrderingMode flag = NILP (above) ? NSWindowBelow : NSWindowAbove;
+ EmacsWindow *window = (EmacsWindow *)[FRAME_NS_VIEW (f1) window];
+ NSWindow *window2 = [FRAME_NS_VIEW (f2) window];
+ BOOL flag = !NILP (above);
- [window orderWindow: flag
- relativeTo: window2];
-
- return Qt;
+ if ([window restackWindow:window2 above:!NILP (above)])
+ return Qt;
+ else
+ return Qnil;
}
else
{
diff --git a/src/nsterm.h b/src/nsterm.h
index 3fb6449..2c9d8e8 100644
--- a/src/nsterm.h
+++ b/src/nsterm.h
@@ -498,6 +498,7 @@ typedef id instancetype;
NSPoint grabOffset;
}
+- (BOOL)restackWindow:(NSWindow *)win above:(BOOL)above;
- (void)setAppearance;
@end
diff --git a/src/nsterm.m b/src/nsterm.m
index 2731063..2defb9e 100644
--- a/src/nsterm.m
+++ b/src/nsterm.m
@@ -8693,6 +8693,112 @@ not_in_argv (NSString *arg)
@implementation EmacsWindow
+/* It seems the only way to reorder child frames is by removing them
+ from the parent and then reattaching them in the correct order. */
+
+- (void)orderFront:(id)sender
+{
+ NSTRACE ("[EmacsWindow orderFront:]");
+
+ NSWindow *parent = [self parentWindow];
+ if (parent)
+ {
+ [parent removeChildWindow:self];
+ [parent addChildWindow:self ordered:NSWindowAbove];
+ }
+ else
+ [super orderFront:sender];
+}
+
+- (void)makeKeyAndOrderFront:(id)sender
+{
+ NSTRACE ("[EmacsWindow makeKeyAndOrderFront:]");
+
+ if ([self parentWindow])
+ {
+ [self orderFront:sender];
+ [self makeKeyWindow];
+ }
+ else
+ [super makeKeyAndOrderFront:sender];
+}
+
+
+/* The array returned by [NSWindow parentWindow] may already be
+ sorted, but the documentation doesn't tell us whether or not it is,
+ so to be safe we'll sort it. */
+NSInteger nswindow_orderedIndex_sort (id w1, id w2, void *c)
+{
+ NSInteger i1 = [w1 orderedIndex];
+ NSInteger i2 = [w2 orderedIndex];
+
+ if (i1 > i2)
+ return NSOrderedAscending;
+ if (i1 < i2)
+ return NSOrderedDescending;
+
+ return NSOrderedSame;
+}
+
+- (void)orderBack:(id)sender
+{
+ NSTRACE ("[EmacsWindow orderBack:]");
+
+ NSWindow *parent = [self parentWindow];
+ if (parent)
+ {
+ NSArray *children = [[parent childWindows]
+ sortedArrayUsingFunction:nswindow_orderedIndex_sort
+ context:nil];
+ [parent removeChildWindow:self];
+ [parent addChildWindow:self ordered:NSWindowAbove];
+
+ for (NSWindow *win in children)
+ {
+ if (win != self)
+ {
+ [parent removeChildWindow:win];
+ [parent addChildWindow:win ordered:NSWindowAbove];
+ }
+ }
+ }
+ else
+ [super orderBack:sender];
+}
+
+- (BOOL)restackWindow:(NSWindow *)win above:(BOOL)above
+{
+ NSTRACE ("[EmacsWindow restackWindow:above:]");
+
+ /* If parent windows don't match we can't restack these frames
+ without changing the parents. */
+ if ([self parentWindow] != [win parentWindow])
+ return NO;
+ else if (![self parentWindow])
+ [self orderWindow:(above ? NSWindowAbove : NSWindowBelow)
+ relativeTo:[win windowNumber]];
+ else
+ {
+ NSInteger index;
+ NSWindow *parent = [self parentWindow];
+ NSMutableArray *children = [[[parent childWindows]
+
sortedArrayUsingFunction:nswindow_orderedIndex_sort
+ context:nil]
+ mutableCopy];
+ [children removeObject:self];
+ index = [children indexOfObject:win];
+ [children insertObject:self atIndex:(above ? index+1 : index)];
+
+ for (NSWindow *w in children)
+ {
+ [parent removeChildWindow:w];
+ [parent addChildWindow:w ordered:NSWindowAbove];
+ }
+ }
+
+ return YES;
+}
+
#ifdef NS_IMPL_COCOA
- (id)accessibilityAttributeValue:(NSString *)attribute
{
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- master ad2567f: Fix child frame restacking on NS (bug#41422),
Alan Third <=