c# wpf textbox spell-checking

C#Texbox Spell Checker Ver todas las palabras mayúsculas



wpf textbox (2)

Con el corrector ortográfico de cuadro de texto en WPF, no parece verificar la ortografía de las palabras que están en mayúscula. Entiendo que esto está diseñado para acrónimos y tal que no los etiquete a todos como errores ortográficos y es útil para eso. Sin embargo, en mi industria (Arquitectura e Ingeniería) hay muchas compañías que escriben sus notas usando todas las mayúsculas, por lo que básicamente hace que el corrector ortográfico sea inútil ...

¿Hay alguna manera de cambiar el corrector ortográfico para no ignorar las palabras en mayúscula?


Podrías simplemente toLowerCase() la cadena antes de ejecutarla a través del corrector ortográfico.


Ok, así que finalmente tuve tiempo de echar otro vistazo a esto y se me ocurrió una forma basada en la respuesta de Tom (aunque no es tan simple como hacerlo). Te advertiré que definitivamente es un truco ... Pero para cualquier otra persona que tenga problemas con esto parece funcionar. Esencialmente, la lógica es la siguiente:

  • Cree un cuadro de texto ''sombra'' que nunca se muestra y establezca su texto en la versión en minúscula del cuadro de texto principal y habilite la verificación ortográfica.
  • Busque en el cuadro de texto sombreado los errores de ortografía basados ​​en el código y obtenga la posición de inicio y la longitud de cualquier error de ortografía en el cuadro.
  • Encuentre la posición relativa de los índices de caracteres encontrados en el cuadro de texto principal.
  • Use una capa adorner para subrayar en rojo las palabras mal escritas.
  • Actualice el texto y vuelva a ejecutar lo anterior cada vez que cambie el texto o cambie el tamaño del cuadro.

Estaba un poco preocupado por el rendimiento, pero tengo bastantes cuadros de texto en mi aplicación y no he notado desaceleración alguna al usar esto. Aquí está el código:

En el controlador cargado de cuadro de texto:

//Create a shadow textbox to run spell check in - set text to the lower version of main text TextBox tbSpell = new TextBox(); tbSpell.Text = tb.Text.ToLower(); //Enable spelling on the shadow box if we have spell checking enabled tbSpell.SpellCheck.IsEnabled = tb.DataContext is KeynoteVM && (tb.DataContext as KeynoteVM).EnableSpelling; //Set the shadow as a tag to the main textbox so we have access to it directly tb.Tag = tbSpell; //Adde handlers for size change or text change as we may need to update adorners tb.SizeChanged += tb_SizeChanged; tb.TextChanged += tb_TextChanged;

Los manejadores de cambio de tamaño y texto simplemente llaman al método de actualización que se ve así:

//Remove existing adorners AdornerLayer lyr = AdornerLayer.GetAdornerLayer(tb); if (lyr != null) { Adorner[] ads = lyr.GetAdorners(tb); if (ads != null) { foreach (Adorner ad in lyr.GetAdorners(tb)) { lyr.Remove(ad); } } } //Get the shadow textbox from the tag property TextBox tbSpell = tb.Tag as TextBox; if (tbSpell == null || !tbSpell.SpellCheck.IsEnabled) { return; } //Make sure we have the latest text tbSpell.Text = tb.Text.ToLower(); //Loop to get all spelling errors starting at index 0 int indx = 0; while (true) { //Find the spelling error indx = tbSpell.GetNextSpellingErrorCharacterIndex(indx, LogicalDirection.Forward); if (indx > -1) { //Have a match, get the length of the error word int len = tbSpell.GetSpellingErrorLength(indx); //Get a rectangle describing the position of the error to use for drawing the underline Rect r = tb.GetRectFromCharacterIndex(indx); Rect rEnd = tb.GetRectFromCharacterIndex(indx + len); //Modify the rectangle width to the width of the word r.Width = rEnd.Right - r.Right; //Create an adorner for the word and set the ''draw location'' property to the rectangle AdornerSpell ad = new AdornerSpell(tb); ad.drawLocation = r; //Add the adorner to the textbox AdornerLayer.GetAdornerLayer(tb).Add(ad); //Increment the index to move past this word indx += len; } else { break; } }

Aquí está el código para la clase adornador que creé (simplemente subraya en rojo):

public class AdornerSpell : Adorner { public Rect drawLocation { get; set; } public AdornerSpell(UIElement adornedElement) : base(adornedElement) { } protected override void OnRender(System.Windows.Media.DrawingContext drawingContext) { drawingContext.DrawLine(new System.Windows.Media.Pen(new SolidColorBrush(Colors.Red), 1), drawLocation.BottomLeft, drawLocation.BottomRight); } }

Entonces, por supuesto, si usa el clic derecho para obtener sugerencias, tiene que modificar eso para obtener las sugerencias del cuadro de texto alternativo en lugar del habitual.

La única peculiaridad que he encontrado es que, como siempre está revisando la minúscula, identifica cosas como "yo" y las escribiré como errores ortográficos, ya que debería escribirse en mayúscula. Estoy seguro de que también hay una forma de evitarlo, pero aún no lo he intentado.

De todos modos, no es seguro, pero parece funcionar y no puedo encontrar nada mejor sin crear completamente un nuevo sistema de revisión ortográfica ... Todavía estoy abierto a otras sugerencias si alguien las tiene, pero al menos es factible.

Editar:

Me di cuenta de que en realidad podría reducir aún más las visitas al rendimiento diciéndole que actualice con un ''BeginInvoke'' en el despachador para ejecutarlo de manera asíncrona. Ahora el texto cambió y los métodos cambiados de tamaño se ven así:

Dispatcher.BeginInvoke(new Action(() => UpdateSpellingAdorners(sender as TextBox)));