2020-10-17 10:52:04 +00:00
|
|
|
import logging
|
|
|
|
from enum import Enum
|
|
|
|
from threading import Thread
|
|
|
|
|
2023-03-07 09:30:16 +00:00
|
|
|
import cv2
|
2023-02-11 21:20:43 +00:00
|
|
|
import numpy as np
|
|
|
|
from mss.base import MSSBase
|
|
|
|
|
2023-03-06 19:07:26 +00:00
|
|
|
from fishy.engine.common import screenshot
|
2023-03-07 09:30:16 +00:00
|
|
|
from fishy.helper import helper
|
|
|
|
from fishy.helper.config import config
|
2022-02-01 16:50:57 +00:00
|
|
|
from fishy.helper.helper import print_exc
|
2023-02-21 17:35:44 +00:00
|
|
|
from fishy.osservices.os_services import os_services
|
2020-10-17 10:52:04 +00:00
|
|
|
|
|
|
|
|
|
|
|
class Status(Enum):
|
2020-10-17 22:35:20 +00:00
|
|
|
CRASHED = -1
|
|
|
|
STOPPED = 0
|
2020-10-17 10:52:04 +00:00
|
|
|
RUNNING = 1
|
|
|
|
|
|
|
|
|
|
|
|
class WindowServer:
|
|
|
|
"""
|
|
|
|
Records the game window, and allows to create instance to process it
|
|
|
|
"""
|
2023-02-11 22:14:40 +00:00
|
|
|
Screen: np.ndarray = None
|
2020-10-17 10:52:04 +00:00
|
|
|
windowOffset = None
|
|
|
|
status = Status.STOPPED
|
2023-03-06 19:07:26 +00:00
|
|
|
sslib = None
|
2023-02-21 17:35:44 +00:00
|
|
|
crop = None
|
2020-10-17 10:52:04 +00:00
|
|
|
|
|
|
|
|
2020-10-17 19:06:07 +00:00
|
|
|
def init():
|
2020-10-17 10:52:04 +00:00
|
|
|
"""
|
|
|
|
Executed once before the main loop,
|
|
|
|
Finds the game window, and calculates the offset to remove the title bar
|
|
|
|
"""
|
2023-03-06 19:07:26 +00:00
|
|
|
WindowServer.sslib = screenshot.create()
|
2023-02-21 17:35:44 +00:00
|
|
|
WindowServer.status = Status.RUNNING
|
|
|
|
WindowServer.crop = os_services.get_game_window_rect()
|
2023-03-06 17:48:09 +00:00
|
|
|
|
2023-03-06 19:07:26 +00:00
|
|
|
if WindowServer.crop is None or not WindowServer.sslib.setup():
|
2023-03-07 09:30:16 +00:00
|
|
|
logging.error("Game window not found by window_server")
|
2020-10-17 10:52:04 +00:00
|
|
|
WindowServer.status = Status.CRASHED
|
2023-03-06 18:02:39 +00:00
|
|
|
return
|
2020-10-17 10:52:04 +00:00
|
|
|
|
2023-02-21 17:35:44 +00:00
|
|
|
|
2023-03-06 17:48:09 +00:00
|
|
|
def get_cropped_screenshot():
|
2023-03-06 19:07:26 +00:00
|
|
|
ss = WindowServer.sslib.grab()
|
2023-03-07 09:30:16 +00:00
|
|
|
|
|
|
|
if config.get("show_grab", 0):
|
|
|
|
helper.save_img("full screen", ss)
|
|
|
|
|
2023-03-06 17:48:09 +00:00
|
|
|
crop = WindowServer.crop
|
|
|
|
cropped_ss = ss[crop[1]:crop[3], crop[0]:crop[2]]
|
2023-03-07 09:30:16 +00:00
|
|
|
|
2023-03-06 17:48:09 +00:00
|
|
|
if cropped_ss.size == 0:
|
|
|
|
return None
|
2023-03-07 09:30:16 +00:00
|
|
|
|
|
|
|
if config.get("show_grab", 0):
|
|
|
|
helper.save_img("Game window", cropped_ss)
|
|
|
|
|
2023-03-06 17:48:09 +00:00
|
|
|
return cropped_ss
|
2023-02-21 17:35:44 +00:00
|
|
|
|
2020-10-17 10:52:04 +00:00
|
|
|
|
|
|
|
def loop():
|
|
|
|
"""
|
|
|
|
Executed in the start of the main loop
|
|
|
|
finds the game window location and captures it
|
|
|
|
"""
|
2023-03-06 17:48:09 +00:00
|
|
|
WindowServer.Screen = get_cropped_screenshot()
|
2020-10-17 10:52:04 +00:00
|
|
|
|
2023-03-06 17:48:09 +00:00
|
|
|
if WindowServer.Screen is None:
|
|
|
|
logging.error("Couldn't find the game window")
|
2020-10-17 10:52:04 +00:00
|
|
|
WindowServer.status = Status.CRASHED
|
|
|
|
|
|
|
|
|
2021-11-21 07:12:14 +00:00
|
|
|
# noinspection PyBroadException
|
2020-10-17 10:52:04 +00:00
|
|
|
def run():
|
|
|
|
# todo use config
|
2022-02-01 11:51:58 +00:00
|
|
|
logging.debug("window server started")
|
2020-10-17 10:52:04 +00:00
|
|
|
while WindowServer.status == Status.RUNNING:
|
2021-11-21 07:12:14 +00:00
|
|
|
try:
|
|
|
|
loop()
|
|
|
|
except Exception:
|
2022-02-01 16:50:57 +00:00
|
|
|
print_exc()
|
2021-11-21 07:12:14 +00:00
|
|
|
WindowServer.status = Status.CRASHED
|
2022-02-01 11:51:58 +00:00
|
|
|
|
|
|
|
if WindowServer.status == Status.CRASHED:
|
|
|
|
logging.debug("window server crashed")
|
|
|
|
elif WindowServer.status == Status.STOPPED:
|
|
|
|
logging.debug("window server stopped")
|
2020-10-17 10:52:04 +00:00
|
|
|
|
|
|
|
|
|
|
|
def start():
|
|
|
|
if WindowServer.status == Status.RUNNING:
|
|
|
|
return
|
|
|
|
|
2020-10-17 19:06:07 +00:00
|
|
|
init()
|
2020-10-17 10:52:04 +00:00
|
|
|
if WindowServer.status == Status.RUNNING:
|
|
|
|
Thread(target=run).start()
|
|
|
|
|
|
|
|
|
|
|
|
def screen_ready():
|
|
|
|
return WindowServer.Screen is not None or WindowServer.status == Status.CRASHED
|
|
|
|
|
|
|
|
|
|
|
|
def stop():
|
|
|
|
WindowServer.status = Status.STOPPED
|