介紹
重新想象 Windows 8 Store Apps 之 WebView
演示 WebView 的基本應用
演示 WebView 如何與 JavaScript 交互
通過 Share Contract 分享 WebView 中的內容
如何全屏 WebView
示例
1、WebView 的基本應用
WebView/Demo.xaml
<Page x:Class="XamlDemo.Controls.WebView.Demo" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:XamlDemo.Controls.WebView" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Margin="120 0 0 0"> <Button Name="btnNavigateUrl" Content="導航到指定的 url" Click="btnNavigateUrl_Click_1" /> <Button Name="btnShowHtml" Content="解析指定的 html 字符串" Click="btnShowHtml_Click_1" Margin="0 10 0 0" /> <Button Name="btnFullScreen" Content="演示當 WebView 全屏時如何操作當前頁(WebView 會遮擋所有元素)" Click="btnFullScreen_Click_1" Margin="0 10 0 0" /> <WebView Name="webView" Width="400" Height="300" HorizontalAlignment="Left" Margin="0 10 0 0" /> </StackPanel> </Grid> </Page>
WebView/Demo.xaml.cs
/* * WebView - 內嵌浏覽器 * Source - 導航到指定的 url * Navigate() - 導航到指定的 url * NavigateToString() - 解析指定的 html 字符串 * LoadCompleted - 在 DOM 加載完成後所觸發的事件 * NavigationFailed - 導航發生錯誤時觸發的事件(事件參數:WebViewNavigationFailedEventArgs) * * WebViewNavigationFailedEventArgs * Uri - 嘗試導航到的 Uri * WebErrorStatus - 錯誤狀態(Windows.Web.WebErrorStatus 枚舉) */ using System; using Windows.UI.Popups; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; namespace XamlDemo.Controls.WebView { public sealed partial class Demo : Page { public Demo() { this.InitializeComponent(); } private void btnNavigateUrl_Click_1(object sender, RoutedEventArgs e) { // 導航到指定的 url webView.Navigate(new Uri("http://webabcd.cnblogs.com/", UriKind.Absolute)); // webView.Source = new Uri("http://webabcd.cnblogs.com/", UriKind.Absolute); // 導航失敗時 webView.NavigationFailed += webView_NavigationFailed; } async void webView_NavigationFailed(object sender, WebViewNavigationFailedEventArgs e) { await new MessageDialog(e.WebErrorStatus.ToString()).ShowAsync(); } private void btnShowHtml_Click_1(object sender, RoutedEventArgs e) { // 解析指定的 html 字符串 webView.NavigateToString("<html><body>I am webabcd</body></html>"); } private void btnFullScreen_Click_1(object sender, RoutedEventArgs e) { var root = Window.Current.Content as Windows.UI.Xaml.Controls.Frame; root.Navigate(typeof(XamlDemo.Controls.WebView.FullScreen)); } } }
2、WebView 如何與 JavaScript 交互
WebView/Interact.xaml
<Page x:Class="XamlDemo.Controls.WebView.Interact" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:XamlDemo.Controls.WebView" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Margin="120 0 0 0"> <Button Name="btnInvokeJavaScript" Content="app 調用 WebView 加載內容中的 JavaScript 腳本" Click="btnInvokeJavaScript_Click_1" /> <Button Name="btnAccessDOM" Content="通過 eval 訪問 DOM" Click="btnAccessDOM_Click_1" Margin="0 10 0 0" /> <WebView Name="webView" Width="400" Height="300" Source="http://localhost:39629/WebViewInteract.html" HorizontalAlignment="Left" Margin="0 10 0 0" /> </StackPanel> </Grid> </Page>
WebView/Interact.xaml.cs
/* * 演示 app 如何與 WebView 中的 JavaScript 進行交互 * * WebView - 內嵌浏覽器 * InvokeScript() - 調用 JavaScript 中的指定函數,並返回執行結果 * ScriptNotify - 當接收到從 JavaScript 發過來的數據時所觸發的事件(事件參數: NotifyEventArgs) * AllowedScriptNotifyUris - 允許觸發 ScriptNotify 事件的 uri 列表 * * NotifyEventArgs * Value - js 傳遞給 app 的數據 * * * 注:本例通過加載 WebServer 項目下的 WebViewInteract.html 來演示 app 與 js 的交互 */ using System; using System.Collections.Generic; using Windows.UI.Popups; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows.UI.Xaml.Navigation; namespace XamlDemo.Controls.WebView { public sealed partial class Interact : Page { public Interact() { this.InitializeComponent(); // 指定允許觸發 ScriptNotify 事件的 uri 列表(如果 uri 是目錄而不是文件,則此目錄下所有文件都可以觸發 ScriptNotify 事件) List<Uri> allowedUris = new List<Uri>(); allowedUris.Add(new Uri("http://localhost:39629/")); webView.AllowedScriptNotifyUris = allowedUris; webView.ScriptNotify += webView_ScriptNotify; } async void webView_ScriptNotify(object sender, NotifyEventArgs e) { // 獲取 js 傳遞過來的數據(js 端通向 app 傳遞數據的方法:window.external.notify('js to app');) await new MessageDialog(e.Value).ShowAsync(); } // app 調用 js private async void btnInvokeJavaScript_Click_1(object sender, RoutedEventArgs e) { string[] arguments = { "webabcd" }; // 調用 js 方法:sayHelloToJs('webabcd'); 並返回結果 string result = webView.InvokeScript("sayHelloToJs", arguments); await new MessageDialog(result).ShowAsync(); } // 通過 eval 方式訪問 DOM private async void btnAccessDOM_Click_1(object sender, RoutedEventArgs e) { // 獲取 document.title 的值 string[] arguments = { "document.title" }; string result = webView.InvokeScript("eval", arguments); await new MessageDialog(result).ShowAsync(); } } }
3、通過 Share Contract 分享 WebView 中的內容
WebView/Share.xaml
<Page x:Class="XamlDemo.Controls.WebView.Share" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:XamlDemo.Controls.WebView" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Grid Background="Transparent"> <StackPanel Margin="120 0 0 0"> <Button Name="btnShare" Content="通過 Share Contract 分享 WebView 中的被選中的文本內容" Click="btnShare_Click_1" /> <WebView Name="webView" Width="400" Height="300" Source="http://webabcd.cnblogs.com/" HorizontalAlignment="Left" Margin="0 10 0 0" /> </StackPanel> </Grid> </Page>
WebView/Share.xaml.cs
/* * 演示如何通過 Share Contract 分享 WebView 中的內容(復制到剪切板也是同理) * * WebView - 內嵌浏覽器 * DataTransferPackage - 返回 DataPackage 對象 */ using Windows.ApplicationModel.DataTransfer; using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; namespace XamlDemo.Controls.WebView { public sealed partial class Share : Page { private DataTransferManager _dataTransferManager; public Share() { this.InitializeComponent(); } private void btnShare_Click_1(object sender, RoutedEventArgs e) { _dataTransferManager = DataTransferManager.GetForCurrentView(); _dataTransferManager.DataRequested += _dataTransferManager_DataRequested; DataTransferManager.ShowShareUI(); } // 分享 WebView 中的被選中的文本內容 void _dataTransferManager_DataRequested(DataTransferManager sender, DataRequestedEventArgs args) { DataRequest request = args.Request; DataPackage dataPackage = webView.DataTransferPackage; DataPackageView dataPackageView = dataPackage.GetView(); // 如果用戶選擇了一段內容,則通過 WebView.DataTransferPackage 獲取到的數據裡就會有StandardDataFormats.Text 格式的內容,此內容就是用戶所選中的內容 if (dataPackageView.Contains(StandardDataFormats.Text)) { dataPackage.Properties.Title = "Title"; dataPackage.Properties.Description = "Description"; request.Data = dataPackage; } else { request.FailWithDisplayText("沒有選中任何內容"); } _dataTransferManager.DataRequested -= _dataTransferManager_DataRequested; } } }
4、全屏 WebView 時需要注意哪些
WebView/FullScreen.xaml
<Page x:Class="XamlDemo.Controls.WebView.FullScreen" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:XamlDemo.Controls.WebView" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" mc:Ignorable="d"> <Page.Resources> <Storyboard x:Name="sbOpenAppBar"> <DoubleAnimation x:Name="aniTranslateYOpen" Storyboard.TargetName="webView" Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Duration="00:00:00.367"> <DoubleAnimation.EasingFunction> <ExponentialEase EasingMode="EaseOut"/> </DoubleAnimation.EasingFunction> </DoubleAnimation> </Storyboard> <Storyboard x:Name="sbCloseAppBar"> <DoubleAnimation x:Name="aniTranslateYClose" Storyboard.TargetName="webView" Storyboard.TargetProperty="(UIElement.RenderTransform).(CompositeTransform.TranslateY)" Duration="00:00:00.367"> <DoubleAnimation.EasingFunction> <ExponentialEase EasingMode="EaseOut"/> </DoubleAnimation.EasingFunction> </DoubleAnimation> </Storyboard> </Page.Resources> <Page.BottomAppBar> <AppBar x:Name="appBar"> <StackPanel Orientation="Horizontal"> <Button x:Name="btnHome" Style="{StaticResource HomeAppBarButtonStyle}" Click="btnHome_Click_1" /> </StackPanel> </AppBar> </Page.BottomAppBar> <Grid Background="Transparent"> <WebView Name="webView" Source="http://webabcd.cnblogs.com/"> <WebView.RenderTransform> <CompositeTransform/> </WebView.RenderTransform> </WebView> </Grid> </Page>
WebView/FullScreen.xaml.cs
/* * 由於 WebView 控件上不允許顯示其他任何元素,那麼當 WebView 全屏時如何操作當前頁呢? * 可以考慮通過 AppBar 操作當前頁面,但是 AppBar 也會被 WebView 擋住,所以我們要做的是當 AppBar 顯示後,減小 WebView 的高度 * * 注:WebViewBrush 上是可以顯示其他元素的 */ using Windows.UI.Xaml; using Windows.UI.Xaml.Controls; using Windows.UI.Xaml.Navigation; namespace XamlDemo.Controls.WebView { public sealed partial class FullScreen : Page { public FullScreen() { this.InitializeComponent(); } protected override void OnNavigatedTo(NavigationEventArgs e) { appBar.Opened += appBar_Opened; appBar.Closed += appBar_Closed; } protected override void OnNavigatedFrom(NavigationEventArgs e) { appBar.Opened -= appBar_Opened; appBar.Closed -= appBar_Closed; } // 顯示 BottomAppBar,減小 WebView 的高度,使其不會遮擋 BottomAppBar void appBar_Opened(object sender, object e) { // 強制更新布局,這樣可以獲取到 WebView 和 BottomAppBar 的最新的真實高度 this.UpdateLayout(); double appBarHeight = appBar.ActualHeight; webView.Height = webView.ActualHeight - appBarHeight; // WebView 的高度減小後會居中顯示,此方法用於將 WebView 的頂端和屏幕的頂端對齊,同時來個動畫效果 aniTranslateYOpen.To = -appBarHeight / 2.0; sbOpenAppBar.Begin(); } // appBar_Opened 的逆運算,不解釋 void appBar_Closed(object sender, object e) { this.UpdateLayout(); double appBarHeight = appBar.ActualHeight; webView.Height = webView.ActualHeight + appBarHeight; aniTranslateYOpen.To = appBarHeight / 2.0; sbCloseAppBar.Begin(); } // 導航到首頁 private void btnHome_Click_1(object sender, RoutedEventArgs e) { var root = Window.Current.Content as Windows.UI.Xaml.Controls.Frame; root.Navigate(typeof(XamlDemo.MainPage)); } } }
OK
[源碼下載]:http://files.cnblogs.com/webabcd/Windows8.rar