1 /* vi:set ts=8 sts=4 sw=4 ft=objc:
3 * VIM - Vi IMproved by Bram Moolenaar
4 * MacVim GUI port by Bjorn Winckler
6 * Do ":help uganda" in Vim to read copying and usage conditions.
7 * Do ":help credits" in Vim to see a list of people who contributed.
8 * See README.txt for an overview of the Vim source code.
13 * Handles resizing of windows, acts as an mediator between MMVimView and
17 #import "MMWindowController.h"
18 #import <PSMTabBarControl.h>
19 #import "MMTextView.h"
20 #import "MMTextStorage.h"
21 #import "MMVimController.h"
23 #import "MMAppController.h"
24 #import "MMTypesetter.h"
25 #import "MMFullscreenWindow.h"
30 @interface MMWindowController (Private)
31 - (NSSize)contentSize;
32 - (NSRect)contentRectForFrameRect:(NSRect)frame;
33 - (NSRect)frameRectForContentRect:(NSRect)contentRect;
34 - (void)resizeWindowToFit:(id)sender;
35 - (NSRect)fitWindowToFrame:(NSRect)frame;
36 - (void)updateResizeIncrements;
37 - (NSTabViewItem *)addNewTabViewItem;
38 - (IBAction)vimMenuItemAction:(id)sender;
39 - (BOOL)askBackendForStarRegister:(NSPasteboard *)pb;
40 - (void)checkWindowNeedsResizing;
41 - (NSSize)resizeVimViewToFitSize:(NSSize)size;
47 NSString *buildMenuItemDescriptor(NSMenu *menu, NSString *tail)
49 return menu ? buildMenuItemDescriptor([menu supermenu], [[menu title]
50 stringByAppendingString:tail])
54 NSMutableArray *buildMenuAddress(NSMenu *menu)
58 addr = buildMenuAddress([menu supermenu]);
59 [addr addObject:[menu title]];
61 addr = [NSMutableArray array];
68 @interface NSWindow (NSWindowPrivate)
69 // Note: This hack allows us to set content shadowing separately from
70 // the window shadow. This is apparently what webkit and terminal do.
71 - (void)_setContentHasShadow:(BOOL)shadow; // new Tiger private method
73 // This is a private api that makes textured windows not have rounded corners.
74 // We want this on Leopard.
75 - (void)setBottomCornerRounded:(BOOL)rounded;
78 @interface NSWindow (NSLeopardOnly)
79 // Note: These functions are Leopard-only, use -[NSObject respondsToSelector:]
80 // before calling them to make sure everything works on Tiger too.
82 #ifndef CGFLOAT_DEFINED
83 // On Leopard, CGFloat is float on 32bit and double on 64bit. On Tiger,
84 // we can't use this anyways, so it's just here to keep the compiler happy.
85 // However, when we're compiling for Tiger and running on Leopard, we
86 // might need the correct typedef, so this piece is copied from ATSTypes.h
88 typedef double CGFloat;
90 typedef float CGFloat;
93 - (void)setAutorecalculatesContentBorderThickness:(BOOL)b forEdge:(NSRectEdge)e;
94 - (void)setContentBorderThickness:(CGFloat)b forEdge:(NSRectEdge)e;
100 @implementation MMWindowController
102 - (id)initWithVimController:(MMVimController *)controller
104 #ifndef NSAppKitVersionNumber10_4 // needed for non-10.5 sdk
105 # define NSAppKitVersionNumber10_4 824
107 unsigned styleMask = NSTitledWindowMask | NSClosableWindowMask
108 | NSMiniaturizableWindowMask | NSResizableWindowMask
109 | NSUnifiedTitleAndToolbarWindowMask;
111 // Use textured background on Leopard or later (skip the 'if' on Tiger for
112 // polished metal window).
113 if (floor(NSAppKitVersionNumber) > NSAppKitVersionNumber10_4)
114 styleMask |= NSTexturedBackgroundWindowMask;
116 // NOTE: The content rect is only used the very first time MacVim is
117 // started (or rather, when ~/Library/Preferences/org.vim.MacVim.plist does
118 // not exist). The chosen values will put the window somewhere near the
119 // top and in the middle of a 1024x768 screen.
120 NSWindow *win = [[NSWindow alloc]
121 initWithContentRect:NSMakeRect(242,364,480,360)
123 backing:NSBackingStoreBuffered
126 if ((self = [super initWithWindow:win])) {
127 vimController = controller;
129 // Window cascading is handled by MMAppController.
130 [self setShouldCascadeWindows:NO];
132 NSView *contentView = [win contentView];
133 vimView = [[MMVimView alloc] initWithFrame:[contentView frame]
134 vimController:vimController];
135 [contentView addSubview:vimView];
137 // Create the tabline separator (which may be visible when the tabline
138 // is hidden). See showTabBar: for circumstances when the separator
140 NSRect tabSepRect = [contentView frame];
141 tabSepRect.origin.y = NSMaxY(tabSepRect)-1;
142 tabSepRect.size.height = 1;
143 tablineSeparator = [[NSBox alloc] initWithFrame:tabSepRect];
145 [tablineSeparator setBoxType:NSBoxSeparator];
146 [tablineSeparator setHidden:NO];
147 [tablineSeparator setAutoresizingMask:NSViewWidthSizable
150 [contentView setAutoresizesSubviews:YES];
151 [contentView addSubview:tablineSeparator];
153 [win setDelegate:self];
154 [win setInitialFirstResponder:[vimView textView]];
156 if ([win styleMask] & NSTexturedBackgroundWindowMask) {
157 // On Leopard, we want to have a textured window to have nice
158 // looking tabs. But the textured window look implies rounded
159 // corners, which looks really weird -- disable them. This is a
160 // private api, though.
161 if ([win respondsToSelector:@selector(setBottomCornerRounded:)])
162 [win setBottomCornerRounded:NO];
164 // When the tab bar is toggled, it changes color for the fraction
165 // of a second, probably because vim sends us events in a strange
166 // order, confusing appkit's content border heuristic for a short
167 // while. This can be worked around with these two methods. There
168 // might be a better way, but it's good enough.
169 if ([win respondsToSelector:@selector(
170 setAutorecalculatesContentBorderThickness:forEdge:)])
171 [win setAutorecalculatesContentBorderThickness:NO
173 if ([win respondsToSelector:
174 @selector(setContentBorderThickness:forEdge:)])
175 [win setContentBorderThickness:0 forEdge:NSMaxYEdge];
178 // Make us safe on pre-tiger OSX
179 if ([win respondsToSelector:@selector(_setContentHasShadow:)])
180 [win _setContentHasShadow:NO];
190 //NSLog(@"%@ %s", [self className], _cmd);
192 [tablineSeparator release]; tablineSeparator = nil;
193 [windowAutosaveKey release]; windowAutosaveKey = nil;
194 [vimView release]; vimView = nil;
199 - (NSString *)description
202 @"%@ : setupDone=%d windowAutosaveKey=%@ vimController=%@";
203 return [NSString stringWithFormat:format,
204 [self className], setupDone, windowAutosaveKey, vimController];
207 - (MMVimController *)vimController
209 return vimController;
212 - (MMTextView *)textView
214 return [vimView textView];
217 - (MMTextStorage *)textStorage
219 return [vimView textStorage];
222 - (MMVimView *)vimView
227 - (NSString *)windowAutosaveKey
229 return windowAutosaveKey;
232 - (void)setWindowAutosaveKey:(NSString *)key
234 [windowAutosaveKey autorelease];
235 windowAutosaveKey = [key copy];
240 //NSLog(@"%@ %s", [self className], _cmd);
242 if (fullscreenWindow != nil) {
243 // if we are closed while still in fullscreen, end fullscreen mode,
244 // release ourselves (because this won't happen in MMWindowController)
245 // and perform close operation on the original window
246 [self leaveFullscreen];
252 [tablineSeparator removeFromSuperviewWithoutNeedingDisplay];
253 [vimView removeFromSuperviewWithoutNeedingDisplay];
254 [vimView cleanup]; // TODO: is this necessary?
256 // It is feasible that the user quits before the window controller is
257 // released, make sure the edit flag is cleared so no warning dialog is
259 [[self window] setDocumentEdited:NO];
261 [[self window] orderOut:self];
266 [[NSApp delegate] windowControllerWillOpen:self];
268 [self addNewTabViewItem];
272 [self updateResizeIncrements];
273 [self resizeWindowToFit:self];
274 [[self window] makeKeyAndOrderFront:self];
277 - (void)updateTabsWithData:(NSData *)data
279 [vimView updateTabsWithData:data];
282 - (void)selectTabWithIndex:(int)idx
284 [vimView selectTabWithIndex:idx];
287 - (void)setTextDimensionsWithRows:(int)rows columns:(int)cols
289 //NSLog(@"setTextDimensionsWithRows:%d columns:%d", rows, cols);
291 [vimView setActualRows:rows columns:cols];
293 if (setupDone && ![vimView inLiveResize])
294 shouldUpdateWindowSize = YES;
297 - (void)createScrollbarWithIdentifier:(long)ident type:(int)type
299 [vimView createScrollbarWithIdentifier:ident type:type];
302 - (void)destroyScrollbarWithIdentifier:(long)ident
304 [vimView destroyScrollbarWithIdentifier:ident];
305 [self checkWindowNeedsResizing];
308 - (void)showScrollbarWithIdentifier:(long)ident state:(BOOL)visible
310 [vimView showScrollbarWithIdentifier:ident state:visible];
311 [self checkWindowNeedsResizing];
314 - (void)setScrollbarPosition:(int)pos length:(int)len identifier:(long)ident
316 [vimView setScrollbarPosition:pos length:len identifier:ident];
319 - (void)setScrollbarThumbValue:(float)val proportion:(float)prop
320 identifier:(long)ident
322 [vimView setScrollbarThumbValue:val proportion:prop identifier:ident];
325 - (void)setDefaultColorsBackground:(NSColor *)back foreground:(NSColor *)fore
327 // NOTE: This is called when the transparency changes so set the opacity
328 // flag on the window here (should be faster if the window is opaque).
329 BOOL isOpaque = [back alphaComponent] == 1.0f;
330 [[self window] setOpaque:isOpaque];
332 [vimView setDefaultColorsBackground:back foreground:fore];
335 - (void)setFont:(NSFont *)font
337 [[NSFontManager sharedFontManager] setSelectedFont:font isMultiple:NO];
338 [[vimView textStorage] setFont:font];
339 [self updateResizeIncrements];
342 - (void)setWideFont:(NSFont *)font
344 [[vimView textStorage] setWideFont:font];
347 - (void)processCommandQueueDidFinish
349 // XXX: If not in live resize and vimview's desired size differs from actual
350 // size, resize ourselves
351 if (shouldUpdateWindowSize) {
352 shouldUpdateWindowSize = NO;
353 [vimView setShouldUpdateWindowSize:NO];
354 [self resizeWindowToFit:self];
358 - (void)popupMenu:(NSMenu *)menu atRow:(int)row column:(int)col
360 if (!setupDone) return;
363 if (row >= 0 && col >= 0) {
364 NSSize cellSize = [[vimView textStorage] cellSize];
365 NSPoint pt = { (col+1)*cellSize.width, (row+1)*cellSize.height };
366 pt = [[vimView textView] convertPoint:pt toView:nil];
368 event = [NSEvent mouseEventWithType:NSRightMouseDown
372 windowNumber:[[self window] windowNumber]
378 event = [[vimView textView] lastMouseDownEvent];
381 [NSMenu popUpContextMenu:menu withEvent:event forView:[vimView textView]];
384 - (void)showTabBar:(BOOL)on
386 [[vimView tabBarControl] setHidden:!on];
388 // Rules for when to show tabline separator:
390 // Tabline visible & Toolbar visible => Separator visible
391 // ================================================================
392 // NO & NO => NO (Tiger), YES (Leopard)
397 // XXX: This is ignored if called while in fullscreen mode
399 NSToolbar *toolbar = [[self window] toolbar];
400 if (([[self window] styleMask] & NSTexturedBackgroundWindowMask) == 0) {
401 [tablineSeparator setHidden:![toolbar isVisible]];
403 [tablineSeparator setHidden:NO];
406 if (([[self window] styleMask] & NSTexturedBackgroundWindowMask) == 0) {
407 [tablineSeparator setHidden:on];
409 [tablineSeparator setHidden:YES];
414 // shouldUpdateWindowSize = YES;
417 - (void)showToolbar:(BOOL)on size:(int)size mode:(int)mode
419 NSToolbar *toolbar = [[self window] toolbar];
420 if (!toolbar) return;
422 [toolbar setSizeMode:size];
423 [toolbar setDisplayMode:mode];
424 [toolbar setVisible:on];
426 // See showTabBar: for circumstances when the separator should be hidden.
427 if (([[self window] styleMask] & NSTexturedBackgroundWindowMask) == 0) {
429 [tablineSeparator setHidden:YES];
431 [tablineSeparator setHidden:![[vimView tabBarControl] isHidden]];
434 // Textured windows don't have a line below there title bar, so we
435 // need the separator in this case as well. In fact, the only case
436 // where we don't need the separator is when the tab bar control
437 // is visible (because it brings its own separator).
438 [tablineSeparator setHidden:![[vimView tabBarControl] isHidden]];
442 - (void)setMouseShape:(int)shape
444 // This switch should match mshape_names[] in misc2.c.
446 // TODO: Add missing cursor shapes.
448 case 2: [[NSCursor IBeamCursor] set]; break;
449 case 3: case 4: [[NSCursor resizeUpDownCursor] set]; break;
450 case 5: case 6: [[NSCursor resizeLeftRightCursor] set]; break;
451 case 9: [[NSCursor crosshairCursor] set]; break;
452 case 10: [[NSCursor pointingHandCursor] set]; break;
453 case 11: [[NSCursor openHandCursor] set]; break;
455 [[NSCursor arrowCursor] set]; break;
458 // Shape 1 indicates that the mouse cursor should be hidden.
460 [NSCursor setHiddenUntilMouseMoves:YES];
463 - (void)adjustLinespace:(int)linespace
465 if (vimView && [vimView textStorage]) {
466 [[vimView textStorage] setLinespace:(float)linespace];
467 shouldUpdateWindowSize = YES;
471 - (void)liveResizeWillStart
473 // Save the original title, if we haven't already.
474 if (lastSetTitle == nil) {
475 lastSetTitle = [[[self window] title] retain];
479 - (void)liveResizeDidEnd
481 if (!setupDone) return;
483 // NOTE: During live resize the window is not constrained to lie inside the
484 // screen (because we must not programmatically alter the window size
485 // during live resize or it will 'jitter'), so at the end of live resize we
486 // make sure a final SetTextDimensionsMsgID message is sent to ensure that
487 // resizeWindowToFit does get called. For this reason and also because we
488 // want to ensure that Vim and MacVim have consistent states, this resize
489 // message is sent synchronously. (If the states were inconsistent the
490 // text view may become too large or too small to fit the window.)
492 NSSize contentSize = [self contentSize];
495 [vimView getDesiredRows:&desiredSize[0] columns:&desiredSize[1]
496 forSize:contentSize];
498 NSData *data = [NSData dataWithBytes:desiredSize length:2*sizeof(int)];
500 BOOL resizeOk = [vimController sendMessageNow:SetTextDimensionsMsgID
505 // Force the window size to match the text view size otherwise Vim and
506 // MacVim will have inconsistent states.
507 [self resizeWindowToFit:self];
510 // If we saved the original title while resizing, restore it.
511 if (lastSetTitle != nil) {
512 [[self window] setTitle:lastSetTitle];
513 [lastSetTitle release];
520 if (!setupDone) return;
523 vimViewRect.origin = NSMakePoint(0, 0);
524 vimViewRect.size = [vimView getDesiredRows:NULL columns:NULL
525 forSize:[self contentSize]];
527 // HACK! If the window does resize, then windowDidResize is called which in
528 // turn calls placeViews. In case the computed new size of the window is
529 // no different from the current size, then we need to call placeViews
531 if (NSEqualRects(vimViewRect, [vimView frame])) {
532 [vimView placeViews];
534 [vimView setFrame:vimViewRect];
538 - (void)enterFullscreen
540 fullscreenWindow = [[MMFullscreenWindow alloc] initWithWindow:[self window]
542 [fullscreenWindow enterFullscreen];
544 [fullscreenWindow setDelegate:self];
547 - (void)leaveFullscreen
549 [fullscreenWindow leaveFullscreen];
550 [fullscreenWindow release];
551 fullscreenWindow = nil;
555 - (IBAction)addNewTab:(id)sender
557 [vimView addNewTab:sender];
560 - (IBAction)toggleToolbar:(id)sender
562 [vimController sendMessage:ToggleToolbarMsgID data:nil];
567 // -- NSWindow delegate ------------------------------------------------------
569 - (void)windowDidBecomeMain:(NSNotification *)notification
571 [vimController sendMessage:GotFocusMsgID data:nil];
573 if ([vimView textStorage]) {
574 NSFontManager *fontManager = [NSFontManager sharedFontManager];
575 [fontManager setSelectedFont:[[vimView textStorage] font]
580 - (void)windowDidResignMain:(NSNotification *)notification
582 [vimController sendMessage:LostFocusMsgID data:nil];
584 if ([vimView textView])
585 [[vimView textView] hideMarkedTextField];
588 - (BOOL)windowShouldClose:(id)sender
590 [vimController sendMessage:VimShouldCloseMsgID data:nil];
594 - (void)windowDidMove:(NSNotification *)notification
596 if (setupDone && windowAutosaveKey) {
597 NSRect frame = [[self window] frame];
598 NSPoint topLeft = { frame.origin.x, NSMaxY(frame) };
599 NSString *topLeftString = NSStringFromPoint(topLeft);
601 [[NSUserDefaults standardUserDefaults]
602 setObject:topLeftString forKey:windowAutosaveKey];
606 - (void)windowDidResize:(id)sender
608 if (!setupDone) return;
610 // Live resizing works as follows:
611 // VimView's size is changed immediatly, and a resize message to the
612 // remote vim instance is sent. The remote vim instance sends a
613 // "vim content size changed" right back, but in live resize mode this
614 // doesn't change the VimView (because we assume that it already has the
615 // correct size because we set the resize increments correctly). Afterward,
616 // the remote vim view sends a batch draw for the text visible in the
617 // resized text area.
619 NSSize contentSize = [self contentSize];
620 [self resizeVimViewToFitSize:contentSize];
623 frame.origin = NSMakePoint(0, 0);
624 frame.size = contentSize;
625 [vimView setFrame:frame];
628 - (NSRect)windowWillUseStandardFrame:(NSWindow *)win
629 defaultFrame:(NSRect)frame
631 // HACK! For some reason 'frame' is not always constrained to fit on the
632 // screen (e.g. it may overlap the menu bar), so first constrain it to the
633 // screen; otherwise the new frame we compute may be too large and this
634 // will mess up the display after the window resizes.
635 frame = [win constrainFrameRect:frame toScreen:[win screen]];
637 // HACK! If the top of 'frame' is lower than the current window frame,
638 // increase 'frame' so that their tops align. Really, 'frame' should
639 // already have its top at least as high as the current window frame, but
640 // for some reason this is not always the case.
641 // (See resizeWindowToFit: for a similar hack.)
642 NSRect cur = [win frame];
643 if (NSMaxY(cur) > NSMaxY(frame)) {
644 frame.size.height = cur.origin.y - frame.origin.y + cur.size.height;
647 frame = [self fitWindowToFrame:frame];
649 // Keep old width and horizontal position unless user clicked while the
650 // Command key is held down.
651 NSEvent *event = [NSApp currentEvent];
652 if (!([event type] == NSLeftMouseUp
653 && [event modifierFlags] & NSCommandKeyMask)) {
654 NSRect currentFrame = [win frame];
655 frame.size.width = currentFrame.size.width;
656 frame.origin.x = currentFrame.origin.x;
665 // -- Services menu delegate -------------------------------------------------
667 - (id)validRequestorForSendType:(NSString *)sendType
668 returnType:(NSString *)returnType
670 if ([sendType isEqual:NSStringPboardType]
671 && [self askBackendForStarRegister:nil])
674 return [super validRequestorForSendType:sendType returnType:returnType];
677 - (BOOL)writeSelectionToPasteboard:(NSPasteboard *)pboard
678 types:(NSArray *)types
680 if (![types containsObject:NSStringPboardType])
683 return [self askBackendForStarRegister:pboard];
686 @end // MMWindowController
690 @implementation MMWindowController (Private)
692 - (NSRect)contentRectForFrameRect:(NSRect)frame
694 NSRect result = [[self window] contentRectForFrameRect:frame];
695 if (![tablineSeparator isHidden])
696 --result.size.height;
700 - (NSRect)frameRectForContentRect:(NSRect)contentRect
702 if (![tablineSeparator isHidden])
703 ++contentRect.size.height;
704 return [[self window] frameRectForContentRect:contentRect];
707 - (NSSize)contentSize
709 return [self contentRectForFrameRect:[[self window] frame]].size;
712 - (void)resizeWindowToFit:(id)sender
714 // Makes the window large enough to contain the vim view, called after the
715 // vim view's size was changed. If the window had to become to big, the
716 // vim view is made smaller.
718 // NOTE: Be very careful when you call this method! Do not call while
719 // processing command queue, instead set 'shouldUpdateWindowSize' to YES.
720 // The only other place it is currently called is when live resize ends.
721 // This is done to ensure that the text view and window sizes match up
722 // (they may become out of sync if a SetTextDimensionsMsgID message to the
723 // backend is dropped).
725 if (!setupDone) return;
727 // Get size of text view, adapt window size to it
728 NSWindow *win = [self window];
729 NSRect frame = [win frame];
730 NSRect contentRect = [self contentRectForFrameRect:frame];
731 NSSize newSize = [vimView desiredSizeForActualRowsAndColumns];
733 // Keep top-left corner of the window fixed when resizing.
734 contentRect.origin.y -= newSize.height - contentRect.size.height;
735 contentRect.size = newSize;
737 frame = [self frameRectForContentRect:contentRect];
738 NSRect maxFrame = [win constrainFrameRect:frame toScreen:[win screen]];
740 // HACK! Assuming the window frame cannot already be placed too high,
741 // adjust 'maxFrame' so that it at least as high up as the current frame.
742 // The reason for doing this is that constrainFrameRect:toScreen: does not
743 // always seem to utilize as much area as possible.
744 if (NSMaxY(frame) > NSMaxY(maxFrame)) {
745 maxFrame.size.height = frame.origin.y - maxFrame.origin.y
749 if (!NSEqualRects(maxFrame, frame)) {
750 // The new window frame is too big to fit on the screen, so fit the
751 // text storage to the biggest frame which will fit on the screen.
752 //NSLog(@"Proposed window frame does not fit on the screen!");
753 frame = [self fitWindowToFrame:maxFrame];
754 [self resizeVimViewToFitSize:[self contentRectForFrameRect:frame].size];
757 // NSLog(@"%s %@", _cmd, NSStringFromRect(frame));
759 // HACK! If the window does resize, then windowDidResize is called which in
760 // turn calls placeViews. In case the computed new size of the window is
761 // no different from the current size, then we need to call placeViews
763 if (NSEqualRects(frame, [win frame])) {
766 [win setFrame:frame display:YES];
770 - (NSRect)fitWindowToFrame:(NSRect)frame
772 if (!setupDone) return frame;
774 NSRect contentRect = [self contentRectForFrameRect:frame];
775 NSSize size = [vimView getDesiredRows:NULL columns:NULL
776 forSize:contentRect.size];
778 // Keep top-left corner of 'frame' fixed.
779 contentRect.origin.y -= size.height - contentRect.size.height;
780 contentRect.size = size;
782 return [self frameRectForContentRect:contentRect];
785 - (void)updateResizeIncrements
787 if (!setupDone) return;
789 NSSize size = [[vimView textStorage] cellSize];
790 [[self window] setContentResizeIncrements:size];
793 - (NSTabViewItem *)addNewTabViewItem
795 return [vimView addNewTabViewItem];
798 - (IBAction)vimMenuItemAction:(id)sender
800 int tag = [sender tag];
802 NSMutableData *data = [NSMutableData data];
803 [data appendBytes:&tag length:sizeof(int)];
805 [vimController sendMessage:ExecuteMenuMsgID data:data];
808 - (BOOL)askBackendForStarRegister:(NSPasteboard *)pb
811 id backendProxy = [vimController backendProxy];
815 reply = [backendProxy starRegisterToPasteboard:pb];
817 @catch (NSException *e) {
818 NSLog(@"WARNING: Caught exception in %s: \"%@\"", _cmd, e);
825 - (void)checkWindowNeedsResizing
827 shouldUpdateWindowSize =
828 shouldUpdateWindowSize || [vimView shouldUpdateWindowSize];
831 - (NSSize)resizeVimViewToFitSize:(NSSize)size
833 // If our optimal (rows,cols) do not match our current (rows,cols), resize
834 // ourselves and tell the Vim process to sync up.
836 NSSize newSize = [vimView getDesiredRows:&desired[0] columns:&desired[1]
840 [vimView getActualRows:&rows columns:&columns];
842 if (desired[0] != rows || desired[1] != columns) {
843 // NSLog(@"Notify Vim that text storage dimensions changed from %dx%d "
844 // @"to %dx%d", columns, rows, desired[0], desired[1]);
845 NSData *data = [NSData dataWithBytes:desired length:2*sizeof(int)];
847 [vimController sendMessage:SetTextDimensionsMsgID data:data];
849 // We only want to set the window title if this resize came from
850 // a live-resize, not (for example) setting 'columns' or 'lines'.
851 if ([[self textView] inLiveResize]) {
852 [[self window] setTitle:[NSString stringWithFormat:@"%dx%d",
853 desired[1], desired[0]]];
861 @end // MMWindowController (Private)