File indexing completed on 2024-05-19 09:30:06
0001 #!/usr/bin/env python3 0002 0003 # SPDX-FileCopyrightText: 2023 Fushan Wen <qydwhotmail@gmail.com> 0004 # SPDX-License-Identifier: MIT 0005 0006 import base64 0007 import os 0008 import shutil 0009 import subprocess 0010 import tempfile 0011 import time 0012 import unittest 0013 from typing import Final 0014 0015 import cv2 as cv 0016 import numpy as np 0017 from appium import webdriver 0018 from appium.options.common.base import AppiumOptions 0019 from appium.webdriver.common.appiumby import AppiumBy 0020 from gi.repository import GLib 0021 0022 KDE_VERSION: Final = 6 0023 KCM_ID: Final = "kcm_cursortheme" 0024 0025 0026 class KCMCursorThemeTest(unittest.TestCase): 0027 """ 0028 Tests for kcm_cursortheme 0029 """ 0030 0031 driver: webdriver.Remote 0032 0033 @classmethod 0034 def setUpClass(cls) -> None: 0035 """ 0036 Opens the KCM and initialize the webdriver 0037 """ 0038 # Install the custom cursor theme 0039 user_data_dir: Final[str] = GLib.get_user_data_dir() 0040 icons_folder: Final = os.path.join(user_data_dir, "icons") 0041 if not os.path.exists(icons_folder): 0042 os.mkdir(icons_folder) 0043 cls.addClassCleanup(lambda: shutil.rmtree(icons_folder)) 0044 0045 icon_theme_folder: Final = os.path.join(user_data_dir, "icons", "testcursortheme") 0046 assert not os.path.exists(icon_theme_folder) 0047 assert os.path.exists("../kcms/cursortheme/autotests/data/testcursortheme") 0048 shutil.copytree("../kcms/cursortheme/autotests/data/testcursortheme", icon_theme_folder) 0049 cls.addClassCleanup(lambda: shutil.rmtree(icon_theme_folder)) 0050 0051 options = AppiumOptions() 0052 options.set_capability("app", f"kcmshell{KDE_VERSION} {KCM_ID}") 0053 options.set_capability("timeouts", {'implicit': 10000}) 0054 # From XCURSORPATH 0055 options.set_capability("environ", { 0056 "XCURSOR_PATH": icons_folder, 0057 "QT_LOGGING_RULES": "kcm_cursortheme.debug=true", 0058 }) 0059 cls.driver = webdriver.Remote(command_executor='http://127.0.0.1:4723', options=options) 0060 0061 def tearDown(self) -> None: 0062 """ 0063 Take screenshot when the current test fails 0064 """ 0065 if not self._outcome.result.wasSuccessful(): 0066 self.driver.get_screenshot_as_file(f"failed_test_shot_{KCM_ID}_#{self.id()}.png") 0067 0068 @classmethod 0069 def tearDownClass(cls) -> None: 0070 """ 0071 Make sure to terminate the driver again, lest it dangles. 0072 """ 0073 cls.driver.quit() 0074 0075 def test_0_open(self) -> None: 0076 """ 0077 Tests the KCM can be opened 0078 """ 0079 self.driver.find_element(AppiumBy.NAME, "&Configure Launch Feedback…") 0080 self.driver.find_element(AppiumBy.NAME, "Test Cursor Theme (DO NOT TRANSLATE)") 0081 0082 def test_1_cursor_theme_preview(self) -> None: 0083 """ 0084 Tests if the cursor preview is loaded 0085 """ 0086 time.sleep(3) # Wait until the window appears 0087 0088 with tempfile.TemporaryDirectory() as temp_dir: 0089 saved_image_path: str = os.path.join(temp_dir, "kcm_window.png") 0090 subprocess.check_call(["import", "-window", "root", saved_image_path]) 0091 0092 cv_first_image = cv.imread(saved_image_path, cv.IMREAD_COLOR) 0093 first_image = base64.b64encode(cv.imencode('.png', cv_first_image)[1].tobytes()).decode() 0094 0095 # Red 0096 cv_second_image = np.zeros((16, 16, 3), dtype=np.uint8) 0097 cv_second_image[:, :] = [0, 0, 255] 0098 second_image = base64.b64encode(cv.imencode('.png', cv_second_image)[1].tobytes()).decode() 0099 self.driver.find_image_occurrence(first_image, second_image) 0100 # Green 0101 cv_second_image[:, :] = [0, 255, 0] 0102 second_image = base64.b64encode(cv.imencode('.png', cv_second_image)[1].tobytes()).decode() 0103 self.driver.find_image_occurrence(first_image, second_image) 0104 # Blue 0105 cv_second_image[:, :] = [255, 0, 0] 0106 second_image = base64.b64encode(cv.imencode('.png', cv_second_image)[1].tobytes()).decode() 0107 self.driver.find_image_occurrence(first_image, second_image) 0108 # Yellow 0109 cv_second_image[:, :] = [0, 255, 255] 0110 second_image = base64.b64encode(cv.imencode('.png', cv_second_image)[1].tobytes()).decode() 0111 self.driver.find_image_occurrence(first_image, second_image) 0112 0113 def test_2_launch_feedback_dialog(self) -> None: 0114 self.driver.find_element(AppiumBy.NAME, "&Configure Launch Feedback…").click() 0115 self.driver.find_element(AppiumBy.NAME, "Blinking") 0116 0117 0118 if __name__ == '__main__': 0119 unittest.main()