/// <summary> /// Moves the position to the end of wrapped line. /// </summary> /// <param name="displayContext">The display context.</param> public static TextPosition ToEndOfWrappedLine( this TextPosition bufferPosition, IDisplayContext displayContext) { // Get the wrapped line and layout. Layout layout; int wrappedLineIndex; LayoutLine wrappedLine = bufferPosition.GetWrappedLine( displayContext, out layout, out wrappedLineIndex); // Move to the end of the wrapped line. If this isn't the last, we // need to shift back one character. int unicodeIndex = wrappedLine.StartIndex + wrappedLine.Length; if (wrappedLineIndex != layout.LineCount - 1) { unicodeIndex--; } // Because the wrappedLine works with UTF-8 encoding, we need to // convert it back to a C# string. string lineText = displayContext.LineBuffer.GetLineText(bufferPosition.LinePosition); int characterIndex = PangoUtility.TranslatePangoToStringIndex( lineText, unicodeIndex); // Create a new buffer position from the elements and return it. return(new TextPosition(bufferPosition.LinePosition, characterIndex)); }
/// <summary> /// Selects the word around the current cursor position. /// </summary> /// <param name="controller">The controller.</param> public static void SelectWord(EditorViewController controller) { // Pull out information about the current context. IDisplayContext displayContext = controller.DisplayContext; LineBuffer buffer = displayContext.LineBuffer; TextPosition position = displayContext.Caret.Position; int lineIndex = position.LinePosition.GetLineIndex(buffer); string lineText = buffer.GetLineText(lineIndex); int characterIndex = position.GetCharacterIndex(buffer); // Find the boundaries for the current word. int startIndex = Math.Max( 0, displayContext.WordTokenizer.GetPreviousWordBoundary( lineText, characterIndex)); int endIndex = Math.Min( lineText.Length, displayContext.WordTokenizer.GetNextWordBoundary(lineText, characterIndex)); // Set the selection to the boundaries. displayContext.Caret.Selection = new TextRange( new TextPosition(position.LinePosition, startIndex), new TextPosition(position.LinePosition, endIndex)); }
/// <summary> /// Draws the margin at the given position. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="renderContext">The render context.</param> /// <param name="lineIndex">The line index being rendered.</param> /// <param name="point">The point of the specific line number.</param> /// <param name="height">The height of the rendered line.</param> /// <param name="lineBlockStyle">The line block style.</param> public abstract void Draw( IDisplayContext displayContext, IRenderContext renderContext, int lineIndex, PointD point, double height, LineBlockStyle lineBlockStyle);
public static void Right(EditorViewController controller) { // Pull out some useful variables. IDisplayContext displayContext = controller.DisplayContext; LineBuffer lineBuffer = displayContext.LineBuffer; // Move the character position based on line context. TextPosition position = displayContext.Caret.Position; LinePosition linePosition = position.LinePosition; int lineIndex = linePosition.GetLineIndex(lineBuffer); int lineLength = lineBuffer.GetLineLength(lineIndex); CharacterPosition characterPosition = position.CharacterPosition; int characterIndex = position.GetCharacterIndex(lineBuffer); if (characterIndex == lineLength) { if (lineIndex < lineBuffer.LineCount - 1) { linePosition = new LinePosition(lineIndex + 1); characterPosition = CharacterPosition.Begin; } } else { characterPosition = new CharacterPosition(characterIndex + 1); } // Cause the text editor to redraw itself. var caretPosition = new TextPosition(linePosition, characterPosition); displayContext.ScrollToCaret(caretPosition); }
protected override void Do( object context, CommandFactoryManager <OperationContext> commandFactory, object commandData, OperationContext operationContext, EditorViewController controller, IDisplayContext displayContext, TextPosition position) { // Create the command and execute it. var textPosition = new TextPosition( displayContext.Caret.Position.LinePosition, displayContext.Caret.Position.CharacterPosition); var splitCommand = new SplitParagraphCommand <OperationContext>( controller.CommandController, textPosition); controller.CommandController.Do(splitCommand, operationContext); // If we have a text position, we need to set it. if (operationContext.Results.HasValue) { displayContext.Caret.SetAndScrollToPosition( operationContext.Results.Value.TextPosition); } }
protected override void Do( object context, CommandFactoryManager <OperationContext> commandFactory, object commandData, OperationContext operationContext, EditorViewController controller, IDisplayContext displayContext, TextPosition position) { IDeleteTextCommand <OperationContext> deleteCommand = controller.CommandController.CreateDeleteTextCommand( new SingleLineTextRange( displayContext.Caret.Position.LinePosition, displayContext.Caret.Position.CharacterPosition, CharacterPosition.Word)); deleteCommand.UpdateTextPosition = DoTypes.All; // Execute the command. controller.CommandController.Do(deleteCommand, operationContext); // If we have a text position, we need to set it. if (operationContext.Results.HasValue) { displayContext.Caret.SetAndScrollToPosition( operationContext.Results.Value.TextPosition); } }
public static void Left(EditorViewController controller) { // Pull out some useful variables. IDisplayContext displayContext = controller.DisplayContext; LineBuffer lineBuffer = displayContext.LineBuffer; // Move the character position based on line context. TextPosition position = displayContext.Caret.Position; LinePosition linePosition = position.LinePosition; CharacterPosition characterPosition = position.CharacterPosition; int characterIndex = position.GetCharacterIndex(lineBuffer); if (characterIndex == 0) { if (linePosition.Index > 0) { linePosition = new LinePosition(linePosition.Index - 1); characterPosition = CharacterPosition.End; } } else { // We have to resolve the character index before we calculate // the position since it may be symbolic. characterPosition = new CharacterPosition(characterIndex - 1); } // Cause the text editor to redraw itself. var caretPosition = new TextPosition(linePosition, characterPosition); displayContext.ScrollToCaret(caretPosition); }
public static void PageUp(EditorViewController controller) { // Extract a number of useful variable for this method. IDisplayContext displayContext = controller.DisplayContext; TextPosition position = displayContext.Caret.Position; // Figure out the layout and wrapped line we are currently on. Layout layout; int wrappedLineIndex; LayoutLine wrappedLine = position.GetWrappedLine( displayContext, out layout, out wrappedLineIndex); // Figure out where in the buffer we're located. int lineHeight; PointD point = position.ToScreenCoordinates(displayContext, out lineHeight); // Shift down the buffer a full page size and clamp it to the actual // buffer size. double bufferY = Math.Max(point.Y - displayContext.VerticalAdjustment.PageSize, 0); // Figure out the X coordinate of the line. If there is an action context, // use that. Otherwise, calculate it from the character index of the position. int pixels = Units.ToPixels(GetLineX(controller, wrappedLine, position)); int lineX = pixels; // Move to the calculated point. var newPoint = new PointD(lineX, bufferY - displayContext.BufferOffsetY); Point(controller, newPoint); }
public static void EndOfBuffer(EditorViewController controller) { IDisplayContext displayContext = controller.DisplayContext; Caret caret = displayContext.Caret; displayContext.ScrollToCaret(caret.Position.ToEndOfBuffer(displayContext)); }
public void Do( object context, CommandFactoryReference commandFactoryReference, CommandFactoryManager <OperationContext> controller) { // Pull out some useful variables for processing. var editViewController = (EditorViewController)context; IDisplayContext displayContext = editViewController.DisplayContext; TextPosition position = displayContext.Caret.Position; // Set up the operation context for this request. var textPosition = new TextPosition( displayContext.Caret.Position.LinePosition, displayContext.Caret.Position.CharacterPosition); var operationContext = new OperationContext( displayContext.LineBuffer, textPosition); // Create the commands and execute them. Do( context, controller, commandFactoryReference.Data, operationContext, editViewController, displayContext, position); }
/// <summary> /// Draws the margins at the given position. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="renderContext">The render context.</param> /// <param name="lineIndex">The line index being rendered.</param> /// <param name="point">The point of the specific line number.</param> /// <param name="height">The height of the rendered line.</param> /// <param name="lineBlockStyle">The line block style.</param> public void Draw( IDisplayContext displayContext, IRenderContext renderContext, int lineIndex, PointD point, double height, LineBlockStyle lineBlockStyle) { // Go through the margins and draw each one so they don't overlap. double dx = point.X; foreach (MarginRenderer marginRenderer in this) { // If it isn't visible, then we do nothing. if (!marginRenderer.Visible) { continue; } // Draw out the individual margin. marginRenderer.Draw( displayContext, renderContext, lineIndex, new PointD(dx, point.Y), height, lineBlockStyle); // Add to the x coordinate so we don't overlap the renders. dx += marginRenderer.Width; } }
/// <summary> /// Determines whether the position is at the beginning of a wrapped line. /// </summary> /// <param name="bufferPosition">The buffer position.</param> /// <param name="displayContext">The display context.</param> /// <returns> /// <c>true</c> if [is begining of wrapped line] [the specified display context]; otherwise, <c>false</c>. /// </returns> public static bool IsBeginingOfWrappedLine( this TextPosition bufferPosition, IDisplayContext displayContext) { return(bufferPosition.CharacterPosition == bufferPosition.GetWrappedLine(displayContext).StartIndex); }
/// <summary> /// Gets the wrapped line associated with this buffer position. /// </summary> /// <param name="bufferPosition">The buffer position.</param> /// <param name="displayContext">The display context.</param> /// <param name="layout">The layout.</param> /// <param name="wrappedLineIndex">Index of the wrapped line.</param> /// <returns></returns> public static LayoutLine GetWrappedLine( this TextPosition bufferPosition, IDisplayContext displayContext, out Layout layout, out int wrappedLineIndex) { // Get the layout and text associated with the line. LineBuffer lineBuffer = displayContext.LineBuffer; int lineIndex = bufferPosition.LinePosition.GetLineIndex(lineBuffer); string text = lineBuffer.GetLineText(lineIndex); layout = displayContext.Renderer.GetLineLayout( lineIndex, LineContexts.Unformatted); // Get the wrapped line associated with this character position. int characterIndex = bufferPosition.GetCharacterIndex(lineBuffer); int unicodeIndex = PangoUtility.TranslateStringToPangoIndex( text, characterIndex); int x; layout.IndexToLineX(unicodeIndex, false, out wrappedLineIndex, out x); // Return the resulting line. return(layout.Lines[wrappedLineIndex]); }
/// <summary> /// Updates the caret/selection on screen. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="previousSelection">The previous selection.</param> public override void UpdateSelection( IDisplayContext displayContext, TextRange previousSelection) { // Make sure we're on the proper thread. CheckGuiThread(); // We need to get a write lock on the entire cache to avoid // anything else making changes. using (new WriteLock(access)) { // Only update the caches if one of the current or previous // selections was actually selecting something. TextRange currentSelection = displayContext.Caret.Selection; if (!previousSelection.IsEmpty || !currentSelection.IsEmpty) { // Clear out the cache for all the lines in the previous // selected range. ClearCacheLines(previousSelection); ClearCacheLines(currentSelection); } // Call the base implementation. base.UpdateSelection(displayContext, previousSelection); } // Process any queued changes. ProcessQueuedLineChanges(); }
/// <summary> /// Gets the wrapped line layout for a given buffer Y coordinate and the /// associated index. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="bufferY">The buffer Y.</param> /// <param name="wrappedLineIndex">Index of the wrapped line.</param> /// <param name="lineContexts">The line contexts.</param> /// <returns></returns> public LayoutLine GetWrappedLineLayout( IDisplayContext displayContext, double bufferY, out int wrappedLineIndex, LineContexts lineContexts) { // Get the line that contains the given Y coordinate. int lineIndex, endLineIndex; GetLineLayoutRange( new Rectangle(0, bufferY, 0, bufferY), out lineIndex, out endLineIndex); // Get the layout-relative Y coordinate. double layoutY = bufferY - GetLineLayoutHeight(0, lineIndex); // Figure out which line inside the layout. Layout layout = GetLineLayout(lineIndex, LineContexts.None); int trailing; layout.XyToIndex(0, (int)layoutY, out wrappedLineIndex, out trailing); // Return the layout line. return(layout.Lines[wrappedLineIndex]); }
public static void BeginningOfWrappedLine(EditorViewController controller) { IDisplayContext displayContext = controller.DisplayContext; Caret caret = displayContext.Caret; displayContext.ScrollToCaret( caret.Position.ToBeginningOfWrappedLine(displayContext)); }
protected abstract void Do( object context, CommandFactoryManager <OperationContext> commandFactory, object commandData, OperationContext operationContext, EditorViewController editViewController, IDisplayContext displayContext, TextPosition position);
/// <summary> /// Gets the wrapped line layout for a given buffer Y coordinate. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="bufferY">The buffer Y.</param> /// <returns></returns> public LayoutLine GetWrappedLineLayout( IDisplayContext displayContext, double bufferY) { int wrappedLineIndex; return(GetWrappedLineLayout( displayContext, bufferY, out wrappedLineIndex, LineContexts.None)); }
/// <summary> /// Gets the wrapped line associated with this buffer position. /// </summary> /// <param name="bufferPosition">The buffer position.</param> /// <param name="displayContext">The display context.</param> /// <returns></returns> public static LayoutLine GetWrappedLine( this TextPosition bufferPosition, IDisplayContext displayContext) { Layout layout; int wrappedLineIndex; return(bufferPosition.GetWrappedLine( displayContext, out layout, out wrappedLineIndex)); }
/// <summary> /// Selects the entire line the current currently is located on. /// </summary> /// <param name="controller">The controller.</param> public static void SelectLine(EditorViewController controller) { IDisplayContext displayContext = controller.DisplayContext; TextPosition position = displayContext.Caret.Position; controller.DisplayContext.Caret.Selection = new TextRange( position.ToBeginningOfLine(displayContext), position.ToEndOfLine(displayContext)); }
/// <summary> /// Gets the index of the wrapped line layout. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="bufferY">The buffer Y.</param> /// <returns></returns> public int GetWrappedLineLayoutIndex( IDisplayContext displayContext, double bufferY) { int wrappedLineIndex; GetWrappedLineLayout( displayContext, bufferY, out wrappedLineIndex, LineContexts.None); return(wrappedLineIndex); }
/// <summary> /// Initializes a new instance of the <see cref="EditorViewRenderer"/> class. /// </summary> /// <param name="displayContext">The display context.</param> protected EditorViewRenderer(IDisplayContext displayContext) { // Set the properties in the renderer. if (displayContext == null) { throw new ArgumentNullException("displayContext"); } DisplayContext = displayContext; }
/// <summary> /// Initializes a new instance of the <see cref="EditorViewRenderer"/> class. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="lineBuffer">The line buffer.</param> public LineBufferRenderer( IDisplayContext displayContext, LineBuffer lineBuffer) : base(displayContext) { // Save the buffer in a property. SetLineBuffer(lineBuffer); // Set up the selection. selectionRenderer = new SelectionRenderer(); }
/// <summary> /// Initializes a new instance of the <see cref="EditorViewRendererDecorator"/> class. /// </summary> /// <param name="displayContext">The display context.</param> /// <param name="editorViewRenderer">The text renderer.</param> protected EditorViewRendererDecorator( IDisplayContext displayContext, EditorViewRenderer editorViewRenderer) : base(displayContext) { EditorViewRenderer = editorViewRenderer; if (editorViewRenderer == null) { throw new ArgumentNullException("editorViewRenderer"); } }
/// <summary> /// Finds the color of the highest priority style and returns it. /// </summary> /// <param name="displayContext">The display context.</param> private void SetHighestColor(IDisplayContext displayContext) { // Go through all the indicators and look for a style. Theme theme = displayContext.Theme; IndicatorStyle highestStyle = null; for (int index = 0; index < indicators.Count; index++) { // Try to get a style for this indicator. If we don't have // one, then just skip it. ILineIndicator indicator = indicators[index]; if (!theme.IndicatorStyles.ContainsKey(indicator.LineIndicatorStyle)) { // No style, nothing to render. continue; } // Get the style for this indicator. IndicatorStyle style = theme.IndicatorStyles[indicator.LineIndicatorStyle]; if (highestStyle == null || highestStyle.Priority < style.Priority) { highestStyle = style; } } // If we don't have a style at the bottom, we aren't visible. Visible = highestStyle != null; if (highestStyle != null) { colors = new[] { highestStyle.Color }; ratios = new[] { 1.0 }; } else { colors = null; ratios = null; } }
/// <summary> /// Gets the buffer position from a given point. /// </summary> /// <param name="widgetPoint">The widget point.</param> /// <param name="displayContext">The display context.</param> /// <returns></returns> public static TextPosition GetTextPosition( PointD widgetPoint, EditorViewController controller) { IDisplayContext displayContext = controller.DisplayContext; double y = widgetPoint.Y + displayContext.BufferOffsetY; int lineIndex = displayContext.Renderer.GetLineLayoutRange(y); Layout layout = displayContext.Renderer.GetLineLayout( lineIndex, LineContexts.None); // Shift the buffer-relative coordinates to layout-relative coordinates. double layoutY = y; if (lineIndex > 0) { layoutY -= displayContext.Renderer.GetLineLayoutHeight(0, lineIndex - 1); } int pangoLayoutY = Units.FromPixels((int)layoutY); // Shift the buffer-relative coordinates to handle padding. LineBlockStyle style = displayContext.Renderer.GetLineStyle( lineIndex, LineContexts.None); double layoutX = widgetPoint.X - style.Left; // Determines where in the layout is the point. int pangoLayoutX = Units.FromPixels((int)layoutX); int unicodeIndex; int trailing; layout.XyToIndex(pangoLayoutX, pangoLayoutY, out unicodeIndex, out trailing); // When dealing with UTF-8 characters, we have to convert the // Unicode index into a C# index. string lineText = displayContext.LineBuffer.GetLineText(lineIndex); unicodeIndex = NormalizeEmptyStrings(lineText, unicodeIndex); int characterIndex = PangoUtility.TranslatePangoToStringIndex( lineText, unicodeIndex); // If the source text is empty, then we disable the trailing. if (lineText.Length == 0) { trailing = 0; } // Return the buffer position. return(new TextPosition(lineIndex, characterIndex + trailing)); }
public static void ShowContextMenu(EditorViewController controller) { // Get the coordinates to display the menu. Since the popup that // sets the coordinates based on the screen, we have to adjust from // text-specific coordinates clear to screen coordinates. // Start by getting the widget's screen coordinates. IDisplayContext displayContext = controller.DisplayContext; int screenX, screenY; displayContext.GdkWindow.GetOrigin(out screenX, out screenY); // Figure out the position of the position in the screen. We add // the screen relative coordinate to the widget-relative, plus add // the height of a single line to shift it down slightly. int lineHeight; PointD point = displayContext.Caret.Position.ToScreenCoordinates( displayContext, out lineHeight); var widgetY = (int)(screenY + lineHeight + point.Y); // Create the context menu and show it on the screen right below // where the user is currently focused. Menu contextMenu = controller.CreateContextMenu(); if (contextMenu != null) { contextMenu.ShowAll(); contextMenu.Popup( null, null, delegate(Menu delegateMenu, out int x, out int y, out bool pushIn) { x = screenX; y = widgetY; pushIn = true; }, 3, Global.CurrentEventTime); } }
protected override void Do( object context, CommandFactoryManager <OperationContext> commandFactory, object commandData, OperationContext operationContext, EditorViewController controller, IDisplayContext displayContext, TextPosition position) { // If we don't have a selection, this is a simple insert command. TextPosition bufferPosition = displayContext.Caret.Position; TextRange selection = displayContext.Caret.Selection; if (!selection.IsEmpty) { // Create and execute the delete command. We do this separately // so they show up as a different undo item. IUndoableCommand <OperationContext> deleteCommand = DeleteSelectionCommandFactory.CreateCommand(controller, displayContext); controller.CommandController.Do(deleteCommand, operationContext); // We have to reset the position so the insert happens as if // the text doesn't exist. bufferPosition = selection.FirstTextPosition; operationContext = new OperationContext( operationContext.LineBuffer, bufferPosition); } // Create the insert command using the (potentially) modified selection. string text = commandData.ToString(); IInsertTextCommand <OperationContext> insertCommand = controller.CommandController.CreateInsertTextCommand(bufferPosition, text); insertCommand.UpdateTextPosition = DoTypes.All; controller.CommandController.Do(insertCommand, operationContext); // If we have a text position, we need to set it. if (operationContext.Results.HasValue) { displayContext.Caret.SetAndScrollToPosition( operationContext.Results.Value.TextPosition); } }
public static void Cut(EditorViewController controller) { // If we don't have anything selected, we don't do anything. IDisplayContext displayContext = controller.DisplayContext; TextRange selection = displayContext.Caret.Selection; if (selection.IsEmpty) { return; } // Copy the text first. Copy(controller); // Then delete the text. Since we know we have a selection, this // will only delete the selected text. DeleteLeft(controller); }
public static void RightWord(EditorViewController controller) { // Pull out some useful variables. IDisplayContext displayContext = controller.DisplayContext; LineBuffer buffer = displayContext.LineBuffer; LineBuffer lineBuffer = displayContext.LineBuffer; // Pull out the line and chracter positions from where we're starting. TextPosition position = displayContext.Caret.Position; LinePosition linePosition = position.LinePosition; int lineIndex = linePosition.GetLineIndex(buffer); string lineText = buffer.GetLineText(lineIndex); CharacterPosition wordPosition = CharacterPosition.Word; CharacterPosition characterPosition = position.CharacterPosition; int characterIndex = characterPosition.GetCharacterIndex(lineText); // If we are at the beginning of the line, we need to move to the // previous line. if (characterIndex == lineText.Length) { // If we are at the last line, we don't do anything. if (lineIndex == lineBuffer.LineCount - 1) { return; } // Move to the end of the previous line. linePosition = new LinePosition(lineIndex + 1); characterPosition = CharacterPosition.Begin; } else { // Move to the previous left word. int rightCharacterIndex = wordPosition.GetCharacterIndex( lineText, characterPosition, WordSearchDirection.Right); characterPosition = new CharacterPosition(rightCharacterIndex); } // Cause the text editor to redraw itself. var caretPosition = new TextPosition(linePosition, characterPosition); displayContext.ScrollToCaret(caretPosition); }