mirror of
https://github.com/hydralauncher/hydra.git
synced 2026-01-19 01:03:57 +00:00
Compare commits
62 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
cdad2f5554 | ||
|
|
b0bf42f754 | ||
|
|
7e321ea9d1 | ||
|
|
01c3ddf167 | ||
|
|
f8770a03f7 | ||
|
|
3b7725d774 | ||
|
|
2679b143ed | ||
|
|
2b0f57f967 | ||
|
|
622107a6f1 | ||
|
|
5908544602 | ||
|
|
b330c94dca | ||
|
|
4b0f998830 | ||
|
|
d3d9315102 | ||
|
|
689fe5715e | ||
|
|
6a52c26874 | ||
|
|
60907cdc4b | ||
|
|
1b00e2ed57 | ||
|
|
6479049256 | ||
|
|
e739f3a483 | ||
|
|
18f27e76d7 | ||
|
|
47018ace60 | ||
|
|
a8332c858e | ||
|
|
d93e580d0f | ||
|
|
0e7e62d596 | ||
|
|
1d05551f4e | ||
|
|
4908d07ef2 | ||
|
|
be4d13533c | ||
|
|
7231848bd8 | ||
|
|
fb5ed9aae3 | ||
|
|
e908cc6273 | ||
|
|
5e670aab24 | ||
|
|
75a9d56624 | ||
|
|
28bd70e745 | ||
|
|
3cbbb71768 | ||
|
|
2034e0a157 | ||
|
|
a27a8644ea | ||
|
|
1a3e33cbc9 | ||
|
|
4e8f260b33 | ||
|
|
29d9c43834 | ||
|
|
d4be3ed4a0 | ||
|
|
16b9c9d340 | ||
|
|
f3f68e9009 | ||
|
|
2caf83b929 | ||
|
|
97467705b0 | ||
|
|
cdb15a0493 | ||
|
|
b9d42ca43f | ||
|
|
3d89fc659b | ||
|
|
e5bc60c13d | ||
|
|
53e7053764 | ||
|
|
24c6a3ebe3 | ||
|
|
3b2fe183b5 | ||
|
|
ba6a41d8e1 | ||
|
|
4ef054175a | ||
|
|
642c2abfd6 | ||
|
|
f90ad4c377 | ||
|
|
20dab9c4c1 | ||
|
|
be6c255bc1 | ||
|
|
d5dfd7853f | ||
|
|
5882d3697c | ||
|
|
046d291585 | ||
|
|
819e8bc508 | ||
|
|
91fe56d810 |
29
.github/ISSUE_TEMPLATE/bug_report.md
vendored
29
.github/ISSUE_TEMPLATE/bug_report.md
vendored
@@ -1,29 +0,0 @@
|
|||||||
---
|
|
||||||
name: Bug report
|
|
||||||
about: Create a report to help us improve. Write in English, please
|
|
||||||
title: "[BUG]"
|
|
||||||
labels: bug
|
|
||||||
assignees: ""
|
|
||||||
---
|
|
||||||
|
|
||||||
**Describe the bug**
|
|
||||||
A clear and concise description of what the bug is.
|
|
||||||
|
|
||||||
**To Reproduce**
|
|
||||||
Steps to reproduce the behavior:
|
|
||||||
|
|
||||||
1. Go to '...'
|
|
||||||
2. Click on '....'
|
|
||||||
3. See error
|
|
||||||
|
|
||||||
**Expected behavior**
|
|
||||||
A clear and concise description of what you expected to happen.
|
|
||||||
|
|
||||||
**Screenshots**
|
|
||||||
If applicable, add screenshots to help explain your problem.
|
|
||||||
|
|
||||||
**Additional context**
|
|
||||||
|
|
||||||
- OS: [Windows 11/Linux Distro/Steam Deck]
|
|
||||||
- Hydra Version:
|
|
||||||
- Additional information and context of your problem:
|
|
||||||
58
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
Normal file
58
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
Normal file
@@ -0,0 +1,58 @@
|
|||||||
|
name: Bug Report
|
||||||
|
description: Create a report to help us improve. Write in English, please.
|
||||||
|
title: "[BUG] "
|
||||||
|
labels: ["bug"]
|
||||||
|
body:
|
||||||
|
- type: markdown
|
||||||
|
attributes:
|
||||||
|
value: |
|
||||||
|
Thank you for creating a bug report to help us improve!
|
||||||
|
- type: textarea
|
||||||
|
id: bug-description
|
||||||
|
attributes:
|
||||||
|
label: Describe the bug
|
||||||
|
description: A clear and concise description of what the bug is.
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: bug-reproduce
|
||||||
|
attributes:
|
||||||
|
label: Steps to Reproduce
|
||||||
|
description: Steps to reproduce the behavior. For example, "1. Go to '...', 2. Click on '...', 3. See error"
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: expected-behavior
|
||||||
|
attributes:
|
||||||
|
label: Expected behavior
|
||||||
|
description: A clear and concise description of what you expected to happen.
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: screenshots
|
||||||
|
attributes:
|
||||||
|
label: Screenshots
|
||||||
|
description: If applicable, add screenshots to help explain your problem.
|
||||||
|
validations:
|
||||||
|
required: false
|
||||||
|
- type: input
|
||||||
|
id: OS
|
||||||
|
attributes:
|
||||||
|
label: Operating System
|
||||||
|
description: Which operating system are you using (e.g., Windows 11/Linux Distro/Steam Deck)?
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: input
|
||||||
|
id: hydra-version
|
||||||
|
attributes:
|
||||||
|
label: Hydra Version
|
||||||
|
description: Please provide the version of Hydra you are using.
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: additional-info
|
||||||
|
attributes:
|
||||||
|
label: Additional Information
|
||||||
|
description: Please provide any additional information and context about your problem.
|
||||||
|
validations:
|
||||||
|
required: false
|
||||||
19
.github/ISSUE_TEMPLATE/feature_request.md
vendored
19
.github/ISSUE_TEMPLATE/feature_request.md
vendored
@@ -1,19 +0,0 @@
|
|||||||
---
|
|
||||||
name: Feature request
|
|
||||||
about: Suggest an idea for Hydra. Write in English, please
|
|
||||||
title: "[REQUEST]"
|
|
||||||
labels: enhancement
|
|
||||||
assignees: ""
|
|
||||||
---
|
|
||||||
|
|
||||||
**Is your feature request related to a problem? Please describe.**
|
|
||||||
A clear and concise description of what the problem is.
|
|
||||||
|
|
||||||
**Describe the solution you'd like**
|
|
||||||
A clear and concise description of what you want to happen.
|
|
||||||
|
|
||||||
**Describe alternatives you've considered**
|
|
||||||
A clear and concise description of any alternative solutions or features you've considered.
|
|
||||||
|
|
||||||
**Additional context**
|
|
||||||
Add any other context or screenshots about the feature request here.
|
|
||||||
37
.github/ISSUE_TEMPLATE/feature_request.yml
vendored
Normal file
37
.github/ISSUE_TEMPLATE/feature_request.yml
vendored
Normal file
@@ -0,0 +1,37 @@
|
|||||||
|
name: Feature Request
|
||||||
|
description: Request a new feature.
|
||||||
|
title: "[REQUEST] "
|
||||||
|
labels: ["enhancement"]
|
||||||
|
body:
|
||||||
|
- type: markdown
|
||||||
|
attributes:
|
||||||
|
value: |
|
||||||
|
Thank you for taking the time to suggest a new feature!
|
||||||
|
- type: textarea
|
||||||
|
id: problem-related
|
||||||
|
attributes:
|
||||||
|
label: Is your feature request related to a problem? Please describe.
|
||||||
|
description: A clear and concise description of what the problem is.
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: solution
|
||||||
|
attributes:
|
||||||
|
label: Describe the solution you'd like
|
||||||
|
description: A clear and concise description of what you want to happen.
|
||||||
|
validations:
|
||||||
|
required: true
|
||||||
|
- type: textarea
|
||||||
|
id: alternatives
|
||||||
|
attributes:
|
||||||
|
label: Describe alternatives you've considered
|
||||||
|
description: A clear and concise description of any alternative solutions or features you've considered.
|
||||||
|
validations:
|
||||||
|
required: false
|
||||||
|
- type: textarea
|
||||||
|
id: additional-context
|
||||||
|
attributes:
|
||||||
|
label: Additional context
|
||||||
|
description: Add any other context or screenshots about the feature request here.
|
||||||
|
validations:
|
||||||
|
required: false
|
||||||
3
.github/workflows/lint.yml
vendored
3
.github/workflows/lint.yml
vendored
@@ -26,3 +26,6 @@ jobs:
|
|||||||
|
|
||||||
- name: Lint
|
- name: Lint
|
||||||
run: yarn lint
|
run: yarn lint
|
||||||
|
|
||||||
|
- name: Format check
|
||||||
|
run: yarn format-check
|
||||||
|
|||||||
@@ -19,7 +19,6 @@
|
|||||||
[](README.uk-UA.md)
|
[](README.uk-UA.md)
|
||||||
[](README.be.md)
|
[](README.be.md)
|
||||||
|
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
10
package.json
10
package.json
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "hydra",
|
"name": "hydra",
|
||||||
"version": "1.2.0",
|
"version": "1.2.2",
|
||||||
"description": "Hydra",
|
"description": "Hydra",
|
||||||
"main": "./out/main/index.js",
|
"main": "./out/main/index.js",
|
||||||
"author": "Los Broxas",
|
"author": "Los Broxas",
|
||||||
@@ -10,8 +10,13 @@
|
|||||||
"url": "https://github.com/hydralauncher/hydra.git"
|
"url": "https://github.com/hydralauncher/hydra.git"
|
||||||
},
|
},
|
||||||
"type": "module",
|
"type": "module",
|
||||||
|
"engines": {
|
||||||
|
"npm": "please-use-yarn",
|
||||||
|
"yarn": ">= 1.19.1"
|
||||||
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"format": "prettier --write .",
|
"format": "prettier --write .",
|
||||||
|
"format-check": "prettier --check .",
|
||||||
"lint": "eslint . --ext .js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix",
|
"lint": "eslint . --ext .js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix",
|
||||||
"typecheck:node": "tsc --noEmit -p tsconfig.node.json --composite false",
|
"typecheck:node": "tsc --noEmit -p tsconfig.node.json --composite false",
|
||||||
"typecheck:web": "tsc --noEmit -p tsconfig.web.json --composite false",
|
"typecheck:web": "tsc --noEmit -p tsconfig.web.json --composite false",
|
||||||
@@ -24,7 +29,8 @@
|
|||||||
"build:win": "electron-vite build && electron-builder --win",
|
"build:win": "electron-vite build && electron-builder --win",
|
||||||
"build:mac": "electron-vite build && electron-builder --mac",
|
"build:mac": "electron-vite build && electron-builder --mac",
|
||||||
"build:linux": "electron-vite build && electron-builder --linux",
|
"build:linux": "electron-vite build && electron-builder --linux",
|
||||||
"prepare": "husky"
|
"prepare": "husky",
|
||||||
|
"typeorm:migration-create": "yarn typeorm migration:create"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@electron-toolkit/preload": "^3.0.0",
|
"@electron-toolkit/preload": "^3.0.0",
|
||||||
|
|||||||
@@ -24,12 +24,12 @@
|
|||||||
"github": "Contribuye en GitHub"
|
"github": "Contribuye en GitHub"
|
||||||
},
|
},
|
||||||
"header": {
|
"header": {
|
||||||
"search": "Buscar",
|
"search": "Buscar juegos",
|
||||||
|
"home": "Inicio",
|
||||||
"catalogue": "Catálogo",
|
"catalogue": "Catálogo",
|
||||||
"downloads": "Descargas",
|
"downloads": "Descargas",
|
||||||
"search_results": "Resultados de búsqueda",
|
"search_results": "Resultados de búsqueda",
|
||||||
"settings": "Ajustes",
|
"settings": "Ajustes"
|
||||||
"home": "Inicio"
|
|
||||||
},
|
},
|
||||||
"bottom_panel": {
|
"bottom_panel": {
|
||||||
"no_downloads_in_progress": "Sin descargas en progreso",
|
"no_downloads_in_progress": "Sin descargas en progreso",
|
||||||
@@ -37,12 +37,17 @@
|
|||||||
"checking_files": "Analizando archivos de {{title}} - ({{percentage}} completado)",
|
"checking_files": "Analizando archivos de {{title}} - ({{percentage}} completado)",
|
||||||
"downloading": "Descargando {{title}}… ({{percentage}} completado) - Finalizando {{eta}} - {{speed}}"
|
"downloading": "Descargando {{title}}… ({{percentage}} completado) - Finalizando {{eta}} - {{speed}}"
|
||||||
},
|
},
|
||||||
|
"catalogue": {
|
||||||
|
"next_page": "Siguiente página",
|
||||||
|
"previous_page": "Pagina anterior"
|
||||||
|
},
|
||||||
"game_details": {
|
"game_details": {
|
||||||
"open_download_options": "Ver opciones de descargas",
|
"open_download_options": "Ver opciones de descargas",
|
||||||
"download_options_zero": "No hay opciones de descargas disponibles",
|
"download_options_zero": "No hay opciones de descargas disponibles",
|
||||||
"download_options_one": "{{count}} opción de descarga",
|
"download_options_one": "{{count}} opción de descarga",
|
||||||
"download_options_other": "{{count}} opciones de descargas",
|
"download_options_other": "{{count}} opciones de descargas",
|
||||||
"updated_at": "Actualizado el {{updated_at}}",
|
"updated_at": "Actualizado el {{updated_at}}",
|
||||||
|
"install": "Instalar",
|
||||||
"resume": "Continuar",
|
"resume": "Continuar",
|
||||||
"pause": "Pausa",
|
"pause": "Pausa",
|
||||||
"cancel": "Cancelar",
|
"cancel": "Cancelar",
|
||||||
@@ -52,7 +57,7 @@
|
|||||||
"eta": "Finalizando en {{eta}}",
|
"eta": "Finalizando en {{eta}}",
|
||||||
"downloading_metadata": "Descargando metadatos…",
|
"downloading_metadata": "Descargando metadatos…",
|
||||||
"checking_files": "Analizando archivos…",
|
"checking_files": "Analizando archivos…",
|
||||||
"filter": "Filtrar repacks",
|
"filter": "Buscar repacks",
|
||||||
"requirements": "Requisitos del Sistema",
|
"requirements": "Requisitos del Sistema",
|
||||||
"minimum": "Mínimos",
|
"minimum": "Mínimos",
|
||||||
"recommended": "Recomendados",
|
"recommended": "Recomendados",
|
||||||
@@ -71,20 +76,17 @@
|
|||||||
"add_to_library": "Agregar a la biblioteca",
|
"add_to_library": "Agregar a la biblioteca",
|
||||||
"remove_from_library": "Eliminar de la biblioteca",
|
"remove_from_library": "Eliminar de la biblioteca",
|
||||||
"no_downloads": "No hay descargas disponibles",
|
"no_downloads": "No hay descargas disponibles",
|
||||||
"next_suggestion": "Siguiente sugerencia",
|
|
||||||
"play_time": "Jugado por {{amount}}",
|
"play_time": "Jugado por {{amount}}",
|
||||||
"install": "Instalar",
|
|
||||||
"play": "Jugar",
|
|
||||||
"not_played_yet": "Aún no has jugado a {{title}}",
|
|
||||||
"close": "Cerrar",
|
|
||||||
"deleting": "Eliminando instalador…",
|
|
||||||
"playing_now": "Jugando ahora",
|
|
||||||
"last_time_played": "Jugado por última vez {{period}}",
|
"last_time_played": "Jugado por última vez {{period}}",
|
||||||
"got_it": "Entendido",
|
"not_played_yet": "Aún no has jugado a {{title}}",
|
||||||
|
"next_suggestion": "Siguiente sugerencia",
|
||||||
|
"play": "Jugar",
|
||||||
|
"deleting": "Eliminando instalador…",
|
||||||
|
"close": "Cerrar",
|
||||||
|
"playing_now": "Jugando ahora",
|
||||||
"change": "Cambiar",
|
"change": "Cambiar",
|
||||||
"repacks_modal_description": "Selecciona el repack que quieres descargar",
|
"repacks_modal_description": "Selecciona el repack que quieres descargar",
|
||||||
"downloads_path": "Ruta de descarga",
|
"select_folder_hint": "Para cambiar la carpeta predeterminada, ve a <0>Ajustes</0>",
|
||||||
"select_folder_hint": "Para cambiar la carpeta predeterminada, accede a",
|
|
||||||
"download_now": "Descargar ahora",
|
"download_now": "Descargar ahora",
|
||||||
"installation_instructions": "Instrucciones de instalación",
|
"installation_instructions": "Instrucciones de instalación",
|
||||||
"installation_instructions_description": "Se requieren de pasos adicionales para instalar este juego",
|
"installation_instructions_description": "Se requieren de pasos adicionales para instalar este juego",
|
||||||
@@ -92,7 +94,15 @@
|
|||||||
"dodi_installation_instruction": "Cuando abras el instalador de DODI, presiona la tecla hacia arriba del teclado <0 /> para iniciar el proceso de instalación:",
|
"dodi_installation_instruction": "Cuando abras el instalador de DODI, presiona la tecla hacia arriba del teclado <0 /> para iniciar el proceso de instalación:",
|
||||||
"dont_show_it_again": "No mostrar de nuevo",
|
"dont_show_it_again": "No mostrar de nuevo",
|
||||||
"copy_to_clipboard": "Copiar",
|
"copy_to_clipboard": "Copiar",
|
||||||
"copied_to_clipboard": "Copiado"
|
"copied_to_clipboard": "Copiado",
|
||||||
|
"got_it": "Entendido",
|
||||||
|
"no_shop_details": "No se pudieron obtener detalles de la tienda.",
|
||||||
|
"download_options": "Opciones de descarga",
|
||||||
|
"download_path": "Ruta de descarga",
|
||||||
|
"previous_screenshot": "Anterior captura",
|
||||||
|
"next_screenshot": "Siguiente captura",
|
||||||
|
"screenshot": "Captura {{number}}",
|
||||||
|
"open_screenshot": "Abrir captura {{number}}"
|
||||||
},
|
},
|
||||||
"activation": {
|
"activation": {
|
||||||
"title": "Activar Hydra",
|
"title": "Activar Hydra",
|
||||||
@@ -118,12 +128,14 @@
|
|||||||
"downloading_metadata": "Descargando metadatos…",
|
"downloading_metadata": "Descargando metadatos…",
|
||||||
"checking_files": "Verificando archivos…",
|
"checking_files": "Verificando archivos…",
|
||||||
"starting_download": "Iniciando descarga…",
|
"starting_download": "Iniciando descarga…",
|
||||||
"remove_from_list": "Eliminar",
|
|
||||||
"delete": "Eliminar instalador",
|
|
||||||
"delete_modal_description": "Esto eliminará todos los archivos de instalación de tu computadora.",
|
|
||||||
"delete_modal_title": "¿Estás seguro?",
|
|
||||||
"deleting": "Eliminando instalador…",
|
"deleting": "Eliminando instalador…",
|
||||||
"install": "Instalar"
|
"delete": "Eliminar instalador",
|
||||||
|
"remove_from_list": "Eliminar",
|
||||||
|
"delete_modal_title": "¿Estás seguro?",
|
||||||
|
"delete_modal_description": "Esto eliminará todos los archivos de instalación de tu computadora.",
|
||||||
|
"install": "Instalar",
|
||||||
|
"real_debrid": "Real Debrid",
|
||||||
|
"torrent": "Torrent"
|
||||||
},
|
},
|
||||||
"settings": {
|
"settings": {
|
||||||
"downloads_path": "Ruta de descarga",
|
"downloads_path": "Ruta de descarga",
|
||||||
@@ -132,7 +144,16 @@
|
|||||||
"enable_download_notifications": "Cuando se completa una descarga",
|
"enable_download_notifications": "Cuando se completa una descarga",
|
||||||
"enable_repack_list_notifications": "Cuando se añade un repack nuevo",
|
"enable_repack_list_notifications": "Cuando se añade un repack nuevo",
|
||||||
"telemetry": "Telemetría",
|
"telemetry": "Telemetría",
|
||||||
"telemetry_description": "Habilitar recopilación de datos de manera anónima"
|
"telemetry_description": "Habilitar recopilación de datos de manera anónima",
|
||||||
|
"real_debrid_api_token_label": "Token API de Real Debrid",
|
||||||
|
"quit_app_instead_hiding": "Salir de Hydra en vez de minimizar en la bandeja del sistema",
|
||||||
|
"launch_with_system": "Iniciar Hydra al inicio del sistema",
|
||||||
|
"general": "General",
|
||||||
|
"behavior": "Otros",
|
||||||
|
"enable_real_debrid": "Activar Real Debrid",
|
||||||
|
"real_debrid": "Real Debrid",
|
||||||
|
"real_debrid_api_token_hint": "Puedes obtener tu clave de API <0>aquí</0>.",
|
||||||
|
"save_changes": "Guardar cambios"
|
||||||
},
|
},
|
||||||
"notifications": {
|
"notifications": {
|
||||||
"download_complete": "Descarga completada",
|
"download_complete": "Descarga completada",
|
||||||
@@ -155,9 +176,5 @@
|
|||||||
},
|
},
|
||||||
"modal": {
|
"modal": {
|
||||||
"close": "Botón de cierre"
|
"close": "Botón de cierre"
|
||||||
},
|
|
||||||
"catalogue": {
|
|
||||||
"next_page": "Siguiente página",
|
|
||||||
"previous_page": "Pagina anterior"
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,7 +15,7 @@
|
|||||||
"checking_files": "{{title}} ({{percentage}} - 파일 검사 중…)",
|
"checking_files": "{{title}} ({{percentage}} - 파일 검사 중…)",
|
||||||
"paused": "{{title}} (일시 정지됨)",
|
"paused": "{{title}} (일시 정지됨)",
|
||||||
"downloading": "{{title}} ({{percentage}} - 다운로드 중…)",
|
"downloading": "{{title}} ({{percentage}} - 다운로드 중…)",
|
||||||
"filter": "필터 라이브러리",
|
"filter": "라이브러리 정렬",
|
||||||
"follow_us": "공식 SNS",
|
"follow_us": "공식 SNS",
|
||||||
"home": "홈",
|
"home": "홈",
|
||||||
"discord": "공식 디스코드",
|
"discord": "공식 디스코드",
|
||||||
@@ -54,10 +54,10 @@
|
|||||||
"remove": "제거",
|
"remove": "제거",
|
||||||
"remove_from_list": "목록에서 제거",
|
"remove_from_list": "목록에서 제거",
|
||||||
"space_left_on_disk": "여유 저장 용량 {{space}} 남음",
|
"space_left_on_disk": "여유 저장 용량 {{space}} 남음",
|
||||||
"eta": "왼료까지 {{eta}}",
|
"eta": "완료까지 {{eta}}",
|
||||||
"downloading_metadata": "메타데이터 다운로드 중…",
|
"downloading_metadata": "메타데이터 다운로드 중…",
|
||||||
"checking_files": "파일 검사 중…",
|
"checking_files": "파일 검사 중…",
|
||||||
"filter": "리팩들을 다음과 같이 걸러내기",
|
"filter": "리팩들을 다음과 같이 정렬하기",
|
||||||
"requirements": "시스템 사양",
|
"requirements": "시스템 사양",
|
||||||
"minimum": "최저 사양",
|
"minimum": "최저 사양",
|
||||||
"recommended": "권장 사양",
|
"recommended": "권장 사양",
|
||||||
@@ -91,8 +91,8 @@
|
|||||||
"download_now": "지금 다운로드",
|
"download_now": "지금 다운로드",
|
||||||
"installation_instructions": "설치 방법",
|
"installation_instructions": "설치 방법",
|
||||||
"installation_instructions_description": "이 게임을 설치하기 위해서는 추가적인 단계가 필요합니다",
|
"installation_instructions_description": "이 게임을 설치하기 위해서는 추가적인 단계가 필요합니다",
|
||||||
"online_fix_instruction": "OnlineFix 게임들은 추출 시 암호가 필요합니다. 비밀번호를 물을 때 다음을 암호로 사용하기:",
|
"online_fix_instruction": "OnlineFix 게임들은 압축 해제 시 암호가 필요합니다. 비밀번호를 물을 때 다음을 암호로 사용하기:",
|
||||||
"dodi_installation_instruction": "DODI 인스톨러를 열었다면 키보드의 위 방향키를 눌러 설치를 시작하세요:",
|
"dodi_installation_instruction": "DODI 인스톨러를 실행했다면 키보드의 위 방향키를 눌러 설치를 시작하세요:",
|
||||||
"dont_show_it_again": "다시 보지 않기",
|
"dont_show_it_again": "다시 보지 않기",
|
||||||
"copy_to_clipboard": "복사하기",
|
"copy_to_clipboard": "복사하기",
|
||||||
"copied_to_clipboard": "복사됨",
|
"copied_to_clipboard": "복사됨",
|
||||||
|
|||||||
@@ -17,7 +17,11 @@
|
|||||||
"downloading": "{{title}} ({{percentage}} - Pobieranie…)",
|
"downloading": "{{title}} ({{percentage}} - Pobieranie…)",
|
||||||
"filter": "Filtruj biblioteke",
|
"filter": "Filtruj biblioteke",
|
||||||
"follow_us": "Śledź nas",
|
"follow_us": "Śledź nas",
|
||||||
"home": "Główna"
|
"home": "Główna",
|
||||||
|
"discord": "Dołącz nasz Discord",
|
||||||
|
"telegram": "Dołącz nasz Telegram",
|
||||||
|
"x": "Śledź na X",
|
||||||
|
"github": "Przyczyń się na GitHub"
|
||||||
},
|
},
|
||||||
"header": {
|
"header": {
|
||||||
"search": "Szukaj",
|
"search": "Szukaj",
|
||||||
@@ -66,6 +70,8 @@
|
|||||||
"copied_link_to_clipboard": "Skopiowano łącze",
|
"copied_link_to_clipboard": "Skopiowano łącze",
|
||||||
"hours": "godzin",
|
"hours": "godzin",
|
||||||
"minutes": "minut",
|
"minutes": "minut",
|
||||||
|
"amount_hours": "{{amount}} godzin",
|
||||||
|
"amount_minutes": "{{amount}} minut",
|
||||||
"accuracy": "{{accuracy}}% dokładność",
|
"accuracy": "{{accuracy}}% dokładność",
|
||||||
"add_to_library": "Dodaj do biblioteki",
|
"add_to_library": "Dodaj do biblioteki",
|
||||||
"remove_from_library": "Usuń z biblioteki",
|
"remove_from_library": "Usuń z biblioteki",
|
||||||
@@ -80,9 +86,23 @@
|
|||||||
"playing_now": "Granie teraz",
|
"playing_now": "Granie teraz",
|
||||||
"change": "Zmień",
|
"change": "Zmień",
|
||||||
"repacks_modal_description": "Wybierz repack, który chcesz pobrać",
|
"repacks_modal_description": "Wybierz repack, który chcesz pobrać",
|
||||||
"downloads_path": "Ścieżka pobierania",
|
|
||||||
"select_folder_hint": "Aby zmienić domyślny folder, przejdź do",
|
"select_folder_hint": "Aby zmienić domyślny folder, przejdź do",
|
||||||
"download_now": "Pobierz teraz"
|
"download_now": "Pobierz teraz",
|
||||||
|
"installation_instructions": "Instrukcja instalacji",
|
||||||
|
"installation_instructions_description": "Do zainstalowania tej gry wymagane są dodatkowe kroki",
|
||||||
|
"online_fix_instruction": "Gry OnlineFix wymagają hasła do wyodrębnienia. W razie potrzeby użyj następującego hasła:",
|
||||||
|
"dodi_installation_instruction": "Po otwarciu instalatora DODI naciśnij klawisz <0 /> w górę, aby rozpocząć proces instalacji:",
|
||||||
|
"dont_show_it_again": "Nie pokazuj tego ponownie",
|
||||||
|
"copy_to_clipboard": "Skopiuj",
|
||||||
|
"copied_to_clipboard": "Skopiowano",
|
||||||
|
"got_it": "Rozumiem",
|
||||||
|
"no_shop_details": "Nie udało się pobrać danych sklepu.",
|
||||||
|
"download_options": "Opcje pobierania",
|
||||||
|
"download_path": "Ścieżka pobierania",
|
||||||
|
"previous_screenshot": "Poprzedni zrzut ekranu",
|
||||||
|
"next_screenshot": "Następny zrzut ekranu",
|
||||||
|
"screenshot": "Zrzut ekranu {{number}}",
|
||||||
|
"open_screenshot": "Otwórz zrzut ekranu {{number}}"
|
||||||
},
|
},
|
||||||
"activation": {
|
"activation": {
|
||||||
"title": "Aktywuj Hydra",
|
"title": "Aktywuj Hydra",
|
||||||
@@ -113,7 +133,9 @@
|
|||||||
"remove_from_list": "Usuń",
|
"remove_from_list": "Usuń",
|
||||||
"delete_modal_title": "Czy na pewno?",
|
"delete_modal_title": "Czy na pewno?",
|
||||||
"delete_modal_description": "Spowoduje to usunięcie wszystkich plików instalacyjnych z komputera",
|
"delete_modal_description": "Spowoduje to usunięcie wszystkich plików instalacyjnych z komputera",
|
||||||
"install": "Instaluj"
|
"install": "Instaluj",
|
||||||
|
"real_debrid": "Real Debrid",
|
||||||
|
"torrent": "Torrent"
|
||||||
},
|
},
|
||||||
"settings": {
|
"settings": {
|
||||||
"downloads_path": "Ścieżka pobierania",
|
"downloads_path": "Ścieżka pobierania",
|
||||||
@@ -122,7 +144,16 @@
|
|||||||
"enable_download_notifications": "Gdy pobieranie zostanie zakończone",
|
"enable_download_notifications": "Gdy pobieranie zostanie zakończone",
|
||||||
"enable_repack_list_notifications": "Gdy dodawany jest nowy repack",
|
"enable_repack_list_notifications": "Gdy dodawany jest nowy repack",
|
||||||
"telemetry": "Telemetria",
|
"telemetry": "Telemetria",
|
||||||
"telemetry_description": "Włącz anonimowe statystyki użycia"
|
"telemetry_description": "Włącz anonimowe statystyki użycia",
|
||||||
|
"real_debrid_api_token_label": "Real Debrid API token",
|
||||||
|
"quit_app_instead_hiding": "Zamknij Hydr zamiast minimalizować do zasobnika",
|
||||||
|
"launch_with_system": "Uruchom Hydra przy starcie systemu",
|
||||||
|
"general": "Ogólne",
|
||||||
|
"behavior": "Zachowania",
|
||||||
|
"enable_real_debrid": "Włącz Real Debrid",
|
||||||
|
"real_debrid": "Real Debrid",
|
||||||
|
"real_debrid_api_token_hint": "Możesz uzyskać swój klucz API <0>tutaj</0>.",
|
||||||
|
"save_changes": "Zapisz zmiany"
|
||||||
},
|
},
|
||||||
"notifications": {
|
"notifications": {
|
||||||
"download_complete": "Pobieranie zakończone",
|
"download_complete": "Pobieranie zakończone",
|
||||||
@@ -142,5 +173,8 @@
|
|||||||
"title": "Programy nie są zainstalowane",
|
"title": "Programy nie są zainstalowane",
|
||||||
"description": "Pliki wykonywalne Wine lub Lutris nie zostały znalezione na twoim systemie",
|
"description": "Pliki wykonywalne Wine lub Lutris nie zostały znalezione na twoim systemie",
|
||||||
"instructions": "Sprawdź prawidłowy sposób instalacji dowolnego z nich w swojej dystrybucji Linuksa, aby gra działała normalnie"
|
"instructions": "Sprawdź prawidłowy sposób instalacji dowolnego z nich w swojej dystrybucji Linuksa, aby gra działała normalnie"
|
||||||
|
},
|
||||||
|
"modal": {
|
||||||
|
"close": "Zamknij"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -152,7 +152,7 @@
|
|||||||
"behavior": "Поведение",
|
"behavior": "Поведение",
|
||||||
"enable_real_debrid": "Включить Real Debrid",
|
"enable_real_debrid": "Включить Real Debrid",
|
||||||
"real_debrid": "Real Debrid",
|
"real_debrid": "Real Debrid",
|
||||||
"real_debrid_api_token_hint": "API ключ можно получить <0>здесь/0>.",
|
"real_debrid_api_token_hint": "API ключ можно получить <0>здесь</0>.",
|
||||||
"save_changes": "Сохранить изменения"
|
"save_changes": "Сохранить изменения"
|
||||||
},
|
},
|
||||||
"notifications": {
|
"notifications": {
|
||||||
|
|||||||
@@ -150,7 +150,7 @@
|
|||||||
"launch_with_system": "随系统启动时运行应用程序",
|
"launch_with_system": "随系统启动时运行应用程序",
|
||||||
"enable_real_debrid": "启用 Real Debrid",
|
"enable_real_debrid": "启用 Real Debrid",
|
||||||
"real_debrid": "Real Debrid",
|
"real_debrid": "Real Debrid",
|
||||||
"real_debrid_api_token_hint": "您可以将API密钥填入<0>这里</0>.",
|
"real_debrid_api_token_hint": "您可以从<0>这里</0>获取API密钥.",
|
||||||
"save_changes": "保存更改"
|
"save_changes": "保存更改"
|
||||||
},
|
},
|
||||||
"notifications": {
|
"notifications": {
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import {
|
|||||||
import type { SqliteConnectionOptions } from "typeorm/driver/sqlite/SqliteConnectionOptions";
|
import type { SqliteConnectionOptions } from "typeorm/driver/sqlite/SqliteConnectionOptions";
|
||||||
|
|
||||||
import { databasePath } from "./constants";
|
import { databasePath } from "./constants";
|
||||||
|
import migrations from "./migrations";
|
||||||
|
|
||||||
export const createDataSource = (options: Partial<SqliteConnectionOptions>) =>
|
export const createDataSource = (options: Partial<SqliteConnectionOptions>) =>
|
||||||
new DataSource({
|
new DataSource({
|
||||||
@@ -19,4 +20,6 @@ export const createDataSource = (options: Partial<SqliteConnectionOptions>) =>
|
|||||||
...options,
|
...options,
|
||||||
});
|
});
|
||||||
|
|
||||||
export const dataSource = createDataSource({});
|
export const dataSource = createDataSource({
|
||||||
|
migrations: migrations,
|
||||||
|
});
|
||||||
|
|||||||
@@ -19,6 +19,8 @@ autoUpdater.setFeedURL({
|
|||||||
const gotTheLock = app.requestSingleInstanceLock();
|
const gotTheLock = app.requestSingleInstanceLock();
|
||||||
if (!gotTheLock) app.quit();
|
if (!gotTheLock) app.quit();
|
||||||
|
|
||||||
|
app.disableHardwareAcceleration();
|
||||||
|
|
||||||
i18n.init({
|
i18n.init({
|
||||||
resources,
|
resources,
|
||||||
lng: "en",
|
lng: "en",
|
||||||
@@ -51,6 +53,8 @@ app.whenReady().then(() => {
|
|||||||
);
|
);
|
||||||
|
|
||||||
dataSource.initialize().then(async () => {
|
dataSource.initialize().then(async () => {
|
||||||
|
await dataSource.runMigrations();
|
||||||
|
|
||||||
await resolveDatabaseUpdates();
|
await resolveDatabaseUpdates();
|
||||||
|
|
||||||
await import("./main");
|
await import("./main");
|
||||||
|
|||||||
78
src/main/migrations/1715900413313-fix_repack_uploadDate.ts
Normal file
78
src/main/migrations/1715900413313-fix_repack_uploadDate.ts
Normal file
@@ -0,0 +1,78 @@
|
|||||||
|
import { createDataSource } from "@main/data-source";
|
||||||
|
import { Repack } from "@main/entity";
|
||||||
|
import { app } from "electron";
|
||||||
|
import { chunk } from "lodash-es";
|
||||||
|
import path from "path";
|
||||||
|
import { In, MigrationInterface, QueryRunner, Table } from "typeorm";
|
||||||
|
|
||||||
|
export class FixRepackUploadDate1715900413313 implements MigrationInterface {
|
||||||
|
public async up(queryRunner: QueryRunner): Promise<void> {
|
||||||
|
await queryRunner.createTable(
|
||||||
|
new Table({
|
||||||
|
name: "repack_temp",
|
||||||
|
columns: [
|
||||||
|
{ name: "title", type: "varchar" },
|
||||||
|
{ name: "old_id", type: "int" },
|
||||||
|
],
|
||||||
|
}),
|
||||||
|
true
|
||||||
|
);
|
||||||
|
|
||||||
|
await queryRunner.query(
|
||||||
|
`INSERT INTO repack_temp (title, old_id) SELECT title, id FROM repack WHERE repacker IN ('onlinefix', 'Xatab');`
|
||||||
|
);
|
||||||
|
|
||||||
|
await queryRunner.query(
|
||||||
|
`DELETE FROM repack WHERE repacker IN ('onlinefix', 'Xatab');`
|
||||||
|
);
|
||||||
|
|
||||||
|
const updateDataSource = createDataSource({
|
||||||
|
database: app.isPackaged
|
||||||
|
? path.join(process.resourcesPath, "hydra.db")
|
||||||
|
: path.join(__dirname, "..", "..", "hydra.db"),
|
||||||
|
});
|
||||||
|
|
||||||
|
await updateDataSource.initialize();
|
||||||
|
|
||||||
|
const updateRepackRepository = updateDataSource.getRepository(Repack);
|
||||||
|
|
||||||
|
const updatedRepacks = await updateRepackRepository.find({
|
||||||
|
where: {
|
||||||
|
repacker: In(["onlinefix", "Xatab"]),
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
const chunks = chunk(
|
||||||
|
updatedRepacks.map((repack) => {
|
||||||
|
const { id: _, ...rest } = repack;
|
||||||
|
return rest;
|
||||||
|
}),
|
||||||
|
500
|
||||||
|
);
|
||||||
|
|
||||||
|
for (const chunk of chunks) {
|
||||||
|
await queryRunner.manager
|
||||||
|
.createQueryBuilder(Repack, "repack")
|
||||||
|
.insert()
|
||||||
|
.values(chunk)
|
||||||
|
.orIgnore()
|
||||||
|
.execute();
|
||||||
|
}
|
||||||
|
|
||||||
|
await queryRunner.query(
|
||||||
|
`UPDATE game
|
||||||
|
SET repackId = (
|
||||||
|
SELECT id
|
||||||
|
from repack LEFT JOIN repack_temp ON repack_temp.title = repack.title
|
||||||
|
WHERE repack_temp.old_id = game.repackId
|
||||||
|
)
|
||||||
|
WHERE EXISTS (select old_id from repack_temp WHERE old_id = game.repackId)`
|
||||||
|
);
|
||||||
|
|
||||||
|
await queryRunner.dropTable("repack_temp");
|
||||||
|
}
|
||||||
|
|
||||||
|
public async down(_: QueryRunner): Promise<void> {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
3
src/main/migrations/index.ts
Normal file
3
src/main/migrations/index.ts
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
import { FixRepackUploadDate1715900413313 } from "./1715900413313-fix_repack_uploadDate";
|
||||||
|
|
||||||
|
export default [FixRepackUploadDate1715900413313];
|
||||||
@@ -3,21 +3,19 @@ import { decodeNonUtf8Response, savePage } from "./helpers";
|
|||||||
import { logger } from "../logger";
|
import { logger } from "../logger";
|
||||||
import { JSDOM } from "jsdom";
|
import { JSDOM } from "jsdom";
|
||||||
|
|
||||||
import { format, parse, sub } from "date-fns";
|
|
||||||
import { ru } from "date-fns/locale";
|
|
||||||
|
|
||||||
import createWorker from "@main/workers/torrent-parser.worker?nodeWorker";
|
import createWorker from "@main/workers/torrent-parser.worker?nodeWorker";
|
||||||
import { toMagnetURI } from "parse-torrent";
|
import { toMagnetURI } from "parse-torrent";
|
||||||
|
|
||||||
const worker = createWorker({});
|
const worker = createWorker({});
|
||||||
|
|
||||||
import { onlinefixFormatter } from "@main/helpers";
|
|
||||||
import makeFetchCookie from "fetch-cookie";
|
import makeFetchCookie from "fetch-cookie";
|
||||||
import { QueryDeepPartialEntity } from "typeorm/query-builder/QueryPartialEntity";
|
import { QueryDeepPartialEntity } from "typeorm/query-builder/QueryPartialEntity";
|
||||||
import { formatBytes } from "@shared";
|
import { formatBytes } from "@shared";
|
||||||
|
|
||||||
const ONLINE_FIX_URL = "https://online-fix.me/";
|
const ONLINE_FIX_URL = "https://online-fix.me/";
|
||||||
|
|
||||||
|
let totalPages = 1;
|
||||||
|
|
||||||
export const getNewRepacksFromOnlineFix = async (
|
export const getNewRepacksFromOnlineFix = async (
|
||||||
existingRepacks: Repack[] = [],
|
existingRepacks: Repack[] = [],
|
||||||
page = 1,
|
page = 1,
|
||||||
@@ -74,18 +72,16 @@ export const getNewRepacksFromOnlineFix = async (
|
|||||||
|
|
||||||
const repacks: QueryDeepPartialEntity<Repack>[] = [];
|
const repacks: QueryDeepPartialEntity<Repack>[] = [];
|
||||||
const articles = Array.from(document.querySelectorAll(".news"));
|
const articles = Array.from(document.querySelectorAll(".news"));
|
||||||
const totalPages = Number(
|
|
||||||
document.querySelector("nav > a:nth-child(13)")?.textContent
|
if (page == 1) {
|
||||||
);
|
totalPages = Number(
|
||||||
|
document.querySelector("nav > a:nth-child(13)")?.textContent
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await Promise.all(
|
await Promise.all(
|
||||||
articles.map(async (article) => {
|
articles.map(async (article) => {
|
||||||
const gameText = article.querySelector("h2.title")?.textContent?.trim();
|
|
||||||
if (!gameText) return;
|
|
||||||
|
|
||||||
const gameName = onlinefixFormatter(gameText);
|
|
||||||
|
|
||||||
const gameLink = article.querySelector("a")?.getAttribute("href");
|
const gameLink = article.querySelector("a")?.getAttribute("href");
|
||||||
if (!gameLink) return;
|
if (!gameLink) return;
|
||||||
|
|
||||||
@@ -94,32 +90,6 @@ export const getNewRepacksFromOnlineFix = async (
|
|||||||
);
|
);
|
||||||
const gameDocument = new JSDOM(gamePage).window.document;
|
const gameDocument = new JSDOM(gamePage).window.document;
|
||||||
|
|
||||||
const uploadDateText = gameDocument.querySelector("time")?.textContent;
|
|
||||||
if (!uploadDateText) return;
|
|
||||||
|
|
||||||
let decodedDateText = uploadDateText;
|
|
||||||
|
|
||||||
// "Вчера" means yesterday.
|
|
||||||
if (decodedDateText.includes("Вчера")) {
|
|
||||||
const yesterday = sub(new Date(), { days: 1 });
|
|
||||||
const formattedYesterday = format(yesterday, "d LLLL yyyy", {
|
|
||||||
locale: ru,
|
|
||||||
});
|
|
||||||
decodedDateText = decodedDateText.replace(
|
|
||||||
"Вчера", // "Change yesterday to the default expected date format"
|
|
||||||
formattedYesterday
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
const uploadDate = parse(
|
|
||||||
decodedDateText,
|
|
||||||
"d LLLL yyyy, HH:mm",
|
|
||||||
new Date(),
|
|
||||||
{
|
|
||||||
locale: ru,
|
|
||||||
}
|
|
||||||
);
|
|
||||||
|
|
||||||
const torrentButtons = Array.from(
|
const torrentButtons = Array.from(
|
||||||
gameDocument.querySelectorAll("a")
|
gameDocument.querySelectorAll("a")
|
||||||
).filter((a) => a.textContent?.includes("Torrent"));
|
).filter((a) => a.textContent?.includes("Torrent"));
|
||||||
@@ -146,13 +116,17 @@ export const getNewRepacksFromOnlineFix = async (
|
|||||||
);
|
);
|
||||||
|
|
||||||
worker.once("message", (torrent) => {
|
worker.once("message", (torrent) => {
|
||||||
|
if (!torrent) return;
|
||||||
|
|
||||||
|
const { name, created } = torrent;
|
||||||
|
|
||||||
repacks.push({
|
repacks.push({
|
||||||
fileSize: formatBytes(torrent.length ?? 0),
|
fileSize: formatBytes(torrent.length ?? 0),
|
||||||
magnet: toMagnetURI(torrent),
|
magnet: toMagnetURI(torrent),
|
||||||
page: 1,
|
page: 1,
|
||||||
repacker: "onlinefix",
|
repacker: "onlinefix",
|
||||||
title: gameName,
|
title: name,
|
||||||
uploadDate: uploadDate,
|
uploadDate: created,
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,9 @@ import { formatBytes } from "@shared";
|
|||||||
import { getFileBuffer } from "@main/helpers";
|
import { getFileBuffer } from "@main/helpers";
|
||||||
|
|
||||||
const worker = createWorker({});
|
const worker = createWorker({});
|
||||||
|
worker.setMaxListeners(11);
|
||||||
|
|
||||||
|
let totalPages = 1;
|
||||||
|
|
||||||
const formatXatabDate = (str: string) => {
|
const formatXatabDate = (str: string) => {
|
||||||
const date = new Date();
|
const date = new Date();
|
||||||
@@ -69,27 +72,37 @@ export const getNewRepacksFromXatab = async (
|
|||||||
|
|
||||||
const repacks: QueryDeepPartialEntity<Repack>[] = [];
|
const repacks: QueryDeepPartialEntity<Repack>[] = [];
|
||||||
|
|
||||||
for (const $a of Array.from(
|
if (page === 1) {
|
||||||
window.document.querySelectorAll(".entry__title a")
|
totalPages = Number(
|
||||||
)) {
|
window.document.querySelector(
|
||||||
try {
|
"#bottom-nav > div.pagination > a:nth-child(12)"
|
||||||
const repack = await getXatabRepack(($a as HTMLAnchorElement).href);
|
)?.textContent
|
||||||
|
);
|
||||||
if (repack) {
|
|
||||||
repacks.push({
|
|
||||||
title: $a.textContent!,
|
|
||||||
repacker: "Xatab",
|
|
||||||
...repack,
|
|
||||||
page,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
} catch (err: unknown) {
|
|
||||||
logger.error((err as Error).message, {
|
|
||||||
method: "getNewRepacksFromXatab",
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const repacksFromPage = Array.from(
|
||||||
|
window.document.querySelectorAll(".entry__title a")
|
||||||
|
).map(($a) => {
|
||||||
|
return getXatabRepack(($a as HTMLAnchorElement).href)
|
||||||
|
.then((repack) => {
|
||||||
|
if (repack) {
|
||||||
|
repacks.push({
|
||||||
|
title: $a.textContent!,
|
||||||
|
repacker: "Xatab",
|
||||||
|
...repack,
|
||||||
|
page,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch((err: unknown) => {
|
||||||
|
logger.error((err as Error).message, {
|
||||||
|
method: "getNewRepacksFromXatab",
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
await Promise.all(repacksFromPage);
|
||||||
|
|
||||||
const newRepacks = repacks.filter(
|
const newRepacks = repacks.filter(
|
||||||
(repack) =>
|
(repack) =>
|
||||||
!existingRepacks.some(
|
!existingRepacks.some(
|
||||||
@@ -98,6 +111,7 @@ export const getNewRepacksFromXatab = async (
|
|||||||
);
|
);
|
||||||
|
|
||||||
if (!newRepacks.length) return;
|
if (!newRepacks.length) return;
|
||||||
|
if (page === totalPages) return;
|
||||||
|
|
||||||
await savePage(newRepacks);
|
await savePage(newRepacks);
|
||||||
|
|
||||||
|
|||||||
@@ -1,10 +1,19 @@
|
|||||||
import { BrowserWindow, Menu, Tray, app } from "electron";
|
import {
|
||||||
|
BrowserWindow,
|
||||||
|
Menu,
|
||||||
|
MenuItem,
|
||||||
|
MenuItemConstructorOptions,
|
||||||
|
Tray,
|
||||||
|
app,
|
||||||
|
shell,
|
||||||
|
} from "electron";
|
||||||
import { is } from "@electron-toolkit/utils";
|
import { is } from "@electron-toolkit/utils";
|
||||||
import { t } from "i18next";
|
import { t } from "i18next";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
import icon from "@resources/icon.png?asset";
|
import icon from "@resources/icon.png?asset";
|
||||||
import trayIcon from "@resources/tray-icon.png?asset";
|
import trayIcon from "@resources/tray-icon.png?asset";
|
||||||
import { userPreferencesRepository } from "@main/repository";
|
import { gameRepository, userPreferencesRepository } from "@main/repository";
|
||||||
|
import { IsNull, Not } from "typeorm";
|
||||||
|
|
||||||
export class WindowManager {
|
export class WindowManager {
|
||||||
public static mainWindow: Electron.BrowserWindow | null = null;
|
public static mainWindow: Electron.BrowserWindow | null = null;
|
||||||
@@ -77,33 +86,66 @@ export class WindowManager {
|
|||||||
public static createSystemTray(language: string) {
|
public static createSystemTray(language: string) {
|
||||||
const tray = new Tray(trayIcon);
|
const tray = new Tray(trayIcon);
|
||||||
|
|
||||||
const contextMenu = Menu.buildFromTemplate([
|
const updateSystemTray = async () => {
|
||||||
{
|
const games = await gameRepository.find({
|
||||||
label: t("open", {
|
where: {
|
||||||
ns: "system_tray",
|
isDeleted: false,
|
||||||
lng: language,
|
executablePath: Not(IsNull()),
|
||||||
}),
|
lastTimePlayed: Not(IsNull()),
|
||||||
type: "normal",
|
|
||||||
click: () => {
|
|
||||||
if (this.mainWindow) {
|
|
||||||
this.mainWindow.show();
|
|
||||||
} else {
|
|
||||||
this.createMainWindow();
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
},
|
take: 5,
|
||||||
{
|
order: {
|
||||||
label: t("quit", {
|
updatedAt: "DESC",
|
||||||
ns: "system_tray",
|
},
|
||||||
lng: language,
|
});
|
||||||
}),
|
|
||||||
type: "normal",
|
const recentlyPlayedGames: Array<MenuItemConstructorOptions | MenuItem> =
|
||||||
click: () => app.quit(),
|
games.map(({ title, executablePath }) => ({
|
||||||
},
|
label: title,
|
||||||
]);
|
type: "normal",
|
||||||
|
click: async () => {
|
||||||
|
if (!executablePath) return;
|
||||||
|
|
||||||
|
shell.openPath(executablePath);
|
||||||
|
},
|
||||||
|
}));
|
||||||
|
|
||||||
|
const contextMenu = Menu.buildFromTemplate([
|
||||||
|
{
|
||||||
|
label: t("open", {
|
||||||
|
ns: "system_tray",
|
||||||
|
lng: language,
|
||||||
|
}),
|
||||||
|
type: "normal",
|
||||||
|
click: () => {
|
||||||
|
if (this.mainWindow) {
|
||||||
|
this.mainWindow.show();
|
||||||
|
} else {
|
||||||
|
this.createMainWindow();
|
||||||
|
}
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
type: "separator",
|
||||||
|
},
|
||||||
|
...recentlyPlayedGames,
|
||||||
|
{
|
||||||
|
type: "separator",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: t("quit", {
|
||||||
|
ns: "system_tray",
|
||||||
|
lng: language,
|
||||||
|
}),
|
||||||
|
type: "normal",
|
||||||
|
click: () => app.quit(),
|
||||||
|
},
|
||||||
|
]);
|
||||||
|
|
||||||
|
return contextMenu;
|
||||||
|
};
|
||||||
|
|
||||||
tray.setToolTip("Hydra");
|
tray.setToolTip("Hydra");
|
||||||
tray.setContextMenu(contextMenu);
|
|
||||||
|
|
||||||
if (process.platform === "win32" || process.platform === "linux") {
|
if (process.platform === "win32" || process.platform === "linux") {
|
||||||
tray.addListener("click", () => {
|
tray.addListener("click", () => {
|
||||||
@@ -117,6 +159,11 @@ export class WindowManager {
|
|||||||
|
|
||||||
this.createMainWindow();
|
this.createMainWindow();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
tray.addListener("right-click", async () => {
|
||||||
|
const contextMenu = await updateSystemTray();
|
||||||
|
tray.popUpContextMenu(contextMenu);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,7 +42,7 @@ export function Modal({
|
|||||||
}, [onClose]);
|
}, [onClose]);
|
||||||
|
|
||||||
const isTopMostModal = () => {
|
const isTopMostModal = () => {
|
||||||
const openModals = document.querySelectorAll("[role=modal]");
|
const openModals = document.querySelectorAll("[role=dialog]");
|
||||||
|
|
||||||
return (
|
return (
|
||||||
openModals.length &&
|
openModals.length &&
|
||||||
|
|||||||
@@ -27,7 +27,7 @@ export const getSteamLanguage = (language: string) => {
|
|||||||
if (language.startsWith("it")) return "italian";
|
if (language.startsWith("it")) return "italian";
|
||||||
if (language.startsWith("hu")) return "hungarian";
|
if (language.startsWith("hu")) return "hungarian";
|
||||||
if (language.startsWith("pl")) return "polish";
|
if (language.startsWith("pl")) return "polish";
|
||||||
if (language.startsWith("zh")) return "chinese";
|
if (language.startsWith("zh")) return "schinese";
|
||||||
if (language.startsWith("da")) return "danish";
|
if (language.startsWith("da")) return "danish";
|
||||||
|
|
||||||
return "english";
|
return "english";
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ export function HeroPanelPlaytime({
|
|||||||
|
|
||||||
const numberFormatter = useMemo(() => {
|
const numberFormatter = useMemo(() => {
|
||||||
return new Intl.NumberFormat(i18n.language, {
|
return new Intl.NumberFormat(i18n.language, {
|
||||||
maximumFractionDigits: 1,
|
maximumFractionDigits: 0,
|
||||||
});
|
});
|
||||||
}, [i18n.language]);
|
}, [i18n.language]);
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user