当前位置:   article > 正文

python利用pyqt5 开发一个自定义浏览器_pyqt5设计浏览器窗口实现自动化

pyqt5设计浏览器窗口实现自动化

python利用pyqt5 开发一个自定义浏览器

这篇文章将讲述如何制作一个DIY浏览器,目前,现在大多数的浏览器都过去庞大,例如即便是Chrome浏览器这种插件丰富的浏览器,Chrome依然是一个内存大户

使用工具:

  1. PyQt5
  2. QtWebEngineWidgets

下面首先介绍制作一款最简单的浏览器,以下是效果图和代码
在这里插入图片描述

from PyQt5.QtWebEngineWidgets import QWebEngineView
from PyQt5.QtCore import QUrl
from PyQt5.QtWidgets import QMainWindow,QApplication,QTabWidget
import sys

class WebView(QWebEngineView):
    def __init__(self, parent):
        super().__init__(parent)
    
 
 
class MainDemo(QMainWindow):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.setWindowTitle('My_Browser')
        self.resize(800, 500)
        # 添加标签栏
        self.tabs = QTabWidget()
        self.tabs.setDocumentMode(True)
        
        
        
        self.add_new_tab(QUrl('http://www.baidu.com'), 'Homepage')
        self.setCentralWidget(self.tabs)

    # 添加新的标签页
    def add_new_tab(self, qurl=QUrl(''), label='Blank'):
        # 设置浏览器
        self.browser = WebView(self)
        # 加载cookie
        
        self.browser.page().load(qurl)
        
        
        # 添加标签
        i = self.tabs.addTab(self.browser, label)
        self.tabs.setCurrentIndex(i)
        # 将标签标题改为网页相关的标题
        self.browser.loadFinished.connect(lambda _, i=i, browser=self.browser: self.tabs.setTabText(i, self.browser.page().title()))
	
if __name__ == '__main__':
    my_application = QApplication(sys.argv) #创建QApplication类的实例
    main_demo = MainDemo()
    main_demo.showMaximized()
    my_application.exec_()
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45

后面我会讲如何制作浏览器的各个功能,如右键菜单栏,导航栏以及获取cookie自动登录等等

  • 右键菜单栏

他们可以自定义右键的菜单栏来添加许多功能,具体效果和代码如下:
在这里插入图片描述

#自定义的一个菜单类
class WebMenu(QMenu):
    def __init__(self):
        super(WebMenu, self).__init__()
        # 定义一个浏览器右键菜单
        self.save_act = QAction("保存cookie")
        self.reload_act = QAction("刷新页面")
        self.run_js = QAction("运行js")
        self.addAction(self.save_act)
        self.addAction(self.reload_act)
        self.addAction(self.run_js)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
        # 添加右键菜单
        self.browser.setContextMenuPolicy(Qt.CustomContextMenu)
        self.browser.customContextMenuRequested.connect(self.MyBrowser_Menu)#将菜单的信号链接到自定义菜单槽函数
       
  • 1
  • 2
  • 3
  • 4
  • 添加导航栏

导航栏与右键菜单栏一样,同样可以自定义菜单栏来实现一些功能
具体代码如下:

        # 添加URL地址栏
        self.urlbar = QLineEdit()
		# 让地址栏支持输入地址回车访
        self.urlbar.returnPressed.connect(self.navigate_to_url)
        # 添加标签栏
        self.tabs = QTabWidget()
        self.tabs.setDocumentMode(True)
        self.tabs.tabBarDoubleClicked.connect(self.tab_open)
        self.tabs.currentChanged.connect(self.current_tab_changed)
        # 允许关闭标签
        self.tabs.setTabsClosable(True)
        # 设置关闭按钮的槽
        self.tabs.tabCloseRequested.connect(self.close_current_tab)
        self.add_new_tab(QUrl('https://www.baidu.com/'), 'Homepage')
        self.setCentralWidget(self.tabs)
        new_tab_action = QAction( 'New Page', self)
        new_tab_action.triggered.connect(self.add_new_tab)
        # 添加导航栏
        navigation_bar = QToolBar('Navigation')
        self.addToolBar(navigation_bar)
        # 添加前进、后退、停止加载和刷新的按钮
        back_button = QAction( 'Back', self)
        forward_button = QAction('Forward', self)
        stop_button = QAction('Stop', self)
        reload_button = QAction('Reload', self)
        back_button.triggered.connect(self.tabs.currentWidget().back)
        forward_button.triggered.connect(self.tabs.currentWidget().forward)
        stop_button.triggered.connect(self.tabs.currentWidget().stop)
        reload_button.triggered.connect(self.tabs.currentWidget().reload)
        # 将按钮添加到导航栏上
        navigation_bar.addAction(back_button)
        navigation_bar.addAction(forward_button)
        navigation_bar.addAction(stop_button)
        navigation_bar.addAction(reload_button)
        navigation_bar.addSeparator()
        navigation_bar.addWidget(self.urlbar)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 保存cookie或者删除cookie

保存cookie的方法其实很简单,只要调用QWebEngineView的内置函数get_cookie() 就可以了

    # 保存cookie
    def save_slot(self):
        cookie = self.browser.get_cookie()
        with open('cookie.txt', 'w', encoding='utf8') as f:
            f.write(cookie)
        
        QMessageBox.information(self,"提示","cookie已保存")
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

同样删除cookie也只需要一行代码即可完成

self.browser.page().profile().defaultProfile().deleteAllCookies()
  • 1
  • 浏览器运行js

浏览器运行js也很简单,一行代码实现

    # 运行js
       	def run_js(self):
        js_string = '''
        document.getElementsByClassName("s_ipt")[0].value = "666666"
        '''

        self.browser.page().runJavaScript(js_string)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

这里暂时先讲这些功能,后续有时间还会进行更多的功能开发,这里放出完整代码

from PyQt5.QtWebEngineWidgets import QWebEngineView,QWebEngineProfile,QWebEngineSettings
from PyQt5.QtCore import Qt,QUrl
from PyQt5.QtWidgets import QToolBar,QLineEdit,QMainWindow,QApplication,QTabWidget,QMenu, QAction,QMessageBox
import sys

class WebView(QWebEngineView):
    def __init__(self, parent):
        super().__init__(parent)
        QWebEngineProfile.defaultProfile().cookieStore().cookieAdded.connect(self.onCookieAdd)
        self.cookies = {}          # 存放cookie字典
    def createWindow(self, webWindowType):
        return main_demo.browser
 
    def onCookieAdd(self, cookie):                       # 处理cookie添加的事件
        name = cookie.name().data().decode('utf-8')     # 先获取cookie的名字,再把编码处理一下
        value = cookie.value().data().decode('utf-8')   # 先获取cookie值,再把编码处理一下
        self.cookies[name] = value                       # 将cookie保存到字典里
 
    # 获取cookie
    def get_cookie(self):
        cookie_str = ''
        for key, value in self.cookies.items():         # 遍历字典
            cookie_str += (key + '=' + value)     # 将键值对拿出来拼接一下
        return cookie_str 
    
class MainDemo(QMainWindow):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.setWindowTitle('My_Browser')
        self.resize(800, 500)
        # 添加标签栏
        self.tabs = QTabWidget()
        self.tabs.setDocumentMode(True)
        # 添加URL地址栏
        self.urlbar = QLineEdit()
		# 让地址栏支持输入地址回车访
        self.urlbar.returnPressed.connect(self.navigate_to_url)
        # 添加标签栏
        self.tabs = QTabWidget()
        self.tabs.setDocumentMode(True)
        self.tabs.tabBarDoubleClicked.connect(self.tab_open)
        self.tabs.currentChanged.connect(self.current_tab_changed)
        # 允许关闭标签
        self.tabs.setTabsClosable(True)
        # 设置关闭按钮的槽
        self.tabs.tabCloseRequested.connect(self.close_current_tab)
        self.add_new_tab(QUrl('https://www.baidu.com/'), 'Homepage')
        self.setCentralWidget(self.tabs)
        new_tab_action = QAction( 'New Page', self)
        new_tab_action.triggered.connect(self.add_new_tab)
        # 添加导航栏
        navigation_bar = QToolBar('Navigation')
        self.addToolBar(navigation_bar)
        # 添加前进、后退、停止加载和刷新的按钮
        back_button = QAction( 'Back', self)
        forward_button = QAction('Forward', self)
        stop_button = QAction('Stop', self)
        reload_button = QAction('Reload', self)
        back_button.triggered.connect(self.tabs.currentWidget().back)
        forward_button.triggered.connect(self.tabs.currentWidget().forward)
        stop_button.triggered.connect(self.tabs.currentWidget().stop)
        reload_button.triggered.connect(self.tabs.currentWidget().reload)
        # 将按钮添加到导航栏上
        navigation_bar.addAction(back_button)
        navigation_bar.addAction(forward_button)
        navigation_bar.addAction(stop_button)
        navigation_bar.addAction(reload_button)
        navigation_bar.addSeparator()
        navigation_bar.addWidget(self.urlbar)
        
        
        # 添加自定义菜单
        self.web_menu = WebMenu()
        

    # 添加新的标签页
    def add_new_tab(self, qurl=QUrl(''), label='Blank'):
        # 设置浏览器
        self.browser = WebView(self)
        self.browser.page().load(qurl)
        
        # 添加右键菜单
        self.browser.setContextMenuPolicy(Qt.CustomContextMenu)
        self.browser.customContextMenuRequested.connect(self.MyBrowser_Menu)#将菜单的信号链接到自定义菜单槽函数
        
        # 添加标签
        i = self.tabs.addTab(self.browser, label)
        self.tabs.setCurrentIndex(i)
        self.browser.urlChanged.connect(lambda qurl, browser=self.browser: self.renew_urlbar(qurl, self.browser))

        # 将标签标题改为网页相关的标题
        self.browser.loadFinished.connect(lambda _, i=i, browser=self.browser: self.tabs.setTabText(i, self.browser.page().title()))
	
    # 响应回车按钮,将浏览器当前访问的URL设置为用户输入的URL
    def navigate_to_url(self):
        current_url = QUrl(self.urlbar.text())
        if current_url.scheme() == '':
            current_url.setScheme('http')
        self.tabs.currentWidget().load(current_url)
    
    # 将当前网页的链接更新到地址栏
    def renew_urlbar(self, url, browser=None):
		# 非当前窗口不更新URL
        if browser != self.tabs.currentWidget():
            return
        self.urlbar.setText(url.toString())
        self.urlbar.setCursorPosition(0)
    
    # 双击标签栏打开新页面
    def tab_open(self, i):
        if i == -1:
            self.add_new_tab()
    def current_tab_changed(self, i):
        qurl = self.tabs.currentWidget().url()
        self.renew_urlbar(qurl, self.tabs.currentWidget())
    def close_current_tab(self, i):
        # 若当前标签页只有一个则不关闭
        if self.tabs.count() < 2:
            return
        self.tabs.removeTab(i)
    
    #创建自定义浏览器右键菜单
    def MyBrowser_Menu(self,pos):
        action = self.web_menu.exec_(self.browser.mapToGlobal(pos))
        if action == self.web_menu.save_act:
            self.save_slot()
        elif action == self.web_menu.reload_act:
            self.reload_slot()
        elif action == self.web_menu.run_js:
            self.run_js()
    
    # 保存cookie
    def save_slot(self):
        cookie = self.browser.get_cookie()
        with open('cookie.txt', 'w', encoding='utf8') as f:
            f.write(cookie)
        
        QMessageBox.information(self,"提示","cookie已保存")
        
        
    
    # 重新加载页面
    def reload_slot(self):
        self.browser.reload()


    # 运行js
    def run_js(self):
        js_string = '''
        document.getElementsByClassName("s_ipt")[0].value = "666666"
        '''

        self.browser.page().runJavaScript(js_string)
        

        
#自定义的一个菜单类
class WebMenu(QMenu):
    def __init__(self):
        super(WebMenu, self).__init__()
        # 定义一个浏览器右键菜单
        self.save_act = QAction("保存cookie")
        self.reload_act = QAction("刷新页面")
        self.run_js = QAction("运行js")
        self.addAction(self.save_act)
        self.addAction(self.reload_act)
        self.addAction(self.run_js)
        
if __name__ == '__main__':
    my_application = QApplication(sys.argv) #创建QApplication类的实例
    main_demo = MainDemo()
    main_demo.showMaximized()
    my_application.exec_()
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173

参考链接:
https://segmentfault.com/a/1190000016222966
https://blog.csdn.net/weixin_34399060/article/details/89625985
https://blog.csdn.net/hxxjxw/article/details/105897678

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/小丑西瓜9/article/detail/95702
推荐阅读
相关标签
  

闽ICP备14008679号