我正在尝试动态设置TextBox控件中每个字符的间距(宽度)。我已经完成了很多阅读,我不相信这在普通的TextBox中是可能的。我对RichTextBox或任何其他可以解决此问题的控件持开放态度。
为了证明这是可能的,我打开了Word,我能够选择一个字符并调整其间距并“拉伸”它。我希望在我的.NET应用程序中实现相同的行为。
是否有代码示例或控件显示如何实现这一目标?
答案 0 :(得分:4)
如果您接受链接到某些WPF的程序集(WindowsBase和PresentationCore),您可以编写自定义TextBox并在WinForms实现中使用它。 WPF有一些不错的类,如GlyphTypeFace(允许加载字体文件和从字形构建几何),以及GlyphRun(允许绘制字形列表 - 文本)。但我们不能在这里使用GlyphRun因为我们希望能够修改某些字形的几何形状。所以我们需要手动获取几何并转换它们。
以下是一个例子:
Winforms代码:
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
// ElementHost allows Winforms to host WPF visual components
ElementHost host = new ElementHost();
host.Dock = DockStyle.Fill;
host.Child = new MyTextBox();
Controls.Add(host);
}
自定义TextBox代码:
public class MyTextBox: UIElement
{
protected override void OnRender(DrawingContext drawingContext)
{
const string sampleText = "Sample String";
const int sampleEmSize = 30;
GlyphTypeface typeFace = new GlyphTypeface(new Uri("file:///C:/WINDOWS/FONTS/segoeui.ttf"));
GeometryGroup group = new GeometryGroup();
group.FillRule = FillRule.Nonzero;
double x = 0;
double y = sampleEmSize;
for (int i = 0; i < sampleText.Length; i++)
{
ushort glyphIndex = typeFace.CharacterToGlyphMap[sampleText[i]];
Geometry glyphGeometry = typeFace.GetGlyphOutline(glyphIndex, sampleEmSize, sampleEmSize).Clone();
TransformGroup glyphTransform = new TransformGroup();
if (sampleText[i] == 'm') // this is a sample, we just change the 'm' characte
{
const double factor = 2;
glyphTransform.Children.Add(new ScaleTransform(factor, 1));
glyphTransform.Children.Add(new TranslateTransform(x, y));
x += factor * typeFace.AdvanceWidths[glyphIndex] * sampleEmSize;
}
else
{
glyphTransform.Children.Add(new TranslateTransform(x, y));
x += typeFace.AdvanceWidths[glyphIndex] * sampleEmSize;
}
glyphGeometry.Transform = glyphTransform;
group.Children.Add(glyphGeometry);
}
drawingContext.DrawGeometry(Brushes.Black, null, group);
}
}
这是WinForms上的结果:
当然,如果你想支持编辑,还有一些工作要做,但这可能会让你开始。
答案 1 :(得分:0)
供您参考,我编写了这段代码,可以让你更改你输入RichTextBox的每个字符的字体,fontstyle。
public int a = 0;
private void richTextBox1_TextChanged(object sender, EventArgs e)
{
if (a == 0)
{
richTextBox1.SelectionFont = new Font(RichTextBox.DefaultFont, FontStyle.Bold);
a = 1;
}
else if (a == 1)
{
richTextBox1.SelectionFont = new Font("Georgia",13, FontStyle.Bold);
a = 2;
}
else if (a == 2)
{
richTextBox1.SelectionFont = new Font("Impact", 11, FontStyle.Italic);
a = 0;
}
}
如果这有助于您,请告诉我。
答案 2 :(得分:0)
您可以查看WinForms的Telerik控件。我知道他们非常重视风格元素。