siliverlight windowless=true 模式下禁止输入中文

     微软官网说明:https://msdn.microsoft.com/zh-cn/library/cc838156(VS.95).aspx

让silverlight在windowless=ture的条件下输入中文。大家都知道,silverligt2.0 和最新的3.0再windowless=true的条件下都无法输入中文,那么我们就必须采用一种迂回的方式解决。

  有以下几种方式可以考虑:

  1、在代码执行过程中动态改变windowless 属性。最初的想法是党textbox获取焦点的时候,让windowless =flase,失去焦点的时候在还原回去 。很不幸,windowless 无法动态更改(只读属性)。

  2、用一个html的input元素来充当输入设备,漂浮在一个假的输入框上。经过我的尝试,效果很不错。足以以假乱真。

缺点是必须在宿主html页面上加两个css样式。我也不知道为什么sl动态生成的有些样式不起作用,只能从从html页面加载才可以。

  按照第二条想法,我封装了一个输入控件,在自己的项目中用,感觉还是可以解决问题。当然还是希望微软在日后把这个不支持输入中文的Bug修复。

  为了支持windowless=false,在程序中判断该属性,来决定是用内置的textbox作为输入设备还是使用input作为输入设备。

  截了两张图:

   输入的时候:

   显示的时候:

   实现代码如下:

  cs:

  1 using System;
  2 using System.Collections.Generic;
  3 using System.Linq;
  4 using System.Net;
  5 using System.Windows;
  6 using System.Windows.Controls;
  7 using System.Windows.Documents;
  8 using System.Windows.Input;
  9 using System.Windows.Media;
 10 using System.Windows.Media.Animation;
 11 using System.Windows.Shapes;
 12 using System.Windows.Browser;
 13 
 14 namespace Sl.Input
 15 {   
 16     /// <summary>
 17     /// 使用的时候请在sl宿主页面加入样式
 18     /// .inputcss
 19     /// {
 20     ///     border-collapse: collapse;
 21     ///     border: solid 0px Transparent; background-color: Transparent;
 22             
 23     /// }
 24     /// .divInputcss
 25     /// {
 26         
 27     ///     border: solid 0px Transparent; background-color:Transparent;
 28     ///      position: absolute; display: none; z-index:1000;
 29             
 30     /// }
 31     /// </summary>
 32     public partial class SLInput : UserControl
 33     {
 34         HtmlElement divIndicatorName;
 35         HtmlElement txtIndicatorNameElements;
 36         public delegate void KeyDownHandel(object sender, string keyCode);
 37         public event KeyDownHandel KeyDownHandelEvent;
 38         public SLInput()
 39         {
 40             InitializeComponent();
 41             System.Windows.Interop.SilverlightHost host = Application.Current.Host;
 42             System.Windows.Interop.Settings setting = host.Settings;
 43             bool isWindowless = setting.Windowless;
 44             
 45             if (isWindowless == true)
 46             {
 47                 CreateHtmlElement();
 48                 this.SizeChanged += new SizeChangedEventHandler(EsmsInput_SizeChanged);
 49                 this.txtBox.Visibility = Visibility.Collapsed;
 50                 this.txtIndicatorName.Visibility = Visibility.Visible;
 51             }
 52         }
 53         /// <summary>
 54         /// 当这个控件大小发生了变化,需要重新调整input的大小
 55         /// </summary>
 56         void EsmsInput_SizeChanged(object sender, SizeChangedEventArgs e)
 57         {
 58             divIndicatorName.SetStyleAttribute("width", e.NewSize.Width.ToString() + "px");
 59             divIndicatorName.SetStyleAttribute("heght", e.NewSize.Height.ToString() + "px");
 60             txtIndicatorNameElements.SetStyleAttribute("width", e.NewSize.Width.ToString() + "px");
 61             txtIndicatorNameElements.SetStyleAttribute("heght", e.NewSize.Height.ToString() + "px");
 62         }
 63         /// <summary>
 64         /// 创建一个input 元素作为输入设备
 65         /// </summary>
 66         void CreateHtmlElement()
 67         {
 68             divIndicatorName = HtmlPage.Document.CreateElement("div");
 69             txtIndicatorNameElements = HtmlPage.Document.CreateElement("input");
 70             divIndicatorName.AppendChild(txtIndicatorNameElements);
 71             divIndicatorName.SetStyleAttribute("display", "none");
 72             divIndicatorName.SetStyleAttribute("position", "absolute");
 73             divIndicatorName.SetStyleAttribute("z-index", "10000");
 74             divIndicatorName.SetStyleAttribute("left", string.Format("{0}px", 0));
 75             divIndicatorName.SetStyleAttribute("top", string.Format("{0}px", 0));
 76             //这个样式必须放在html中,动态生成的样式不起作用,原因不明
 77             divIndicatorName.CssClass = "divInputcss";
 78             txtIndicatorNameElements.SetStyleAttribute("background-color", "Transparent");
 79             //这个样式必须放在html中,动态生成的样式不起作用,原因不明
 80             txtIndicatorNameElements.CssClass = "inputcss";
 81             HtmlPage.Document.Body.AppendChild(divIndicatorName);
 82             txtIndicatorNameElements.AttachEvent("onblur", new EventHandler(onLostFocus));
 83             //注册一个keydown事件用于托管代码中调用
 84             txtIndicatorNameElements.AttachEvent("onkeydown", new EventHandler(onExecuteQueryByonKeyDown));
 85             //这是一个用border画的虚假的输入框,当它被点击的时候,显示input元素,并定位到这个border上面
 86             this.bdInputName.MouseLeftButtonDown += new MouseButtonEventHandler(bdInputName_MouseLeftButtonDown);
 87         }
 88 
 89         private void onLostFocus(object sender, EventArgs e)
 90         {
 91             hideHtmlElementByResize(null, null);
 92         }
 93         private void onExecuteQueryByonKeyDown(object sender, EventArgs e)
 94         {
 95             if (KeyDownHandelEvent != null)
 96             {
 97                 string keyCode = HtmlPage.Window.Eval("event.keyCode").ToString();
 98                 KeyDownHandelEvent(this, keyCode);
 99             }
100         }
101         private void hideHtmlElementByResize(object sender, EventArgs e)
102         {
103             divIndicatorName.SetStyleAttribute("display", "none");
104             divIndicatorName.SetStyleAttribute("left", string.Format("{0}px", 0));
105             divIndicatorName.SetStyleAttribute("top", string.Format("{0}px", 0));
106             this.txtIndicatorName.Text = txtIndicatorNameElements.GetAttribute("value");
107             this.txtIndicatorName.Opacity = 1;
108             Application.Current.Host.Content.Resized -= new EventHandler(hideHtmlElementByResize);
109         }
110         void bdInputName_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
111         {
112             Point posRoot = e.GetPosition(null);
113             Point posRela = e.GetPosition(this.bdInputName);
114             double left = posRoot.X - posRela.X + 2;
115             double top = posRoot.Y - posRela.Y + 2;
116             divIndicatorName.SetStyleAttribute("display", "block");
117             divIndicatorName.SetStyleAttribute("left", string.Format("{0}px", left));
118             divIndicatorName.SetStyleAttribute("top", string.Format("{0}px", top));
119             divIndicatorName.SetStyleAttribute("position", "absolute");
120             txtIndicatorNameElements.SetAttribute("value", this.txtIndicatorName.Text);
121             txtIndicatorNameElements.Focus();
122             this.txtIndicatorName.Opacity = 0;
123             Application.Current.Host.Content.Resized += new EventHandler(hideHtmlElementByResize);
124         }
125         public double EsmsWidth
126         {
127             set
128             {
129                 this.bdInputName.Width = value;
130                 EsmsInputWidth = value;
131             }
132             get
133             {
134                 return this.bdInputName.Width;
135             }
136         }
137         public double EsmsHeight
138         {
139             set
140             {
141                 this.bdInputName.Height = value;
142                 EsmsInputHeight = value;
143             }
144             get
145             {
146                 return this.bdInputName.Height;
147             }
148         }
149         public double EsmsInputWidth
150         {
151             set
152             {
153                 if (this.txtIndicatorNameElements != null)
154                 {
155                     this.txtIndicatorNameElements.SetStyleAttribute("width", (value - 4).ToString());
156                     this.divIndicatorName.SetStyleAttribute("width", (value - 4).ToString());
157                     this.txtIndicatorName.Width = value;
158                 }
159             }
160             get
161             {
162                 return this.bdInputName.Width;
163             }
164         }
165         public double EsmsInputHeight
166         {
167             set
168             {
169                 if (this.txtIndicatorNameElements != null)
170                 {
171                     this.txtIndicatorNameElements.SetStyleAttribute("height", (value - 4).ToString());
172                     this.divIndicatorName.SetStyleAttribute("height", (value - 4).ToString());
173                 }
174             }
175             get
176             {
177                 return this.bdInputName.Height;
178             }
179         }
180         public string Text
181         {
182             get
183             {
184                 if (txtIndicatorNameElements != null)
185                 {
186                     this.txtIndicatorName.Text = txtIndicatorNameElements.GetAttribute("value");
187                 }
188                 return this.txtIndicatorName.Text;
189             }
190             set
191             {
192                 this.txtIndicatorName.Text = value;
193                 if (txtIndicatorNameElements != null)
194                 {
195                     txtIndicatorNameElements.SetAttribute("value", value ?? "");
196                 }
197             }
198         }
199     }
200 }

xaml:

 1 <UserControl x:Class="Sl.Input.SLInput"
 2     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
 3     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
 4     <Grid x:Name="LayoutRoot">
 5         <Border MinWidth="50" MinHeight="22" Grid.Column="1" BorderThickness="1,1,1,1" CornerRadius="2,2,2,2" x:Name="bdInputName" ToolTipService.ToolTip="模糊查询" BorderBrush="#FF005D93">
 6             <Border.Background>
 7                 <LinearGradientBrush EndPoint="0.5,1" StartPoint="0.5,0">
 8                     <GradientStop Color="#FFEFFAFE"/>
 9                     <GradientStop Color="#FFD6F0FA" Offset="1"/>
10                 </LinearGradientBrush>
11                 
12             </Border.Background>
13             <Grid>
14             <TextBox x:Name="txtBox" Visibility="Visible"></TextBox>
15             <TextBlock VerticalAlignment="Center" HorizontalAlignment="Left" Height="Auto" Margin="2" x:Name="txtIndicatorName" Text="" Width="Auto" TextWrapping="NoWrap" FontFamily="MS Reference Sans Serif" Visibility="Collapsed">
16             
17             </TextBlock>
18                 </Grid>
19         </Border>
20     </Grid>
21 </UserControl>

引用代码:

1 <userControls:SLInput x:Name="txt" ></userControls:SLInput>

源文链接:http://blog.csdn.net/swqqcs/article/details/12233611

posted @ 2015-10-14 15:24  wangping01  阅读(405)  评论(0编辑  收藏  举报