在之前部落格裡的ArcGIS API for Silverlight 彈出框執行個體中,是通過點擊地圖要素,彈出框,但是由於沒有控制元素個數,只是通過顯示隱藏來進行的話,在滑鼠移入和移出操作中,會出現滑鼠移入的時候,總不能立刻彈出框,而是需要多次才行,使用者體驗較差,現在通過控制加入一個彈出框,移出時去除剛加入的彈出框,嚴格控制彈出框個數來實現。
核心代碼如下:
//滑鼠移入事件 graphic.MouseEnter += new MouseEventHandler(swz_graphic_MouseEnter); graphic.MouseLeave += new MouseEventHandler(swz_graphic_MouseLeave);void swz_graphic_MouseEnter(object sender, MouseEventArgs e){ Point p = e.GetPosition(LayoutRoot); p.X = p.X - 40; p.Y = p.Y - 165; //滑鼠左鍵,顯示ToolTip資訊 Graphic g = sender as Graphic; tip_Base.g_TipSW_LeftBottom = new TipSW_LeftBottom(this, p, g.Attributes["SWZMC"].ToString(), g.Attributes["SWZBM"].ToString());} void swz_graphic_MouseLeave(object sender, MouseEventArgs e){ tip_Base.g_TipSW_LeftBottom.closeWindow(this);}public partial class TipSW_LeftBottom : UserControl{ MainPage mp; string l_name; string l_swzbm; public TipSW_LeftBottom() { InitializeComponent(); } public TipSW_LeftBottom(MainPage mp, Point p, string name, string swzbm) { InitializeComponent(); this.mp = mp; this.l_name = name; this.l_swzbm = swzbm; //處理標題的間距問題 string tmp = name; StringBuilder sb = new StringBuilder(); for (int i = 0; i < tmp.Length; i++) { sb.Append(tmp[i] + " "); } this.title.Content = sb.ToString(); //綁定洪水預報的資料 getDataSoapClient client = new getDataSoapClient(); client.getHSYBInfoCompleted += new EventHandler<getHSYBInfoCompletedEventArgs>(client_getHSYBInfoCompleted); client.getHSYBInfoAsync(name.Trim()); getXQYJInfoSoapClient client2 = new getXQYJInfoSoapClient(); client2.GetAllSWZCompleted += new EventHandler<GetAllSWZCompletedEventArgs>(client_GetAllSWZCompleted); client2.GetAllSWZAsync(); this.Margin = new Thickness(p.X, p.Y, 0, 0); mp.LayoutRoot.Children.Add(this); } #region 通用方法,只需要更改Show,在執行個體化表單的時候,傳入不同的參數即可 private Point _location; private bool _isShowing; private Popup _popup; private Grid _grid; private Canvas _canvas; private FrameworkElement _content; //初始化並顯示彈出表單.公用方法在顯示功能表項目時調用 public void Show(Point location, string name,string swzbm) { this.l_name = name; this.l_swzbm = swzbm; if (_isShowing) throw new InvalidOperationException(); _isShowing = true; _location = location; ConstructPopup(this); _popup.IsOpen = true; //處理標題的間距問題 string tmp = name; StringBuilder sb = new StringBuilder(); for (int i = 0; i < tmp.Length; i++) { sb.Append(tmp[i] + " "); } this.title.Content = sb.ToString(); //綁定洪水預報的資料 getDataSoapClient client = new getDataSoapClient(); client.getHSYBInfoCompleted += new EventHandler<getHSYBInfoCompletedEventArgs>(client_getHSYBInfoCompleted); client.getHSYBInfoAsync(name.Trim()); //水位站資料 getXQYJInfoSoapClient client2 = new getXQYJInfoSoapClient(); client2.GetAllSWZCompleted += new EventHandler<GetAllSWZCompletedEventArgs>(client_GetAllSWZCompleted); client2.GetAllSWZAsync(); } public void Show(Point location) { if (_isShowing) throw new InvalidOperationException(); _isShowing = true; _location = location; ConstructPopup(this); _popup.IsOpen = true; } //關閉彈出表單 public void Close() { _isShowing = false; if (_popup != null) { _popup.IsOpen = false; } } //彈出框外面點擊則關閉該視窗 protected virtual void OnClickOutside() { Close(); } // 用Grid來布局,初始化彈出表單 //在Grid裡面添加一個Canvas,用來監測功能表項目外面的滑鼠點擊事件 private void ConstructPopup(FrameworkElement _element) { if (_popup != null) return; _popup = new Popup(); _grid = new Grid(); _popup.Child = _grid; _canvas = new Canvas(); _canvas.MouseLeftButtonDown += (sender, args) => { OnClickOutside(); }; _canvas.MouseRightButtonDown += (sender, args) => { args.Handled = true; OnClickOutside(); }; _canvas.Background = new SolidColorBrush(Colors.Transparent); _grid.Children.Add(_canvas); _content = _element; _content.HorizontalAlignment = HorizontalAlignment.Left; _content.VerticalAlignment = VerticalAlignment.Top; _content.Margin = new Thickness(_location.X, _location.Y, 0, 0); _grid.Children.Add(_content); UpdateSize(); } /// <summary> /// 更新大小 /// </summary> private void UpdateSize() { _grid.Width = Application.Current.Host.Content.ActualWidth; _grid.Height = Application.Current.Host.Content.ActualHeight; if (_canvas != null) { _canvas.Width = _grid.Width; _canvas.Height = _grid.Height; } } #endregion #region WebService 調用方法及關閉表單方法 void client_GetAllSWZCompleted(object sender, GetAllSWZCompletedEventArgs e) { try { ObservableCollection<RiverFall> lists = e.Result; foreach (RiverFall item in lists) { if (item.SWZBM == l_swzbm) { this.dt.Content = item.DTNow.ToString("yyyy年M月d日H時"); this.sw.Content = "水位:" + item.SW.ToString("N2") + "m"; } } } catch (Exception ex) { this.dt.Content = "沒有監測到該網站資料"; this.sw.Content = ""; } } void client_getHSYBInfoCompleted(object sender, getHSYBInfoCompletedEventArgs e) { try { IList<洪水預報> ret = e.Result; if (ret.Count > 0) { foreach (洪水預報 r in ret) { this.tbhsyb.Text = r.標題.Length > 9 ? r.標題.Substring(0, 7) + "..." : r.標題; this.tbhsyb.Foreground = new SolidColorBrush(Colors.Red); } } else { this.tbhsyb.Text = "暫無預報"; this.tbhsyb.Foreground = new SolidColorBrush(Colors.Black); } } catch { } } //用於移除剛加入的彈出框,在主表單滑鼠移出後,調用此方法 public void closeWindow(MainPage mp) { mp.LayoutRoot.Children.RemoveAt(mp.LayoutRoot.Children.Count - 1); } #endregion }
這裡代碼中仍然保留了原先的點擊彈出框的Show方法,可以根據需要調用Show方法或直接執行個體化帶參數的建構函式都可以。