Android基础之WebView | 网络请求方式 | HttpURLConnection | OkHttp | 带实例

WebView

简介

  • 一般用于加载一些网络界面
  • Android内置webkit内核的高性能浏览器,而WebView则是在这个基础上进行封装后的一个 控件,WebView直译网页视图,我们可以简单的看作一个可以嵌套到界面上的一个浏览器控件!

方法

  • WebChromeClient

辅助WebView处理Javascript的对话框、网站图标、网站title、加载进度等

方法

作用

onJsAlert(WebView view,String url,String message,JsResult result)

处理Js中的Alert对话框

onJsConfirm(WebView view,String url,String message,JsResult result)

处理Js中的Confirm对话框

onJsPrompt(WebView view,String url,String message,String defaultValue,JsPromptResult result)

处理Js中的Prompt对话框

onProgressChanged(WebView view,int newProgress)

当加载进度条发生改变时调用

onReceivedIcon(WebView view, Bitmap icon)

获得网页的icon

onReceivedTitle(WebView view, String title)

获得网页的标题

  • WebViewClient

辅助WebView处理各种通知与请求事件

方法

作用

onPageStared(WebView view,String url)

通知主程序网页开始加载

onPageFinished(WebView view,String url,Bitmap favicon)

通知主程序,网页加载完毕

doUpdateVisitedHistory(WebView view,String url,boolean isReload)

更新历史记录

onLoadResource(WebView view,String url)

通知主程序WebView即将加载指定url的资源

onScaleChanged(WebView view,float oldScale,float newScale)

ViewView的缩放发生改变时调用

shouldOverrideKeyEvent(WebView view,KeyEvent event)

控制webView是否处理按键时间,如果返回true,则WebView不处理,返回false则处理

shouldOverrideUrlLoading(WebView view,String url)

控制对新加载的Url的处理,返回true,说明主程序处理WebView不做处理,返回false意味着WebView会对其进行处理

onReceivedError(WebView view,int errorCode,String description,String failingUrl)

遇到不可恢复的错误信息时调用

  • WebSettings

WebView相关配置的设置,比如setJavaScriptEnabled()设置是否允许JS脚本执行

方法

作用

getSettings()

返回一个WebSettings对象,用来控制WebView的属性设置

loadUrl(String url)

加载指定的Url

loadData(String data,String mimeType,String encoding)

加载指定的Data到WebView中.使用"data:"作为标记头,该方法不能加载网络数据.其中mimeType为数据类型如:textml,image/jpeg. encoding为字符的编码方式

loadDataWithBaseURL(String baseUrl, String data, String mimeType, String encoding, String historyUrl)

比上面的loadData更加强大

setWebViewClient(WebViewClient client)

为WebView指定一个WebViewClient对象.WebViewClient可以辅助WebView处理各种通知,请求等事件。

setWebChromeClient(WebChromeClient client)

为WebView指定一个WebChromeClient对象,WebChromeClient专门用来辅助WebView处理js的对话框,网站title,网站图标,加载进度条等

实例

  • xml
<WebView
	        android:id="@+id/web_view"
	        android:layout_width="409dp"
	        android:layout_height="729dp"
	        app:layout_constraintBottom_toBottomOf="parent"
	        app:layout_constraintEnd_toEndOf="parent"
	        app:layout_constraintStart_toStartOf="parent"
	        app:layout_constraintTop_toTopOf="parent" />
  • MainActivity
public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        WebView webView = findViewById(R.id.web_view);
        webView.getSettings().setJavaScriptEnabled(true);
        webView.setWebViewClient(new WebViewClient());
        webView.loadUrl("https://www.baidu.com");
    }
}
  • Manifest

在Android9.0之后,url不支持明文格式,所以要么进行加密https,要么在application里添加一行android:usesCleartextTraffic="true"(但是也不行),或者降低SDK版本

<uses-permission android:name="android.permission.INTERNET"/>

<application
	        android:allowBackup="true"
	        android:usesCleartextTraffic="true"
	        android:icon="@mipmap/ic_launcher"
	        android:label="@string/app_name"
	        android:roundIcon="@mipmap/ic_launcher_round"
	        android:supportsRtl="true"
	        android:theme="@style/AppTheme">
	        <activity android:name=".MainActivity">
	            <intent-filter>
	                <action android:name="android.intent.action.MAIN" />

	                <category android:name="android.intent.category.LAUNCHER" />
	            </intent-filter>
	        </activity>
</application>
  • 下载地址

DoSomeAndroidTest/WebView at main · qricis/DoSomeAndroidTest · GitHub


网络请求方式

  • 在过去,Android上发送Http请求一般有两种方式:HttpURLConnection和HttpClient,但是由于HttpClient的API数量过多,在Android6.0的系统中,被完全移除了
// HttpURLConnection

// 获取该实例
URL url = new URL("http://baidu.com");
HttpUriConnection connection = (HttpURLConnection) url.openConnection();

// 设置请求所用的方法(get/post),get表示希望从服务器获取数据,post表示希望提交数据给服务器
connection.setRequestMethod("GET")

// 连接超时
connection.setConnectTimeout(8000);

// 读取超时的毫秒数
connection.setReadTimeout(8000);

// 获取服务器返回的输入流
InputStream in = connection.getInputStream();

// 调用disconnect()方法关闭该http连接
connection.disconnect()
  • xml
<Button
		        android:id="@+id/send_request"
		        android:layout_width="163dp"
		        android:layout_height="0dp"
		        android:text="@string/sendrequest"
		        android:onClick="sendResquest"
		        app:layout_constraintHeight_default="percent"
		        app:layout_constraintHeight_percent="0.08"
		        app:layout_constraintEnd_toEndOf="parent"
		        app:layout_constraintStart_toStartOf="parent"
		        app:layout_constraintTop_toTopOf="parent" />

<ScrollView
		        android:layout_width="match_parent"
		        android:layout_height="0dp"
		        android:layout_marginTop="1dp"
		        app:layout_constraintHeight_default="percent"
		        app:layout_constraintHeight_percent="0.9"
		        app:layout_constraintBottom_toBottomOf="parent"
		        app:layout_constraintEnd_toEndOf="parent"
		        app:layout_constraintHorizontal_bias="0.0"
		        app:layout_constraintStart_toStartOf="parent"
		        app:layout_constraintTop_toBottomOf="@+id/send_request"
		        app:layout_constraintVertical_bias="1.0">

		    <TextView
		            android:id="@+id/response_text"
		            android:layout_width="match_parent"
		            android:layout_height="wrap_content" />
</ScrollView>
  • Manifest
<uses-permission android:name="android.permission.INTERNET"/>

<application
		        android:allowBackup="true"
		        android:icon="@mipmap/ic_launcher"
		        android:label="@string/app_name"
		        android:roundIcon="@mipmap/ic_launcher_round"
		        android:supportsRtl="true"
		        android:theme="@style/AppTheme">
		        <activity android:name=".MainActivity">
		            <intent-filter>
		                <action android:name="android.intent.action.MAIN" />

		                <category android:name="android.intent.category.LAUNCHER" />
		            </intent-filter>
		        </activity>
</application>
  • MainActivity
public class MainActivity extends AppCompatActivity {

    TextView responseText;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        responseText = findViewById(R.id.response_text);

    }

    public void sendResquest(View view) {

        sendRequestWithHttpURLConnection();

    }

    private void sendRequestWithHttpURLConnection() {

        //开启线程来发起网络请求
        new Thread(new Runnable() {
            @Override
            public void run() {
                HttpURLConnection connection = null;
                BufferedReader reader = null;

                try {
                    URL url = new URL("https://www.baidu.com");
                    connection = (HttpURLConnection) url.openConnection();
                    connection.setRequestMethod("GET");
                    connection.setConnectTimeout(8000);
                    connection.setReadTimeout(8000);
                    InputStream in = connection.getInputStream();

                    //向服务器提交数据的写法
                    /*connection.setRequestMethod("POST");
			                    DataOutputStream out = new DataOutputStream(connection.getOutputStream());
			                    out.writeBytes("username=admin&password=123456");*/

                    //对获取到的输入流进行读取
                    reader = new BufferedReader(new InputStreamReader(in));
                    StringBuilder response = new StringBuilder();
                    String line;
                    while ((line = reader.readLine()) != null) {
                        response.append(line);
                    }
                    showResponse(response.toString());
                } catch (Exception e) {
                    e.printStackTrace();
                } finally {
                    if (reader != null) {
                        try {
                            reader.close();
                        } catch (IOException e) {
                            e.printStackTrace();
                        }
                    }
                    if (connection != null) {
                        connection.disconnect();
                    }
                }
            }
        }).start();
    }

    private void showResponse(final String response) {
        runOnUiThread(new Runnable() {
            @Override
            public void run() {
                //在这里进行UI操作,将结果显示在界面上
                responseText.setText(response);
            }
        });
    }

}

OkHttp

  • build.gradle
implementation 'com.squareup.okhttp3:mockwebserver:4.8.1'
  • MainActivity
private void sendRequestWithOkHttp() {
    new Thread(new Runnable() {
        @Override
        public void run() {
            try {
                OkHttpClient client = new OkHttpClient();

                Request request = new Request.Builder()
                    .url("https://www.baidu.com")
                    .build();

                Response response = client.newCall(request).execute();
                String responseData = response.body().string();
                showResponse(responseData);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }).start();
}
  • 升级版(解析数据)
private void parseXMLWithPull(String xmlData) {
    try {
        XmlPullParserFactory factory = XmlPullParserFactory.newInstance();
        XmlPullParser xmlPullParser = factory.newPullParser();
        xmlPullParser.setInput(new StringReader(xmlData));

        int eventType = xmlPullParser.getEventType();

        String id = "";
        String name = "";
        String version = "";

        while (eventType != XmlPullParser.END_DOCUMENT) {
            String nodeName = xmlPullParser.getName();
            switch (eventType) {
                    //开始解析某个节点
                case XmlPullParser.START_TAG:{
                    if ("id".equals(nodeName)) {
                        id = xmlPullParser.nextText();
                    } else if ("name".equals(nodeName)) {
                        name = xmlPullParser.nextText();
                    } else if ("version".equals(nodeName)) {
                        version = xmlPullParser.nextText();
                    }
                    break;
                }
                    //完成解析某个节点
                case XmlPullParser.END_TAG:{
                    if ("app".equals(nodeName)) {
                        Log.d("MainActivity","id is " + id);
                        Log.d("MainActivity","name is " + name);
                        Log.d("MainActivity","version is " + version);
                    }
                    break;
                }
                default:
                    break;
            }
            eventType = xmlPullParser.next();
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}

private void parseXMLWithSAX(String xmlData) {
    try {
        SAXParserFactory factory = SAXParserFactory.newInstance();
        XMLReader xmlReader = factory.newSAXParser().getXMLReader();
        ContentHandler handler = new ContentHandler();
        //将ContentHandler的实例设置到XMLReader中
        xmlReader.setContentHandler(handler);
        //开始执行解析
        xmlReader.parse(new InputSource(new StringReader(xmlData)));
    } catch (Exception e) {
        e.printStackTrace();
    }
}

private void parseJSONWithJSONObject(String jsonData) {

    try {
        JSONArray jsonArray = new JSONArray(jsonData);
        for (int i = 0; i < jsonArray.length(); i++) {
            JSONObject jsonObject = jsonArray.getJSONObject(i);
            String id = jsonObject.getString("id");
            String name = jsonObject.getString("name");
            String version = jsonObject.getString("version");

            Log.d("MainActivity","id is " + id);
            Log.d("MainActivity","name is " + name);
            Log.d("MainActivity","version is " + version);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }

}

private void parseJSONWithGson(String jsonData) {

    Gson gson = new Gson();
    List<App> appList = gson.fromJson(jsonData,new TypeToken<List<App>>(){}.getType());

    for (App app : appList) {
        Log.d("MainActivity","id is " + app.getId());
        Log.d("MainActivity","name is " + app.getName());
        Log.d("MainActivity","version is " + app.getVersion());
    }

}

private void showResponse(final String response) {
    runOnUiThread(new Runnable() {
        @Override
        public void run() {
            //在这里进行UI操作,将结果显示在界面上
            responseText.setText(response);
        }
    });
}

下载地址

DoSomeAndroidTest/NetworkTest at main · qricis/DoSomeAndroidTest · GitHub

热门文章

暂无图片
编程学习 ·

exe4j详细使用教程(附下载安装链接)

一、exe4j介绍 ​ exe4j是一个帮助你集成Java应用程序到Windows操作环境的java可执行文件生成工具&#xff0c;无论这些应用是用于服务器&#xff0c;还是图形用户界面&#xff08;GUI&#xff09;或命令行的应用程序。如果你想在任务管理器中及Windows XP分组的用户友好任务栏…
暂无图片
编程学习 ·

AUTOSAR从入门到精通100讲(126)-浅谈车载充电系统通信方案

01 引言 本文深入研究车载充电系统策略,设计出一套基于电动汽车电池管理系统与车载充电机的CAN通信协议,可供电动汽车设计人员参考借鉴。 02 电动汽车充电系统通讯网络 电动汽车整车控制系统中采用的是CAN总线通信方式,由一个整车内部高速CAN网络、内部低速CAN网络和一个充电…
暂无图片
编程学习 ·

CMake(九):生成器表达式

当运行CMake时&#xff0c;开发人员倾向于认为它是一个简单的步骤&#xff0c;需要读取项目的CMakeLists.txt文件&#xff0c;并生成相关的特定于生成器的项目文件集(例如Visual Studio解决方案和项目文件&#xff0c;Xcode项目&#xff0c;Unix Makefiles或Ninja输入文件)。然…
暂无图片
编程学习 ·

47.第十章 网络协议和管理配置 -- 网络配置(八)

4.3.3 route 命令 路由表管理命令 路由表主要构成: Destination: 目标网络ID,表示可以到达的目标网络ID,0.0.0.0/0 表示所有未知网络,又称为默认路由,优先级最低Genmask:目标网络对应的netmaskIface: 到达对应网络,应该从当前主机哪个网卡发送出来Gateway: 到达非直连的网络,…
暂无图片
编程学习 ·

元宇宙技术基础

请看图&#xff1a; 1、通过AR、VR等交互技术提升游戏的沉浸感 回顾游戏的发展历程&#xff0c;沉浸感的提升一直是技术突破的主要方向。从《愤怒的小鸟》到CSGO,游戏建模方式从2D到3D的提升使游戏中的物体呈现立体感。玩家在游戏中可以只有切换视角&#xff0c;进而提升沉浸…
暂无图片
编程学习 ·

flink的伪分布式搭建

一 flink的伪分布式搭建 1.1 执行架构图 1.Flink程序需要提交给 Job Client2.Job Client将作业提交给 Job Manager3.Job Manager负责协调资源分配和作业执行。 资源分配完成后&#xff0c;任务将提交给相应的 Task Manage。4.Task Manager启动一个线程以开始执行。Task Manage…
暂无图片
编程学习 ·

十进制正整数与二进制字符串的转换(C++)

Function one&#xff1a; //十进制数字转成二进制字符串 string Binary(int x) {string s "";while(x){if(x % 2 0) s 0 s;else s 1 s;x / 2;}return s; } Function two&#xff1a; //二进制字符串变为十进制数字 int Decimal(string s) {int num 0, …
暂无图片
编程学习 ·

[含lw+源码等]微信小程序校园辩论管理平台+后台管理系统[包运行成功]Java毕业设计计算机毕设

项目功能简介: 《微信小程序校园辩论管理平台后台管理系统》该项目含有源码、论文等资料、配套开发软件、软件安装教程、项目发布教程等 本系统包含微信小程序做的辩论管理前台和Java做的后台管理系统&#xff1a; 微信小程序——辩论管理前台涉及技术&#xff1a;WXML 和 WXS…
暂无图片
编程学习 ·

树莓派驱动DHT11温湿度传感器

1&#xff0c;直接使用python库 代码如下 import RPi.GPIO as GPIO import dht11 import time import datetimeGPIO.setwarnings(True) GPIO.setmode(GPIO.BCM)instance dht11.DHT11(pin14)try:while True:result instance.read()if result.is_valid():print(ok)print(&quo…
暂无图片
编程学习 ·

ELK简介

ELK简介 ELK是三个开源软件的缩写&#xff0c;Elasticsearch、Logstash、Kibana。它们都是开源软件。不过现在还新增了一个 Beats&#xff0c;它是一个轻量级的日志收集处理工具(Agent)&#xff0c;Beats 占用资源少&#xff0c;适合于在各个服务器上搜集日志后传输给 Logstas…
暂无图片
编程学习 ·

Linux 基础

通常大数据框架都部署在 Linux 服务器上&#xff0c;所以需要具备一定的 Linux 知识。Linux 书籍当中比较著名的是 《鸟哥私房菜》系列&#xff0c;这个系列很全面也很经典。但如果你希望能够快速地入门&#xff0c;这里推荐《Linux 就该这么学》&#xff0c;其网站上有免费的电…
暂无图片
编程学习 ·

Windows2022 无线网卡装不上驱动

想来 Windows2022 和 windows10/11 的驱动应该差不多通用的&#xff0c;但是死活装不上呢&#xff1f; 搜一下&#xff0c;有人提到 “默认安装时‘无线LAN服务’是关闭的&#xff0c;如果需要开启&#xff0c;只需要在“添加角色和功能”中&#xff0c;选择开启“无线LAN服务…
暂无图片
编程学习 ·

【嵌入式面试宝典】版本控制工具Git常用命令总结

目录 创建仓库 查看信息 版本回退 版本检出 远程库 Git 创建仓库 git initgit add <file> 可反复多次使用&#xff0c;添加多个文件git commit -m <message> 查看信息 git status 仓库当前的状态git diff 差异对比git log 历史记录&#xff0c;提交日志--pret…
暂无图片
编程学习 ·

用Postman生成测试报告

newman newman是一款基于nodejs开发的可以运行postman脚本的工具&#xff0c;使用Newman&#xff0c;可以直接从命令运行和测试postman集合。 安装nodejs 下载地址&#xff1a;https://nodejs.org/en/download/ 选择自己系统相对应的版本内容进行下载&#xff0c;然后傻瓜式安…
暂无图片
编程学习 ·

Java面向对象之多态、向上转型和向下转型

文章目录前言一、多态二、引用类型之间的转换Ⅰ.向上转型Ⅱ.向下转型总结前言 今天继续Java面向对象的学习&#xff0c;学习面向对象的第三大特征&#xff1a;多态&#xff0c;了解多态的意义&#xff0c;以及两种引用类型之间的转换&#xff1a;向上转型、向下转型。  希望能…
暂无图片
编程学习 ·

IntelliJ IDEA 的 Metamodel 配置

如果不在 IntelliJ IDEA 中配置的话&#xff0c;将会出现编译错误。 这是因为 Metamodel 源代码不是在 src 目录中的&#xff0c;而是在编译的时候生成的。 要解决这个问题其实也非常简单&#xff0c;按照下面 2 个步骤就可以了。 配置 首先需要进入进入 IntelliJ IDEA 的编…