如何插入版权,商标,服务标记,等进入WPF文本框时,字体不支持的符号 [英] How to insert copyright, trademark, service mark, etc. into WPF textbox when font doesn't support symbols

查看:172
本文介绍了如何插入版权,商标,服务标记,等进入WPF文本框时,字体不支持的符号的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我们有一个显示包含各种企业符号文本的WPF应用程序;如商标,注册商标,版权和服务标志。

We have a WPF application that displays text containing the various corporate symbols; such as trademark, registered trademark, copyright, and service mark.

该数据库有一些领域,包括标准的企业符号。最初,该数据被标记如下:

The database has some fields that include the standard corporate symbols. Initially, the data was marked as follows:

示例公司(TM)或示例规划(SM)

我们可以很容易地改变占位符各自的Unicode等价物;实际上在大多数情况下

We can easily change the placeholders to their respective Unicode equivalents; and actually have in most cases.

我们的问题是,所使用的应用程序不支持的服务标记符号的字体(这仅仅是一个上标 SM )。机会是我们不能替换的字体或编辑它。

The problem we have is that the font used by the application doesn't support the Service Mark symbol (which is just a superscripted SM). Chances are we can not replace the font or edit it.

字段可以是一个简单的产品名称,并在最后的象征,或长的描述与符号包含0次或更多次。我们结合文本框或标签直接向视图模型和/或业务对象(通常通过的DataTemplates)。在应用程序中的所有数据是只读的。

The fields could be a simple product name with the symbol at the end, or a long description with a symbol contained 0 or more times. We bind TextBoxes or Labels directly to a ViewModel and/or the business object (usually through DataTemplates). All the data in the application is read-only.

因此,假设我们要通过代码(C#和WPF),我有哪些选择?解决这个

So, assuming we have to tackle this via code (in C# and WPF), what are my options?

推荐答案

编辑:我发现了一个不同的答案是,的TextBlock 也有一个内联集合,其中一个可以添加运行秒。 Anvaka的回答巧妙地利用附加属性为一种转换器。

I discovered in a different answer that the TextBlock also has an Inlines collection to which one can add Runs. Anvaka's answer ingeniously uses an attached property as a sort of converter.

我对如何处理这个一对夫妇的想法。只有一个会处理Word正确包装和处理字符使用不同的字体运行。

I had a couple ideas about how to approach this. Only one would handle word wrap correctly and handle character runs with different fonts.

使用 FlowDocumentScrollViewer 并绑定字符串它使用 ValueConverter 的字符串转换为一个的FlowDocument

Use a FlowDocumentScrollViewer and bind the string to it using a ValueConverter that converts the string to a FlowDocument.

<FlowDocumentScrollViewer
    HorizontalScrollBarVisibility="Hidden"
    VerticalScrollBarVisibility="Hidden"
    Document="{Binding MyString, Converter={StaticResource MyConverter}}" />

可以创建对转换器属性来设置常字体属性,不能设置在在 FlowDocumentScrollViewer ,并且必须在的FlowDocument 设置转换器造成的。你可能还需要为需要不同的字体(也可能是不同的大小)异常的子串一些字体属性。另一种选择是创建绑定 S于在的FlowDocument 对于其中的一些属性(的RelativeSource

You can create properties on the converter to set the regular Font properties, which can't be set on the FlowDocumentScrollViewer and has to be set on the FlowDocument that the converter creates. You'll probably also need some Font properties for the exception substrings that need a different Font (and possibly different size). Another option is to create Bindings on the FlowDocument for some of those properties (RelativeSource).

和这里是你如何创建一个的FlowDocument 中的代码:

And here's how you create a FlowDocument in code:

FlowDocument doc = new FlowDocument();
doc.FontFamily = new FontFamily( "Our Own Font" );
Paragraph par = new Paragraph();
doc.Blocks.Add( par );



然后,你需要输入字符串分割的特殊子,同时保持这些子完好无损。 。你必须推出自己的分路器和具有在变频器子的集合或者提供给该转换器

Then you'll need to split the incoming string on the special substrings while keeping those substrings intact. You'll have to roll your own splitter and have a collection of substrings in the converter or supplied to the converter.

添加一个正常的子段落:

Add a normal substring to the paragraph:

Run r = new Run( substring );
par.Inlines.Add( r );



添加一个特殊的子串用不同字体的段落:

Add a special substring to the paragraph with a different Font:

Run r = new Run( substring );
r.FontFamily = new FontFamily( "Arial" );
par.Inlines.Add( r );



以上只是小片段。我不知道你是怎么想办法分割字符串或遍历子,因为我不熟悉的数据,所以我也没有提供我拼凑只是为了看看我的想法会工作的方法。你也可以使用词典,以检测一个字符串,并在输出时使用的替代品,如检测(SM)和替换它

The above are just little snippets. I don't know how you want to approach splitting the string or iterating over the substrings since I'm not familiar with the data, so I didn't supply the method I slapped together just to see if my idea would work. You could also use a Dictionary in order to detect one substring and use a replacement in the output, such as detecting "(SM)" and replacing it with "℠".

让我知道如果您有任何疑问或有什么事我可以详细说明。

Let me know if you have any questions or if there's anything I can elaborate on.

(这是很好的,你说这是只读的。A 的RichTextBox 会不行,因为它的文件属性不是的DependencyProperty ,因此不能用<$ C $的目标C>绑定​​。虽然,人们可能能够使用模式= OneWayToSource 来扭转这种局面,实施 ConvertBack ,而不是转换

(It's good that you said it is read-only. A RichTextBox would not work because its Document property is not a DependencyProperty and therefore can't be the target of a Binding. Although, one might be able to use Mode=OneWayToSource to reverse it, implementing ConvertBack instead of Convert.)

我想你剩下的东西了(遍历字符串,并创造那些运行)是棘手的部分。

"I think what you left out (iterating over the string and creating those Runs) is the tricky part."

我确实是关于特殊子分割字符串非常简短。当我说,我不知道你将如何分割字符串,我不是说我不知道​​如何做到这一点在所有(我转述),但你会怎么想要的,我不知道来处理它。我以为这不会是你很难这部分弄清楚,因为这是我想有什么样的字符串处理问题的应聘者弄清楚。这一点,你会发现边缘情况之间的数据需要在如何处理它的变化。

I was indeed very brief about splitting the string on the special substrings. When I said, "I don't know how you'll split the string," I was not saying that I had no idea how to do it at all (I rephrased it), but that I had no idea how you would want to handle it. I assumed it would not be hard for you to figure that part out because it's the kind of string manipulation problem I would have potential hires figure out. That, and you may discover edge cases amongst your data that require changes in how you handle it.

我会使用的IndexOf()子字符串向你描述一个相对粗糙的版本()

因此,这里的问题中的非的问题:你有很多字符串(例如,公司名称(R),产品制造商(TM))包含0或多个特殊子。这些子很少,已知的,输入字符串需要分割成几个字符串,其中的特殊和非特殊子已经从对方(例如, {公司名称,隔离(R) ,产品制造商,(TM)} )。

So here's the problem-within-the-problem: You have many strings (e.g., "Company Name(R), makers of Product(TM)") that contain 0 or more special substrings. These substrings are few and known, and the input string needs to be split into several strings where the special and nonspecial substrings have been isolated from each other (e.g., {"Company Name", "(R)", ", makers of Product", "(TM)"}).

特殊子很少,已知的,所以你需要一个阵列的那些。你知道通过 .IndexOf的返回值()是否发现了一个字符串或没有。循环与已知的特殊子,你可以找到任何他们的第一个实例与指数相比,撇开子字符串的长度了。

The special substrings are few and known, so you need an array of those. You know by the return value of .IndexOf() whether it found a substring or not. Looping over the known special substrings, you can find the first instance of any of them with an index comparison, setting aside the length of the substring, too.

每次找到字符串最早的特殊子取值(如果有的话),你让衍生字符串 A C B 是特殊子, A C 是之前和之后。追加 A B 列表 C 将成为新的取值和你做一遍。除非你找到取值无特殊子,这是不是空的,在这种情况下,你只是追加它的整体。

Each time you find the earliest special substring in string S (if any), you make derived strings A, B, and C. B is the special substring, A and C are the before and after. Append A and B to a List and C becomes the new S and you do it again. Except when you find no special substrings in S and it isn't empty, in which case you just append it whole.

现在在列表每个奇数索引的字符串是一个特殊的子串。您可能要参考我的一个词典提及在这个答案的前部分用作查找添加运行 当你找到子是(SM)

Now every odd-indexed string in the List is a special substring. You may want to refer to my mention of a Dictionary in the previous portion of this answer for use as a lookup to add a Run of "℠" when the substring you found was "(SM)".

这篇关于如何插入版权,商标,服务标记,等进入WPF文本框时,字体不支持的符号的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆