/// <summary> /// Makes render object representing a grid cell. That render object /// may be inserted into the corresponding RenderTable's cell, or /// for tree grids, into a RenderArea that combines the cell with tree glyphs. /// </summary> /// <param name="row">Grid row index.</param> /// <param name="col">Grid column index.</param> /// <param name="cellStyle">Cell style. May be modified by owner-drawn cells.</param> /// <param name="text">The cell text.</param> /// <returns>The render object representing the cell. /// The type of object varies depending on the cell's content - it can be /// a RenderText, a RenderImage, or a RenderArea containing both. /// </returns> private RenderObject MakeCellRO(int row, int col, ref CellStyle cellStyle, out string text) { Image image; CheckEnum chk; text = _grid.GetDataDisplay(row, col, out image, out chk); // special treatment of bool columns - suppress text if a checkbox is drawn: if (cellStyle.DataType == typeof(bool) && chk != CheckEnum.None) { text = null; } // handle owner-drawn cells: if (_grid.DrawMode == DrawModeEnum.OwnerDraw && _grid2 != null) { // note: the next call may modify cell's style, text and image while returning null. RenderObject ro = _grid2.MakeOwnerDrawCellRO(row, col, ref cellStyle, ref text, ref image); if (ro != null) { return(ro); } // else process as regular (non-ownerdraw) cell; taking into consideration // the possibly modified cell style, text and image. } bool overlay = false; bool hasImage = image != null || chk != CheckEnum.None; switch (cellStyle.Display) { case DisplayEnum.ImageOnly: text = null; break; case DisplayEnum.None: text = null; hasImage = false; break; case DisplayEnum.Overlay: overlay = true; break; case DisplayEnum.Stack: break; case DisplayEnum.TextOnly: hasImage = false; break; default: Debug.Assert(false); break; } if (cellStyle.ImageAlign == ImageAlignEnum.Hide) { hasImage = false; } if (string.IsNullOrEmpty(text) && !hasImage) { return(null); } else if (!hasImage) { return(MakeTextRO(text, null)); } else if (string.IsNullOrEmpty(text)) { return(MakeImageRO(image, chk, null)); } else { RenderObject rimg = MakeImageRO(image, chk, "img"); RenderObject rtxt = MakeTextRO(text, "txt"); ImageOn ion = AlignImage(rimg, cellStyle, overlay); AlignText(rtxt, GetTextAlign(cellStyle, cellStyle.DataType, text), ion); RenderArea ra = new RenderArea(); ra.Stacking = StackingRulesEnum.BlockLeftToRight; ra.Children.Add(rimg); ra.Children.Add(rtxt); if (ion == ImageOn.Left || ion == ImageOn.Right) { ra.Width = "img.width + txt.width"; } else if (ion == ImageOn.Top || ion == ImageOn.Bottom) { ra.Height = "img.height + txt.height"; } else { ra.Width = Unit.Auto; ra.Height = Unit.Auto; } return(ra); } }
/// <summary> /// Used to position text within the cell relative to image. /// This method assumes that the cell (represented by a RenderArea) contains /// both image and text, and that the image (RenderImage) is the first child /// within the render area (referenced by "prev" in position strings). /// </summary> /// <param name="rtxt"></param> /// <param name="ta"></param> /// <param name="ion"></param> private void AlignText(RenderObject rtxt, TextAlignEnum ta, ImageOn ion) { switch (ta) { case TextAlignEnum.LeftTop: rtxt.X = ion == ImageOn.Left ? "prev.right" : "0"; rtxt.Y = ion == ImageOn.Top ? "prev.bottom" : "0"; break; case TextAlignEnum.LeftCenter: rtxt.X = ion == ImageOn.Left ? "prev.right" : "0"; rtxt.Y = ion == ImageOn.Top ? "prev.bottom + (parent.height - prev.height - height) / 2" : (ion == ImageOn.Bottom ? "(parent.height - prev.height - height) / 2" : "(parent.height - height) / 2"); break; case TextAlignEnum.LeftBottom: rtxt.X = ion == ImageOn.Left ? "prev.right" : "0"; rtxt.Y = ion == ImageOn.Bottom ? "prev.top - height" : "parent.height - height"; break; case TextAlignEnum.CenterTop: rtxt.X = ion == ImageOn.Left ? "prev.right + (parent.width - prev.width - width) / 2" : (ion == ImageOn.Right ? "(parent.width - prev.width - width) / 2" : "(parent.width - width) / 2"); rtxt.Y = ion == ImageOn.Top ? "prev.bottom" : "0"; break; case TextAlignEnum.CenterCenter: rtxt.X = ion == ImageOn.Left ? "prev.right + (parent.width - prev.width - width) / 2" : (ion == ImageOn.Right ? "(parent.width - prev.width - width) / 2" : "(parent.width - width) / 2"); rtxt.Y = ion == ImageOn.Top ? "prev.bottom + (parent.height - prev.height - height) / 2" : (ion == ImageOn.Bottom ? "(parent.height - prev.height - height) / 2" : "(parent.height - height) / 2"); break; case TextAlignEnum.CenterBottom: rtxt.X = ion == ImageOn.Left ? "prev.right + (parent.width - prev.width - width) / 2" : (ion == ImageOn.Right ? "(parent.width - prev.width - width) / 2" : "(parent.width - width) / 2"); rtxt.Y = ion == ImageOn.Bottom ? "prev.top - height" : "parent.height - height"; break; case TextAlignEnum.RightTop: rtxt.X = ion == ImageOn.Right ? "prev.left - width" : "parent.width - width"; rtxt.Y = ion == ImageOn.Top ? "prev.bottom" : "0"; break; case TextAlignEnum.RightCenter: rtxt.X = ion == ImageOn.Right ? "prev.left - width" : "parent.width - width"; rtxt.Y = ion == ImageOn.Top ? "prev.bottom + (parent.height - prev.height - height) / 2" : (ion == ImageOn.Bottom ? "(parent.height - prev.height - height) / 2" : "(parent.height - height) / 2"); break; case TextAlignEnum.RightBottom: rtxt.X = ion == ImageOn.Right ? "prev.left - width" : "parent.width - width"; rtxt.Y = ion == ImageOn.Bottom ? "prev.top - height" : "parent.height - height"; break; default: // "general" alignments should not get here Debug.Assert(false); break; } }