/// <summary> /// Find the ideal size to fit all the commands inside. /// </summary> /// <param name="states">Collection of additional state for commands.</param> /// <param name="details">Lookup interface for calculations.</param> /// <returns>Bounding rectangle covering all commands.</returns> public Rectangle FindIdealSize(CommandStateCollection states, ICommandDetails details) { // Peform layout of commands Rectangle rectLayout = InternalLayoutCommands(states, details, true); // Track total width or height required int total = 0; // Process all commands for (int i = 0; i < _states.Count; i++) { CommandState state = _states[i]; // Add the size it needs for drawing in direction total += WithFlowLength(state.DrawRect.Size); } // Modify the return rectangle with calculated total if (_details.Direction == LayoutDirection.Horizontal) { rectLayout.Width = total; } else { rectLayout.Height = total; } // Clear out any temporary working values ClearDown(); // Peform layout of commands return(rectLayout); }
private void InternalDraw(Graphics g, ICommandDetails details, Rectangle drawRect) { // Tell the control to draw itself in the correct state _command.Draw(g, details, drawRect, _state, true); }
/// <summary> /// Initializes a new instance of the CommandState class. /// </summary> /// <param name="details">Source used for obtaining command details.</param> /// <param name="command">Command to handle state for.</param> public CommandState(ICommandDetails details, CommandBase command) { // Default state _state = ItemState.Normal; _displayed = false; _drawRect = Rectangle.Empty; _command = command; _details = details; }
/// <summary> /// Perform sizing and positioning of commands. /// </summary> /// <param name="states">Collection of additional state for commands.</param> /// <param name="details">Lookup interface for calculations.</param> /// <returns>Bounding rectangle covering all commands.</returns> public Rectangle LayoutCommands(CommandStateCollection states, ICommandDetails details) { // Peform layout of commands Rectangle rectLayout = InternalLayoutCommands(states, details, false); // Clear out any temporary working values ClearDown(); return(rectLayout); }
/// <summary> /// Draw the command as a Separator. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="drawRect">Bounding rectangle for drawing command.</param> /// <param name="state">State of the command to be drawn.</param> /// <param name="topLevel">Drawing as a top level item.</param> public override void Draw(Graphics g, ICommandDetails details, Rectangle drawRect, ItemState state, bool topLevel) { // Use a helper method for perform drawing CommandDraw.DrawSeparatorCommand(g, details.Style, details.Direction, drawRect, details.SepDarkColor, details.SepLightColor); }
/// <summary> /// Draw the command as a Button. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="drawRect">Bounding rectangle for drawing command.</param> /// <param name="state">State of the command to be drawn.</param> /// <param name="topLevel">Drawing as a top level item.</param> public override void Draw(Graphics g, ICommandDetails details, Rectangle drawRect, ItemState state, bool topLevel) { string drawText; CommandImage drawImage; // Decide if the Text of the button should be drawn if (details.ImageAndText == ImageAndText.ImageOnly) { drawText = string.Empty; } else { drawText = Text; } // Decide if the Image of the button should be drawn if (details.ImageAndText == ImageAndText.TextOnly) { drawImage = CommandImage.Empty; } else { drawImage = CommandImage; } // Use the provided layout direction by default LayoutDirection direction = details.Direction; // Do we need to override for drawing? if (details.OnlyHorizontalText) { direction = LayoutDirection.Horizontal; } // Use a helper method to draw command appropriately CommandDraw.DrawButtonCommand(g, details.Style, direction, drawRect, state, Enabled, details.TextEdge, details.Font, details.TextColor, details.BaseColor, drawText, drawImage, null, details.TrackBaseColor1, details.TrackBaseColor2, details.TrackLightColor1, details.TrackLightColor2, details.TrackLightLightColor1, details.TrackLightLightColor2, details.TrackDarkColor, _buttonStyle, _pushed, false, false); }
private void Prepare(Graphics g, CommandStateCollection states, ICommandDetails details, bool findIdealSize) { // Cache useful information _states = states; _details = details; // Initialize simple working values _maximumTangent = 0; _finished = false; // If try to find ideal size then give it unlimited space if (findIdealSize) { _layoutRect = new Rectangle(0, 0, MAXIMUM, MAXIMUM); } else { _layoutRect = _details.LayoutRect; } // Starting position depends on orientation if (_details.Direction == LayoutDirection.Horizontal) { _leftSpace = _layoutRect.Left; } else { _leftSpace = _layoutRect.Top; } // Amount of free space to use depends on orientation _freeSpace = WithFlowLength(_layoutRect); // Ask each command for its requested raw size CalculateRawCommandSize(g); // Adjust size of button commands to reflect detail properties AdjustButtonSizes(); }
/// <summary> /// Calculate required drawing size for separator. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="topLevel">Drawing as a top level item.</param> /// <returns>Size of required area for command.</returns> public override Size CalculateDrawSize(Graphics g, ICommandDetails details, bool topLevel) { // Separator is the same size in both directions and should stretch to match the // actual required height (for horizontal direction) or width (for vertical direction). switch (details.Style) { case VisualStyle.Plain: return(new Size(SEPARATOR_CONSTANT_PLAIN, SEPARATOR_CONSTANT_PLAIN)); case VisualStyle.IDE: return(new Size(SEPARATOR_CONSTANT_IDE, SEPARATOR_CONSTANT_IDE)); case VisualStyle.IDE2005: return(new Size(SEPARATOR_CONSTANT_IDE2005, SEPARATOR_CONSTANT_IDE2005)); case VisualStyle.Office2003: return(new Size(SEPARATOR_CONSTANT_OFFICE2003, SEPARATOR_CONSTANT_OFFICE2003)); default: Debug.Assert(false); return(Size.Empty); } }
private Rectangle InternalLayoutCommands(CommandStateCollection states, ICommandDetails details, bool findIdealSize) { Rectangle returnRect = Rectangle.Empty; using (Graphics g = details.HostControl.CreateGraphics()) { // Prepare state for processing Prepare(g, states, details, findIdealSize); // Position the most important 'System' commands first, followed by // the less important 'Near' commands and lastly the 'Far' commands // which have the lowest priority of all. CalculateByPosition(g, Position.System, false); CalculateByPosition(g, Position.Near, true); CalculateByPosition(g, Position.Far, false); // Calculate the final positions depending on maximum values encountered CalculateFinalPositions(); returnRect = _layoutRect; // Calculate the actual area we have decided to use if (_details.Direction == LayoutDirection.Horizontal) { returnRect.Height = _maximumTangent; } else { returnRect.Width = _maximumTangent; } } return(returnRect); }
/// <summary> /// Calculate required drawing size for push button. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="topLevel">Drawing as a top level item.</param> /// <returns>Size of required area for command.</returns> public override Size CalculateDrawSize(Graphics g, ICommandDetails details, bool topLevel) { int width = 0; int height = 0; // The size of the button area is calculated as.... // // Size needed for image (the image is not rotated when shown vertically) // Size needed for the text (the text is rotated when shown vertically) // // Do we have an image that needs positioning? if ((Image != null) && (details.ImageAndText != ImageAndText.TextOnly)) { Size imageSize = ImageSpace(details.Style); width = imageSize.Width; height = imageSize.Height; // With an image we need an extra pixel gap to the left (IDE and Office2003 only) if ((details.Style == VisualStyle.IDE) || (details.Style == VisualStyle.IDE2005) || (details.Style == VisualStyle.Office2003)) { width += SPACE_LEFT_EXTRA; } } // Do we have any text to position? if ((Text.Length > 0) && (details.ImageAndText != ImageAndText.ImageOnly)) { // Get regular size of the text (horizontally) Size textSize = CommandDraw.TextSize(g, details.Font, Text); // Are we drawing the contents as if horizontal if ((details.Direction == LayoutDirection.Horizontal) || details.OnlyHorizontalText) { // Position the text drawn horizontal switch (details.TextEdge) { case TextEdge.Left: case TextEdge.Right: // Increase width by text width width += textSize.Width; // If we have an image as well then need a spacing gap if (Image != null) { width += SPACE_GAP_WIDTH; } // Make sure height is enough for text if (height < textSize.Height) { height = textSize.Height; } break; case TextEdge.Top: case TextEdge.Bottom: // Increase height by text height height += SPACE_HEIGHT + textSize.Height; // If we have an image as well then need a spacing gap if (Image != null) { height += SPACE_HEIGHT; } // Make sure width is enough for text if (width < textSize.Width) { width = textSize.Width; } break; } } else { // Position the text drawn vertical switch (details.TextEdge) { case TextEdge.Left: case TextEdge.Right: // Increase height text height height += textSize.Width; // If we have an image as well then need a spacing gap if (Image != null) { height += SPACE_GAP_WIDTH; } // Make sure width is enough for text if (width < textSize.Height) { width = textSize.Height; } break; case TextEdge.Top: case TextEdge.Bottom: // Increase height by text height width += textSize.Height; // If we have an image as well then need a spacing gap if (Image != null) { width += SPACE_HEIGHT; } // Make sure width is enough for text if (height < textSize.Width) { height = textSize.Width; } break; } } } // Calculate total area using borders and spacing gaps around inner size width += (BORDER_WIDTH * 2) + (SPACE_WIDTH * 2); height += (BORDER_HEIGHT * 2) + (SPACE_HEIGHT * 2); // The width and height are always the same no matter which direction we are in return(new Size(width, height)); }
/// <summary> /// Derived classes implement this to draw the command. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="drawRect">Bounding rectangle for drawing command.</param> /// <param name="state">State of the command to be drawn.</param> /// <param name="topLevel">Drawing as a top level item.</param> public abstract void Draw(Graphics g, ICommandDetails details, Rectangle drawRect, ItemState state, bool topLevel);
/// <summary> /// Derived classes implement this to return required drawing size for command. /// </summary> /// <param name="g">Graphics reference used in calculations.</param> /// <param name="details">Source details needed to perform calculation.</param> /// <param name="topLevel">Drawing as a top level item.</param> /// <returns>Size of required area for command.</returns> public abstract Size CalculateDrawSize(Graphics g, ICommandDetails details, bool topLevel);
private void ClearDown() { _states = null; _details = null; }