Compare commits
47 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2907ac74d4 | ||
|
|
ea678f37b0 | ||
|
|
076082c945 | ||
|
|
5ee98f90e8 | ||
|
|
c988dd88d7 | ||
|
|
f7d6c461dc | ||
|
|
14771ae946 | ||
|
|
7e9086b20e | ||
|
|
4b3c4870ba | ||
|
|
43cebd0c04 | ||
|
|
5ce13109b0 | ||
|
|
6e428c91d1 | ||
|
|
4430045550 | ||
|
|
282cb06091 | ||
|
|
772c2743b5 | ||
|
|
90199b89a5 | ||
|
|
e1d2e3f3e5 | ||
|
|
3f9fe1f2c6 | ||
|
|
c79bbc5756 | ||
|
|
63e1bec2b9 | ||
|
|
d26b7c6f75 | ||
|
|
da8dc4fa54 | ||
|
|
413b81c47f | ||
|
|
9ef419e3df | ||
|
|
39893912d9 | ||
|
|
49456ca6c3 | ||
|
|
6b9b8f0dbb | ||
|
|
5eb48b2717 | ||
|
|
5339cfca70 | ||
|
|
1462b2d0b8 | ||
|
|
3798a23183 | ||
|
|
ddaf916170 | ||
|
|
d6e37b058f | ||
|
|
2e9ad7d7cb | ||
|
|
190da74f66 | ||
|
|
f1315dda7f | ||
|
|
43e6105eb3 | ||
|
|
d785209eb6 | ||
|
|
da8b6a9010 | ||
|
|
1fd68722da | ||
|
|
c9a2c1d0e4 | ||
|
|
161f536a62 | ||
|
|
1a32e9944e | ||
|
|
6deb753198 | ||
|
|
4e33a98631 | ||
|
|
dcb9464d8f | ||
|
|
b94936b29f |
15
.github/workflows/release.yml
vendored
@@ -15,8 +15,6 @@ jobs:
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: '0'
|
||||
- name: Install Flutter
|
||||
uses: subosito/flutter-action@v2
|
||||
with:
|
||||
@@ -32,13 +30,18 @@ jobs:
|
||||
curl -u ${{ secrets.BASIC_AUTH }} -o android/key.properties ${{ secrets.URL_PREFIX }}key.properties
|
||||
- name: Build
|
||||
run: dart run fl_build -p android,linux
|
||||
- name: Rename for fdroid
|
||||
run: |
|
||||
mv build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_arm64.apk build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_arm64.apk
|
||||
mv build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_arm.apk build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_arm.apk
|
||||
mv build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_amd64.apk build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_amd64.apk
|
||||
- name: Create Release
|
||||
uses: softprops/action-gh-release@v2
|
||||
with:
|
||||
files: |
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_arm64.apk
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_arm.apk
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_amd64.apk
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_arm64.apk
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_arm.apk
|
||||
build/app/outputs/flutter-apk/${{ env.APP_NAME }}_v1.0.${{ env.BUILD_NUMBER }}_amd64.apk
|
||||
${{ env.APP_NAME }}_${{ env.BUILD_NUMBER }}_amd64.AppImage
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
@@ -49,8 +52,6 @@ jobs:
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: '0'
|
||||
- name: Install Flutter
|
||||
uses: subosito/flutter-action@v2
|
||||
- name: Build
|
||||
|
||||
30
.metadata
@@ -4,7 +4,7 @@
|
||||
# This file should be version controlled and should not be manually edited.
|
||||
|
||||
version:
|
||||
revision: "bae5e49bc2a867403c43b2aae2de8f8c33b037e4"
|
||||
revision: "761747bfc538b5af34aa0d3fac380f1bc331ec49"
|
||||
channel: "stable"
|
||||
|
||||
project_type: app
|
||||
@@ -13,26 +13,26 @@ project_type: app
|
||||
migration:
|
||||
platforms:
|
||||
- platform: root
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: android
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: ios
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: linux
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: macos
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: web
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
- platform: windows
|
||||
create_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
base_revision: bae5e49bc2a867403c43b2aae2de8f8c33b037e4
|
||||
create_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
base_revision: 761747bfc538b5af34aa0d3fac380f1bc331ec49
|
||||
|
||||
# User provided section
|
||||
|
||||
|
||||
4
.vscode/launch.json
vendored
@@ -8,6 +8,10 @@
|
||||
"name": "debug",
|
||||
"request": "launch",
|
||||
"type": "dart",
|
||||
"env": {
|
||||
// Comment this line to use the default display
|
||||
"DISPLAY": ":1"
|
||||
}
|
||||
// "args": [
|
||||
// "-v"
|
||||
// ]
|
||||
|
||||
31
README.md
@@ -14,34 +14,35 @@ Especially thanks to <a href="https://github.com/TerminalStudio/dartssh2">dartss
|
||||
</p>
|
||||
|
||||
|
||||
## ⬇️ Download
|
||||
🎉 **The `Android / Linux / Windows` version are now built via GitHub Actions**
|
||||
## 📥 Install
|
||||
|
||||
[iOS & macOS](https://apps.apple.com/app/id1586449703) / [Android & Linux & Windows](https://github.com/lollipopkit/flutter_server_box/releases)
|
||||
|
||||
- All deprecated versions before `v930` can be found in [here](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid).
|
||||
- To prevent injection attacks and etc., please don't download from untrusted sources. eg: Gitee release is not related to this project.
|
||||
Platform | From
|
||||
--- | ---
|
||||
iOS / macOS | [AppStore](https://apps.apple.com/app/id1586449703)
|
||||
Android | [GitHub](https://github.com/lollipopkit/flutter_server_box/releases) / [CDN](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid) / [F-Droid](https://f-droid.org/packages/tech.lolli.toolbox) / [OpenAPK](https://www.openapk.net/serverbox/tech.lolli.toolbox/)
|
||||
Linux / Windows | [GitHub](https://github.com/lollipopkit/flutter_server_box/releases) / [CDN](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid)
|
||||
|
||||
**Please only download pkgs from the source that you trust!**
|
||||
- `AppStore` & `CDN` packages are built by myself
|
||||
- Github releases are built by Github Actions
|
||||
- Other sources are built by themselves
|
||||
|
||||
## 🔖 Feature
|
||||
- `Status chart` (CPU, Sensors, GPU...), `SSH` Term, `SFTP`, `Docker & Pkg & Process`...
|
||||
- Platform specific: `Bio auth`、`Msg push`、`Home widget`、`watchOS App`...
|
||||
- English, 简体中文; Deutsch [@its-tom](https://github.com/its-tom), 繁體中文 [@kalashnikov](https://github.com/kalashnikov), Indonesian [@azkadev](https://github.com/azkadev), Français [@FrancXPT](https://github.com/FrancXPT), Dutch [@QazCetelic](https://github.com/QazCetelic); Español, Русский язык, Português, 日本語 (Generated by GPT)
|
||||
|
||||
|
||||
## 🏙️ ScreenShots
|
||||
<table>
|
||||
<tr>
|
||||
<td><img width="277px" src="imgs/server.png"></td>
|
||||
<td><img width="277px" src="imgs/detail.png"></td>
|
||||
<td><img width="277px" src="imgs/sftp.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/1.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/2.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/3.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
<table>
|
||||
<tr>
|
||||
<td><img width="277px" src="imgs/editor.png"> </td>
|
||||
<td><img width="277px" src="imgs/ssh.png"></td>
|
||||
<td><img width="277px" src="imgs/docker.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/4.png"> </td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/5.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/6.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
||||
31
README_zh.md
@@ -13,15 +13,18 @@
|
||||
特别感谢 <a href="https://github.com/TerminalStudio/dartssh2">dartssh2</a> & <a href="https://github.com/TerminalStudio/xterm.dart">xterm.dart</a>。
|
||||
</p>
|
||||
|
||||
## 📥 安装
|
||||
|
||||
## ⬇️ Download
|
||||
🎉 **现在 `Android / Linux / Windows` 版本使用 GitHub Actions 构建**。
|
||||
|
||||
[iOS & macOS](https://apps.apple.com/app/id1586449703) / [Android & Linux & Windows](https://github.com/lollipopkit/flutter_server_box/releases)
|
||||
|
||||
- 所有 `v930` 之前的版本可以在 [这里](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid) 找到。
|
||||
- 为了防止注入攻击等,请不要从不受信任的来源下载。例如:Gitee 的发行包与该项目无关。
|
||||
平台 | 下载
|
||||
--- | ---
|
||||
iOS / macOS | [AppStore](https://apps.apple.com/app/id1586449703)
|
||||
Android | [GitHub](https://github.com/lollipopkit/flutter_server_box/releases) / [CDN](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid) / [F-Droid](https://f-droid.org/packages/tech.lolli.toolbox) / [OpenAPK](https://www.openapk.net/serverbox/tech.lolli.toolbox/)
|
||||
Linux / Windows | [GitHub](https://github.com/lollipopkit/flutter_server_box/releases) / [CDN](https://cdn.lolli.tech/serverbox/?sort=time&order=desc&layout=grid)
|
||||
|
||||
**请不要从不受信任的来源下载!**
|
||||
- `AppStore` & `CDN` 的包由我构建
|
||||
- Github 的包由 Github Actions 构建
|
||||
- 其他来源由其所有者构建
|
||||
|
||||
## 🔖 特点
|
||||
- `状态图表`(CPU、传感器、GPU 等), `SSH` 终端, `SFTP`, `Docker & 包 & 进程` 管理器...
|
||||
@@ -35,16 +38,14 @@
|
||||
## 🏙️ 截屏
|
||||
<table>
|
||||
<tr>
|
||||
<td><img width="277px" src="imgs/server.png"></td>
|
||||
<td><img width="277px" src="imgs/detail.png"></td>
|
||||
<td><img width="277px" src="imgs/sftp.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/1.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/2.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/3.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
<table>
|
||||
<tr>
|
||||
<td><img width="277px" src="imgs/editor.png"> </td>
|
||||
<td><img width="277px" src="imgs/ssh.png"></td>
|
||||
<td><img width="277px" src="imgs/docker.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/4.png"> </td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/5.png"></td>
|
||||
<td><img width="277px" src="https://cdn.lolli.tech/serverbox/screenshot/6.png"></td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
|
||||
BIN
imgs/detail.png
|
Before Width: | Height: | Size: 135 KiB |
BIN
imgs/docker.png
|
Before Width: | Height: | Size: 115 KiB |
BIN
imgs/editor.png
|
Before Width: | Height: | Size: 173 KiB |
|
Before Width: | Height: | Size: 112 KiB |
BIN
imgs/server.png
|
Before Width: | Height: | Size: 135 KiB |
BIN
imgs/sftp.png
|
Before Width: | Height: | Size: 135 KiB |
BIN
imgs/ssh.png
|
Before Width: | Height: | Size: 144 KiB |
@@ -1,6 +1,4 @@
|
||||
PODS:
|
||||
- countly_flutter (24.4.1):
|
||||
- Flutter
|
||||
- device_info_plus (0.0.1):
|
||||
- Flutter
|
||||
- file_picker (0.0.1):
|
||||
@@ -36,7 +34,6 @@ PODS:
|
||||
- Flutter
|
||||
|
||||
DEPENDENCIES:
|
||||
- countly_flutter (from `.symlinks/plugins/countly_flutter/ios`)
|
||||
- device_info_plus (from `.symlinks/plugins/device_info_plus/ios`)
|
||||
- file_picker (from `.symlinks/plugins/file_picker/ios`)
|
||||
- Flutter (from `Flutter`)
|
||||
@@ -55,8 +52,6 @@ DEPENDENCIES:
|
||||
- watch_connectivity (from `.symlinks/plugins/watch_connectivity/ios`)
|
||||
|
||||
EXTERNAL SOURCES:
|
||||
countly_flutter:
|
||||
:path: ".symlinks/plugins/countly_flutter/ios"
|
||||
device_info_plus:
|
||||
:path: ".symlinks/plugins/device_info_plus/ios"
|
||||
file_picker:
|
||||
@@ -91,7 +86,6 @@ EXTERNAL SOURCES:
|
||||
:path: ".symlinks/plugins/watch_connectivity/ios"
|
||||
|
||||
SPEC CHECKSUMS:
|
||||
countly_flutter: 56233d921c6b4e0a720774a39b8ee8110d6f8d91
|
||||
device_info_plus: 97af1d7e84681a90d0693e63169a5d50e0839a0d
|
||||
file_picker: c79185e70b9b45728cde2a8d8da454e0cb43f287
|
||||
Flutter: e0871f40cf51350855a761d2e70bf5af5b9b5de7
|
||||
|
||||
@@ -690,7 +690,7 @@
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CODE_SIGN_ENTITLEMENTS = Runner/Runner.entitlements;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_BITCODE = NO;
|
||||
INFOPLIST_FILE = "Runner/Info-$(CONFIGURATION).plist";
|
||||
@@ -700,7 +700,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
@@ -826,7 +826,7 @@
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CODE_SIGN_ENTITLEMENTS = Runner/Runner.entitlements;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_BITCODE = NO;
|
||||
INFOPLIST_FILE = "Runner/Info-$(CONFIGURATION).plist";
|
||||
@@ -836,7 +836,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
@@ -854,7 +854,7 @@
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CODE_SIGN_ENTITLEMENTS = Runner/Runner.entitlements;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_BITCODE = NO;
|
||||
INFOPLIST_FILE = "Runner/Info-$(CONFIGURATION).plist";
|
||||
@@ -864,7 +864,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
|
||||
@@ -885,7 +885,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
@@ -898,7 +898,7 @@
|
||||
"@executable_path/Frameworks",
|
||||
"@executable_path/../../Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.StatusWidget;
|
||||
@@ -924,7 +924,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
@@ -937,7 +937,7 @@
|
||||
"@executable_path/Frameworks",
|
||||
"@executable_path/../../Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.StatusWidget;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
@@ -960,7 +960,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GENERATE_INFOPLIST_FILE = YES;
|
||||
@@ -973,7 +973,7 @@
|
||||
"@executable_path/Frameworks",
|
||||
"@executable_path/../../Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.StatusWidget;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
@@ -996,7 +996,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_ASSET_PATHS = "";
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_PREVIEWS = YES;
|
||||
@@ -1008,7 +1008,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.WatchEnd;
|
||||
@@ -1037,7 +1037,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_ASSET_PATHS = "";
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_PREVIEWS = YES;
|
||||
@@ -1049,7 +1049,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.WatchEnd;
|
||||
PRODUCT_NAME = ServerBox;
|
||||
@@ -1075,7 +1075,7 @@
|
||||
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_ASSET_PATHS = "";
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
ENABLE_PREVIEWS = YES;
|
||||
@@ -1087,7 +1087,7 @@
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
MTL_FAST_MATH = YES;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox.WatchEnd;
|
||||
PRODUCT_NAME = ServerBox;
|
||||
|
||||
25
lib/app.dart
@@ -3,10 +3,14 @@ import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:fl_lib/l10n/gen_l10n/lib_l10n.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||
import 'package:server_box/core/extension/context/locale.dart';
|
||||
import 'package:server_box/data/res/build_data.dart';
|
||||
import 'package:server_box/data/res/rebuild.dart';
|
||||
import 'package:server_box/data/res/store.dart';
|
||||
import 'package:server_box/view/page/home/home.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
|
||||
part 'intro.dart';
|
||||
|
||||
class MyApp extends StatelessWidget {
|
||||
const MyApp({super.key});
|
||||
@@ -71,17 +75,26 @@ class MyApp extends StatelessWidget {
|
||||
...AppLocalizations.localizationsDelegates,
|
||||
],
|
||||
supportedLocales: AppLocalizations.supportedLocales,
|
||||
localeListResolutionCallback: LocaleUtil.resolve,
|
||||
title: BuildData.name,
|
||||
themeMode: themeMode,
|
||||
theme: light,
|
||||
darkTheme: tMode < 3 ? dark : dark.toAmoled,
|
||||
home: _buildAppContent(ctx),
|
||||
);
|
||||
}
|
||||
home: Builder(
|
||||
builder: (context) {
|
||||
context.setLibL10n();
|
||||
final appL10n = AppLocalizations.of(context);
|
||||
if (appL10n != null) l10n = appL10n;
|
||||
|
||||
Widget _buildAppContent(BuildContext ctx) {
|
||||
//if (Pros.app.isWearOS) return const WearHome();
|
||||
return const HomePage();
|
||||
final intros = _IntroPage.builders;
|
||||
if (intros.isNotEmpty) {
|
||||
return _IntroPage(intros);
|
||||
}
|
||||
|
||||
return const HomePage();
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import 'package:dartssh2/dartssh2.dart';
|
||||
import 'package:server_box/view/widget/unix_perm.dart';
|
||||
|
||||
extension SftpFileX on SftpFileMode {
|
||||
String get str {
|
||||
@@ -8,6 +9,26 @@ extension SftpFileX on SftpFileMode {
|
||||
|
||||
return '$user$group$other';
|
||||
}
|
||||
|
||||
UnixPerm toUnixPerm() {
|
||||
return UnixPerm(
|
||||
user: RWX(
|
||||
r: userRead,
|
||||
w: userWrite,
|
||||
x: userExecute,
|
||||
),
|
||||
group: RWX(
|
||||
r: groupRead,
|
||||
w: groupWrite,
|
||||
x: groupExecute,
|
||||
),
|
||||
other: RWX(
|
||||
r: otherRead,
|
||||
w: otherWrite,
|
||||
x: otherExecute,
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
String _getRoleMode(bool r, bool w, bool x) {
|
||||
|
||||
@@ -170,7 +170,7 @@ class Backup {
|
||||
}
|
||||
|
||||
Pros.reload();
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
|
||||
_logger.info('Restore success');
|
||||
}
|
||||
|
||||
@@ -12,32 +12,17 @@ enum ShellFunc {
|
||||
suspend,
|
||||
;
|
||||
|
||||
static const _homeVar = '\$HOME';
|
||||
static const seperator = 'SrvBoxSep';
|
||||
|
||||
/// The suffix `\t` is for formatting
|
||||
static const cmdDivider = '\necho $seperator\n\t';
|
||||
static const _srvBoxDir = '.config/server_box';
|
||||
static const scriptFile = 'mobile_v${BuildData.script}.sh';
|
||||
|
||||
/// Issue #159
|
||||
///
|
||||
/// Use script commit count as version of shell script.
|
||||
///
|
||||
/// So different version of app can run at the same time.
|
||||
///
|
||||
/// **Can't** use it in SFTP, because SFTP can't recognize `$HOME`
|
||||
static String getShellPath(String home) => '$home/$_srvBoxDir/$scriptFile';
|
||||
|
||||
static const srvBoxDir = '$_homeVar/$_srvBoxDir';
|
||||
static const _installShellPath = '$_homeVar/$_srvBoxDir/$scriptFile';
|
||||
|
||||
// Issue #299, chmod ~/.config to avoid permission issue
|
||||
/// srvboxm -> ServerBox Mobile
|
||||
static const scriptFile = 'srvboxm_v${BuildData.script}.sh';
|
||||
static const scriptPath = '/dev/shm/$scriptFile';
|
||||
static const installShellCmd = """
|
||||
chmod +x ~/.config &> /dev/null
|
||||
mkdir -p $_homeVar/$_srvBoxDir
|
||||
cat > $_installShellPath
|
||||
chmod +x $_installShellPath
|
||||
cat > $scriptPath
|
||||
chmod 744 $scriptPath
|
||||
""";
|
||||
|
||||
String get flag {
|
||||
@@ -57,7 +42,7 @@ chmod +x $_installShellPath
|
||||
}
|
||||
}
|
||||
|
||||
String get exec => 'sh $_installShellPath -$flag';
|
||||
String get exec => 'sh $scriptPath -$flag';
|
||||
|
||||
String get name {
|
||||
switch (this) {
|
||||
|
||||
@@ -72,7 +72,7 @@ final class DockerImg implements ContainerImg {
|
||||
final String repository;
|
||||
final String size;
|
||||
@override
|
||||
final String tag;
|
||||
final String? tag;
|
||||
|
||||
DockerImg({
|
||||
required this.containers,
|
||||
@@ -95,14 +95,30 @@ final class DockerImg implements ContainerImg {
|
||||
|
||||
String toRawJson() => json.encode(toJson());
|
||||
|
||||
factory DockerImg.fromJson(Map<String, dynamic> json) => DockerImg(
|
||||
containers: json["Containers"],
|
||||
createdAt: json["CreatedAt"],
|
||||
id: json["ID"],
|
||||
repository: json["Repository"],
|
||||
size: json["Size"],
|
||||
tag: json["Tag"],
|
||||
);
|
||||
factory DockerImg.fromJson(Map<String, dynamic> json) {
|
||||
final containers = switch (json["Containers"]) {
|
||||
final String a => a,
|
||||
final Object? a => a.toString(),
|
||||
};
|
||||
final repo = switch (json["Repository"] ?? json["Names"]) {
|
||||
final String a => a,
|
||||
final List a => a.firstOrNull.toString(),
|
||||
final Object? a => a.toString(),
|
||||
};
|
||||
final size = switch (json["Size"]) {
|
||||
final String a => a,
|
||||
final int a => a.bytes2Str,
|
||||
final Object? a => a.toString(),
|
||||
};
|
||||
return DockerImg(
|
||||
containers: containers,
|
||||
createdAt: json["CreatedAt"],
|
||||
id: json["ID"] ?? json["Id"] ?? '',
|
||||
repository: repo,
|
||||
size: size,
|
||||
tag: json["Tag"],
|
||||
);
|
||||
}
|
||||
|
||||
Map<String, dynamic> toJson() => {
|
||||
"Containers": containers,
|
||||
|
||||
@@ -3,13 +3,6 @@ import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class AppProvider extends ChangeNotifier {
|
||||
int? _newestBuild;
|
||||
int? get newestBuild => _newestBuild;
|
||||
set newestBuild(int? build) {
|
||||
_newestBuild = build;
|
||||
notifyListeners();
|
||||
}
|
||||
|
||||
BuildContext? ctx;
|
||||
|
||||
bool isWearOS = false;
|
||||
|
||||
@@ -160,11 +160,18 @@ class ContainerProvider extends ChangeNotifier {
|
||||
}
|
||||
|
||||
// Parse images
|
||||
final imageRaw = ContainerCmdType.images.find(segments);
|
||||
final imageRaw = ContainerCmdType.images.find(segments).trim();
|
||||
final isEntireJson = imageRaw.startsWith('[') && imageRaw.endsWith(']');
|
||||
try {
|
||||
final imgLines = imageRaw.split('\n');
|
||||
imgLines.removeWhere((element) => element.isEmpty);
|
||||
images = imgLines.map((e) => ContainerImg.fromRawJson(e, type)).toList();
|
||||
if (isEntireJson) {
|
||||
images = (json.decode(imageRaw) as List)
|
||||
.map((e) => ContainerImg.fromRawJson(json.encode(e), type))
|
||||
.toList();
|
||||
} else {
|
||||
final lines = imageRaw.split('\n');
|
||||
lines.removeWhere((element) => element.isEmpty);
|
||||
images = lines.map((e) => ContainerImg.fromRawJson(e, type)).toList();
|
||||
}
|
||||
} catch (e, trace) {
|
||||
error = ContainerErr(
|
||||
type: ContainerErrType.parseImages,
|
||||
@@ -298,6 +305,6 @@ enum ContainerCmdType {
|
||||
}) {
|
||||
return ContainerCmdType.values
|
||||
.map((e) => e.exec(type, sudo: sudo, includeStats: includeStats))
|
||||
.join(' && echo ${ShellFunc.seperator} && ');
|
||||
.join('\necho ${ShellFunc.seperator}\n');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -347,9 +347,13 @@ class ServerProvider extends ChangeNotifier {
|
||||
if (homePath == null || homePath.isEmpty) {
|
||||
throw Exception('Got empty home path');
|
||||
}
|
||||
final remotePath = ShellFunc.getShellPath(homePath);
|
||||
final reqId = Pros.sftp.add(
|
||||
SftpReq(spi, remotePath, localPath, SftpReqType.upload),
|
||||
SftpReq(
|
||||
spi,
|
||||
ShellFunc.scriptPath,
|
||||
localPath,
|
||||
SftpReqType.upload,
|
||||
),
|
||||
completer: completer,
|
||||
);
|
||||
await completer.future;
|
||||
|
||||
@@ -2,9 +2,6 @@
|
||||
|
||||
class BuildData {
|
||||
static const String name = "ServerBox";
|
||||
static const int build = 970;
|
||||
static const String engine = "3.22.2";
|
||||
static const String buildAt = "2024-06-13 00:44:23";
|
||||
static const int modifications = 0;
|
||||
static const int script = 49;
|
||||
static const int build = 1018;
|
||||
static const int script = 51;
|
||||
}
|
||||
|
||||
@@ -3,15 +3,17 @@ abstract final class GithubIds {
|
||||
// If you want to change your Github ID, please open an issue.
|
||||
static const contributors = <GhId>{
|
||||
'PaperCube',
|
||||
'Integral-Tech',
|
||||
'its-tom',
|
||||
'leganck',
|
||||
'azkadev',
|
||||
'kalashnikov',
|
||||
'FrancXPT',
|
||||
'RainSunMe',
|
||||
'calvinweb',
|
||||
'QazCetelic',
|
||||
'RainSunMe',
|
||||
'FrancXPT',
|
||||
'Liloupar',
|
||||
'dccif',
|
||||
'QazCetelic',
|
||||
};
|
||||
|
||||
static const participants = <GhId>{
|
||||
@@ -71,6 +73,17 @@ abstract final class GithubIds {
|
||||
'FHU-yezi',
|
||||
'ZRY233',
|
||||
'Jasonzhu1207',
|
||||
'sakuraanzu',
|
||||
'licaon-kter',
|
||||
'77160860',
|
||||
'mijjjj',
|
||||
'muyunil',
|
||||
'Hua159',
|
||||
'jaydong2016',
|
||||
'geol',
|
||||
'Mooling0602',
|
||||
'IllTamer',
|
||||
'marlkiller',
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@@ -276,6 +276,14 @@ class SettingStore extends PersistentStore {
|
||||
|
||||
late final betaTest = property('betaTest', false);
|
||||
|
||||
/// If it's empty, skip change window size.
|
||||
/// Format: {width}x{height}
|
||||
late final windowSize = property('windowSize', '');
|
||||
|
||||
late final introVer = property('introVer', 0);
|
||||
|
||||
late final letterCache = property('letterCache', false);
|
||||
|
||||
// Never show these settings for users
|
||||
//
|
||||
// ------BEGIN------
|
||||
|
||||
127
lib/intro.dart
Normal file
@@ -0,0 +1,127 @@
|
||||
part of 'app.dart';
|
||||
|
||||
final class _IntroPage extends StatelessWidget {
|
||||
final List<IntroPageBuilder> pages;
|
||||
|
||||
const _IntroPage(this.pages);
|
||||
|
||||
static const _builders = {
|
||||
1: _buildAppSettings,
|
||||
2: _buildRecommended,
|
||||
1006: _buildTermLetterCache,
|
||||
};
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return LayoutBuilder(
|
||||
builder: (context, cons) {
|
||||
final padTop = cons.maxHeight * .16;
|
||||
final pages_ = pages.map((e) => e(context, padTop)).toList();
|
||||
return IntroPage(
|
||||
pages: pages_,
|
||||
onDone: (ctx) {
|
||||
Stores.setting.introVer.put(BuildData.build);
|
||||
Navigator.of(ctx).pushReplacement(
|
||||
MaterialPageRoute(builder: (_) => const HomePage()),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
static Widget _buildTermLetterCache(BuildContext context, double padTop) {
|
||||
return ListView(
|
||||
padding: _introListPad,
|
||||
children: [
|
||||
SizedBox(height: padTop),
|
||||
IntroPage.title(icon: BoxIcons.bxs_terminal, big: true),
|
||||
SizedBox(height: padTop),
|
||||
ListTile(
|
||||
leading: const Icon(Bootstrap.input_cursor),
|
||||
title: Text(l10n.letterCache),
|
||||
subtitle: Text(l10n.letterCacheTip, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(prop: _setting.letterCache),
|
||||
).cardx,
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
static Widget _buildRecommended(BuildContext context, double padTop) {
|
||||
return ListView(
|
||||
padding: _introListPad,
|
||||
children: [
|
||||
SizedBox(height: padTop),
|
||||
IntroPage.title(icon: Bootstrap.stars, big: true),
|
||||
SizedBox(height: padTop),
|
||||
ListTile(
|
||||
leading: const Icon(MingCute.delete_2_fill),
|
||||
title: const Text('rm -r'),
|
||||
subtitle: Text(l10n.sftpRmrDirSummary, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(prop: _setting.sftpRmrDir),
|
||||
).cardx,
|
||||
ListTile(
|
||||
leading: const Icon(IonIcons.stats_chart, size: _kIconSize),
|
||||
title: Text(l10n.parseContainerStats),
|
||||
subtitle: Text(l10n.parseContainerStatsTip, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(prop: _setting.containerParseStat),
|
||||
).cardx,
|
||||
ListTile(
|
||||
leading: const Icon(OctIcons.cpu),
|
||||
title: Text(l10n.noLineChartForCpu),
|
||||
subtitle: Text(l10n.cpuViewAsProgressTip, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(prop: _setting.cpuViewAsProgress),
|
||||
).cardx,
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
static Widget _buildAppSettings(BuildContext ctx, double padTop) {
|
||||
return ListView(
|
||||
padding: _introListPad,
|
||||
children: [
|
||||
SizedBox(height: padTop),
|
||||
IntroPage.title(text: l10n.init, big: true),
|
||||
SizedBox(height: padTop),
|
||||
ListTile(
|
||||
leading: const Icon(IonIcons.language),
|
||||
title: Text(l10n.language),
|
||||
onTap: () async {
|
||||
final selected = await ctx.showPickSingleDialog(
|
||||
title: l10n.language,
|
||||
items: AppLocalizations.supportedLocales,
|
||||
name: (p0) => p0.code,
|
||||
initial: _setting.locale.fetch().toLocale,
|
||||
);
|
||||
if (selected != null) {
|
||||
_setting.locale.put(selected.code);
|
||||
RNodes.app.notify();
|
||||
}
|
||||
},
|
||||
trailing: Text(
|
||||
l10n.languageName,
|
||||
style: const TextStyle(fontSize: 15, color: Colors.grey),
|
||||
),
|
||||
).cardx,
|
||||
ListTile(
|
||||
leading: const Icon(Icons.update),
|
||||
title: Text(l10n.autoCheckUpdate),
|
||||
subtitle: Text(l10n.fdroidReleaseTip, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(prop: _setting.autoCheckAppUpdate),
|
||||
).cardx,
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
static List<IntroPageBuilder> get builders {
|
||||
final storedVer = _setting.introVer.fetch();
|
||||
return _builders.entries
|
||||
.where((e) => e.key > storedVer)
|
||||
.map((e) => e.value)
|
||||
.toList();
|
||||
}
|
||||
|
||||
static final _setting = Stores.setting;
|
||||
static const _kIconSize = 23.0;
|
||||
static const _introListPad = EdgeInsets.symmetric(horizontal: 17);
|
||||
}
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Adresse",
|
||||
"all": "Alle",
|
||||
"alreadyLastDir": "Bereits im letzten Verzeichnis.",
|
||||
"alterUrl": "Url ändern",
|
||||
"askContinue": "{msg}. Weiter?",
|
||||
"attention": "Achtung",
|
||||
"authFailTip": "Authentifizierung fehlgeschlagen, bitte überprüfen Sie, ob das Passwort/Schlüssel/Host/Benutzer usw. falsch sind.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Das Backup wird nur einfach verschlüsselt.\nBitte bewahre die Datei sicher auf.",
|
||||
"backupVersionNotMatch": "Die Backup-Version stimmt nicht überein.",
|
||||
"battery": "Batterie",
|
||||
"beforeConnect": "ServerBox wird nach der Verbindung ein Skript in `~/.config/server_box` schreiben und ausführen. Für weitere technische Details besuchen Sie bitte [Github]({url}).",
|
||||
"bgRun": "Hintergrundaktualisierung",
|
||||
"bgRunTip": "Dieser Schalter bedeutet nur, dass die App versuchen wird, im Hintergrund zu laufen. Ob sie im Hintergrund laufen kann, hängt davon ab, ob die Berechtigungen aktiviert sind oder nicht. Bei nativem Android deaktivieren Sie bitte \"Batterieoptimierung\" in dieser App, und bei miui ändern Sie bitte die Energiesparrichtlinie auf \"Unbegrenzt\".",
|
||||
"bioAuth": "Biozertifizierung",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Decode",
|
||||
"decompress": "Dekomprimieren",
|
||||
"delete": "Löschen",
|
||||
"deleteScripts": "Gleichzeitiges Löschen von Server-Skripten",
|
||||
"deleteServers": "Batch-Löschung von Servern",
|
||||
"deviceName": "Gerätename",
|
||||
"dirEmpty": "Stelle sicher, dass der Ordner leer ist.",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Export",
|
||||
"extraArgs": "Extra args",
|
||||
"failed": "Failed",
|
||||
"fallbackSshDest": "SSH-Fallback-Ziel",
|
||||
"fdroidReleaseTip": "Wenn Sie diese App von F-Droid heruntergeladen haben, wird empfohlen, diese Option zu deaktivieren.",
|
||||
"feedback": "Feedback",
|
||||
"feedbackOnGithub": "Wenn du Fragen hast, stelle diese bitte auf Github.",
|
||||
"fieldMustNotEmpty": "Die Eingabefelder dürfen nicht leer sein.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Images",
|
||||
"import": "Importieren",
|
||||
"inAppUpdate": "Im App aktualisieren? Andernfalls mit einem Browser herunterladen.",
|
||||
"init": "Initialisieren",
|
||||
"inner": "Eingebaut",
|
||||
"inputDomainHere": "Domain eingeben",
|
||||
"install": "install",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Deutsch",
|
||||
"lastTry": "Letzter Versuch",
|
||||
"launchPage": "Startseite",
|
||||
"letterCache": "Buchstaben-Caching",
|
||||
"letterCacheTip": "Empfohlen zu aktivieren, aber die Aktivierung verhindert die Eingabe von CJK (Chinesisch, Japanisch, Koreanisch) Zeichen",
|
||||
"license": "Lizenzen",
|
||||
"light": "Hell",
|
||||
"loadingFiles": "Lädt Dateien...",
|
||||
@@ -173,12 +175,13 @@
|
||||
"name": "Name",
|
||||
"needHomeDir": "Wenn Sie ein Synology-Benutzer sind, [sehen Sie hier](https://kb.synology.com/DSM/tutorial/user_enable_home_service). Benutzer anderer Systeme müssen suchen, wie man ein Home-Verzeichnis erstellt.",
|
||||
"needRestart": "App muss neugestartet werden",
|
||||
"net": "Netz",
|
||||
"net": "Netzwerk",
|
||||
"netViewType": "Netzwerkansicht Typ",
|
||||
"newContainer": "Neuer Container",
|
||||
"noClient": "Kein Client",
|
||||
"noInterface": "Kein Interface",
|
||||
"noLineChart": "Verwenden Sie keine Liniendiagramme",
|
||||
"noLineChartForCpu": "Verwenden Sie keine Liniendiagramme für CPU",
|
||||
"noNotiPerm": "Keine Benachrichtigungsrechte, möglicherweise keine Fortschrittsanzeige beim Herunterladen von App-Updates.",
|
||||
"noOptions": "Keine Optionen verfügbar",
|
||||
"noPrivateKeyTip": "Der private Schlüssel existiert nicht, möglicherweise wurde er gelöscht oder es liegt ein Konfigurationsfehler vor.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "Einfügen",
|
||||
"path": "Pfad",
|
||||
"percentOfSize": "{percent}% von {size}",
|
||||
"permission": "Berechtigungen",
|
||||
"pickFile": "Datei wählen",
|
||||
"pingAvg": "Avg:",
|
||||
"pingInputIP": "Bitte gib eine Ziel-IP/Domain ein.",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Auswahl merken",
|
||||
"rememberPwdInMem": "Passwort im Speicher behalten",
|
||||
"rememberPwdInMemTip": "Für Container, Aufhängen usw.",
|
||||
"rememberWindowSize": "Fenstergröße merken",
|
||||
"remotePath": "Entfernte Pfade",
|
||||
"rename": "Umbenennen",
|
||||
"reportBugsOnGithubIssue": "Bitte Bugs auf {url} melden",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "Total",
|
||||
"traffic": "Durchflussmenge",
|
||||
"trySudo": "Versuche es mit sudo",
|
||||
"ttl": "ttl",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Unbekannt",
|
||||
"unknownError": "Unbekannter Fehler",
|
||||
"unkownConvertMode": "Unbekannter Konvertierungsmodus",
|
||||
|
||||
@@ -2,33 +2,31 @@
|
||||
"@@locale": "en",
|
||||
"about": "About",
|
||||
"aboutThanks": "Thanks to the following people who participated in.",
|
||||
"acceptBeta": "Accept test version updates",
|
||||
"acceptBeta": "Accept beta version updates",
|
||||
"add": "Add",
|
||||
"addAServer": "add a server",
|
||||
"addPrivateKey": "Add private key",
|
||||
"addSystemPrivateKeyTip": "Currently don't have any private key, do you add the one that comes with the system (~/.ssh/id_rsa)?",
|
||||
"addSystemPrivateKeyTip": "Currently private keys don't exist, do you want to add the one that comes with the system (~/.ssh/id_rsa)?",
|
||||
"added2List": "Added to task list",
|
||||
"addr": "Address",
|
||||
"all": "All",
|
||||
"alreadyLastDir": "Already in last directory.",
|
||||
"alterUrl": "Alter url",
|
||||
"askContinue": "{msg}. Continue?",
|
||||
"attention": "Attention",
|
||||
"authFailTip": "Authentication failed, please check if the password/key/host/user, etc., are incorrect.",
|
||||
"authFailTip": "Authentication failed, please check whether credentials are correct",
|
||||
"authRequired": "Auth required",
|
||||
"auto": "Auto",
|
||||
"autoBackupConflict": "Only one automatic backup can be turned on at the same time.",
|
||||
"autoCheckUpdate": "Auto check update",
|
||||
"autoCheckUpdate": "Automatic update check",
|
||||
"autoConnect": "Auto connect",
|
||||
"autoRun": "Automatic Run",
|
||||
"autoUpdateHomeWidget": "Auto update home widget",
|
||||
"autoRun": "Auto run",
|
||||
"autoUpdateHomeWidget": "Automatic home widget update",
|
||||
"backup": "Backup",
|
||||
"backupTip": "The exported data is simply encrypted. \nPlease keep it safe.",
|
||||
"backupTip": "The exported data is weakly encrypted. \nPlease keep it safe.",
|
||||
"backupVersionNotMatch": "Backup version is not match.",
|
||||
"battery": "Battery",
|
||||
"beforeConnect": "ServerBox will write and execute a script in `~/.config/server_box` after connection. For more technical details, please visit [Github]({url}).",
|
||||
"bgRun": "Run in backgroud",
|
||||
"bgRunTip": "This switch only means the program will try to run in the background, whether it can run in the background depends on whether the permission is enabled or not. For native Android, please disable \"Battery Optimization\" in this app, and for miui, please change the power saving policy to \"Unlimited\".",
|
||||
"bgRun": "Run in background",
|
||||
"bgRunTip": "This switch only means the program will try to run in the background. Whether it can run in the background depends on whether the permission is enabled or not. For AOSP-based Android ROMs, please disable \"Battery Optimization\" in this app. For MIUI / HyperOS, please change the power saving policy to \"Unlimited\".",
|
||||
"bioAuth": "Biometric auth",
|
||||
"browser": "Browser",
|
||||
"bulkImportServers": "Batch import servers",
|
||||
@@ -56,7 +54,7 @@
|
||||
"convert": "Convert",
|
||||
"copy": "Copy",
|
||||
"copyPath": "Copy path",
|
||||
"cpuViewAsProgressTip": "Display the usage rate of each CPU in a progress bar style (old style)",
|
||||
"cpuViewAsProgressTip": "Display the usage of each CPU in a progress bar style (old style)",
|
||||
"createFile": "Create file",
|
||||
"createFolder": "Create folder",
|
||||
"cursorType": "Cursor type",
|
||||
@@ -69,10 +67,9 @@
|
||||
"decode": "Decode",
|
||||
"decompress": "Decompress",
|
||||
"delete": "Delete",
|
||||
"deleteScripts": "Delete server scripts at the same time",
|
||||
"deleteServers": "Batch delete servers",
|
||||
"deviceName": "Device name",
|
||||
"dirEmpty": "Make sure dir is empty.",
|
||||
"dirEmpty": "Make sure the folder is empty.",
|
||||
"disabled": "Disabled",
|
||||
"disconnected": "Disconnected",
|
||||
"disk": "Disk",
|
||||
@@ -93,16 +90,18 @@
|
||||
"edit": "Edit",
|
||||
"editVirtKeys": "Edit virtual keys",
|
||||
"editor": "Editor",
|
||||
"editorHighlightTip": "The current code highlighting performance is worse and can be optionally turned off to improve.",
|
||||
"editorHighlightTip": "The current code highlighting performance is not ideal and can be optionally turned off to improve.",
|
||||
"encode": "Encode",
|
||||
"error": "Error",
|
||||
"exampleName": "Example name",
|
||||
"experimentalFeature": "Experimental feature",
|
||||
"export": "Export",
|
||||
"extraArgs": "Extra args",
|
||||
"extraArgs": "Extra arguments",
|
||||
"failed": "Failed",
|
||||
"fallbackSshDest": "Fallback SSH destination",
|
||||
"fdroidReleaseTip": "If you downloaded this app from F-Droid, it is recommended to turn off this option.",
|
||||
"feedback": "Feedback",
|
||||
"feedbackOnGithub": "If you have any questions, please feedback on Github.",
|
||||
"feedbackOnGithub": "If you have any questions, please create issues on Github.",
|
||||
"fieldMustNotEmpty": "These fields must not be empty.",
|
||||
"fileNotExist": "{file} not exist",
|
||||
"fileTooLarge": "File '{file}' too large {size}, max {sizeMax}",
|
||||
@@ -124,7 +123,7 @@
|
||||
"goto": "Go to",
|
||||
"hideTitleBar": "Hide title bar",
|
||||
"hideTitleBarTip": "After turning it on, please hold down the three buttons in the top right corner to drag.",
|
||||
"highlight": "Code highlight",
|
||||
"highlight": "Code highlighting",
|
||||
"homeWidgetUrlConfig": "Config home widget url",
|
||||
"host": "Host",
|
||||
"hour": "Hour",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Images list",
|
||||
"import": "Import",
|
||||
"inAppUpdate": "Update within the app? Otherwise, download using a browser.",
|
||||
"init": "Initialize",
|
||||
"inner": "Inner",
|
||||
"inputDomainHere": "Input Domain here",
|
||||
"install": "install",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "English",
|
||||
"lastTry": "Last try",
|
||||
"launchPage": "Launch page",
|
||||
"letterCache": "Letter caching",
|
||||
"letterCacheTip": "Recommended to enable, but enabling it prevents the input of CJK (Chinese, Japanese, Korean) characters",
|
||||
"license": "License",
|
||||
"light": "Light",
|
||||
"loadingFiles": "Loading files...",
|
||||
@@ -162,7 +164,7 @@
|
||||
"madeWithLove": "Made with ❤️ by {myGithub}",
|
||||
"manual": "Manual",
|
||||
"max": "max",
|
||||
"maxRetryCount": "Number of server reconnection",
|
||||
"maxRetryCount": "Number of server reconnections",
|
||||
"maxRetryCountEqual0": "Will retry again and again.",
|
||||
"min": "min",
|
||||
"minute": "Minute",
|
||||
@@ -172,13 +174,14 @@
|
||||
"ms": "ms",
|
||||
"name": "Name",
|
||||
"needHomeDir": "If you are a Synology user, [see here](https://kb.synology.com/DSM/tutorial/user_enable_home_service). Users of other systems need to search for how to create a home directory.",
|
||||
"needRestart": "Need to restart app",
|
||||
"net": "Net",
|
||||
"netViewType": "Net view type",
|
||||
"needRestart": "App needs to be restarted",
|
||||
"net": "Network",
|
||||
"netViewType": "Network view type",
|
||||
"newContainer": "New container",
|
||||
"noClient": "No client",
|
||||
"noInterface": "No interface",
|
||||
"noLineChart": "Do not use line charts",
|
||||
"noLineChartForCpu": "Do not use line charts for CPU",
|
||||
"noNotiPerm": "No notification permissions, possibly no progress indication when downloading app updates.",
|
||||
"noOptions": "No options",
|
||||
"noPrivateKeyTip": "The private key does not exist, it may have been deleted or there is a configuration error.",
|
||||
@@ -197,22 +200,23 @@
|
||||
"ok": "OK",
|
||||
"onServerDetailPage": "On server detail page",
|
||||
"onlyOneLine": "Only display as one line (scrollable)",
|
||||
"onlyWhenCoreBiggerThan8": "Works only when the number of cores > 8",
|
||||
"onlyWhenCoreBiggerThan8": "Works only when the number of cores is greater than 8",
|
||||
"open": "Open",
|
||||
"openLastPath": "Open the last path",
|
||||
"openLastPathTip": "Different servers will have different logs, and the log is the path to the exit",
|
||||
"parseContainerStats": "Parse the container occupancy status",
|
||||
"parseContainerStatsTip": "Docker parsing the occupancy status is relatively slow.",
|
||||
"parseContainerStatsTip": "Parsing the occupancy status of Docker is relatively slow.",
|
||||
"paste": "Paste",
|
||||
"path": "Path",
|
||||
"percentOfSize": "{percent}% of {size}",
|
||||
"permission": "Permissions",
|
||||
"pickFile": "Pick file",
|
||||
"pingAvg": "Avg:",
|
||||
"pingInputIP": "Please input a target IP / domain.",
|
||||
"pingNoServer": "No server to ping.\nPlease add a server in server tab.",
|
||||
"pkg": "Pkg",
|
||||
"pkgUpgradeTip": "Please backup your system before updating.",
|
||||
"platformNotSupportUpdate": "Current platform does not support in app update.\nPlease build from source and install it.",
|
||||
"platformNotSupportUpdate": "Current platform does not support in-app update.\nPlease build from source and install it.",
|
||||
"plugInType": "Insertion Type",
|
||||
"plzEnterHost": "Please enter host.",
|
||||
"plzSelectKey": "Please select a key.",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Remember the selection",
|
||||
"rememberPwdInMem": "Remember password in memory",
|
||||
"rememberPwdInMemTip": "Used for containers, suspending, etc.",
|
||||
"rememberWindowSize": "Remember window size",
|
||||
"remotePath": "Remote path",
|
||||
"rename": "Rename",
|
||||
"reportBugsOnGithubIssue": "Please report bugs on {url}",
|
||||
@@ -249,7 +254,7 @@
|
||||
"sequence": "Sequence",
|
||||
"server": "Server",
|
||||
"serverDetailOrder": "Detail page widget order",
|
||||
"serverFuncBtns": "Server func buttons",
|
||||
"serverFuncBtns": "Server function buttons",
|
||||
"serverOrder": "Server order",
|
||||
"serverTabConnecting": "Connecting...",
|
||||
"serverTabEmpty": "There is no server.\nClick the fab to add one.",
|
||||
@@ -273,14 +278,14 @@
|
||||
"sshTip": "This function is now in the experimental stage.\n\nPlease report bugs on {url} or join our development.",
|
||||
"sshVirtualKeyAutoOff": "Auto switching of virtual keys",
|
||||
"start": "Start",
|
||||
"stats": "Stats",
|
||||
"stats": "Statistics",
|
||||
"stop": "Stop",
|
||||
"stopped": "Stopped",
|
||||
"storage": "Storage",
|
||||
"success": "Success",
|
||||
"supportFmtArgs": "The following formatting parameters are supported:",
|
||||
"suspend": "Suspend",
|
||||
"suspendTip": "The suspend function requires root privileges and systemd support.",
|
||||
"suspendTip": "The suspend function requires root permission and systemd support.",
|
||||
"switchTo": "Switch to {val}",
|
||||
"sync": "Sync",
|
||||
"syncTip": "A restart may be required for some changes to take effect.",
|
||||
@@ -299,10 +304,10 @@
|
||||
"total": "Total",
|
||||
"traffic": "Traffic",
|
||||
"trySudo": "Try using sudo",
|
||||
"ttl": "ttl",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Unknown",
|
||||
"unknownError": "Unknown error",
|
||||
"unkownConvertMode": "Unknown convert mode",
|
||||
"unkownConvertMode": "Unknown conversion mode",
|
||||
"update": "Update",
|
||||
"updateAll": "Update all",
|
||||
"updateIntervalEqual0": "You set to 0, will not update automatically.\nCan't calculate CPU status.",
|
||||
@@ -316,7 +321,7 @@
|
||||
"useCdn": "Using CDN",
|
||||
"useCdnTip": "Non-Chinese users are recommended to use CDN. Would you like to use it?",
|
||||
"useNoPwd": "No password will be used",
|
||||
"usePodmanByDefault": "Defaulting to Podman",
|
||||
"usePodmanByDefault": "Use Podman by default",
|
||||
"used": "Used",
|
||||
"user": "User",
|
||||
"versionHaveUpdate": "Found: v1.0.{build}, click to update",
|
||||
@@ -324,13 +329,13 @@
|
||||
"versionUpdated": "Current: v1.0.{build}, is up to date",
|
||||
"view": "View",
|
||||
"viewErr": "See error",
|
||||
"virtKeyHelpClipboard": "Copy to the clipboard if terminal selected is not empty, otherwise paste the contents of the clipboard to the terminal.",
|
||||
"virtKeyHelpClipboard": "Copy to the clipboard if the selected terminal is not empty, otherwise paste the content of the clipboard to the terminal.",
|
||||
"virtKeyHelpIME": "Turn on/off the keyboard",
|
||||
"virtKeyHelpSFTP": "Open current directory in SFTP.",
|
||||
"waitConnection": "Please wait for the connection to be established.",
|
||||
"wakeLock": "Keep awake",
|
||||
"watchNotPaired": "No paired Apple Watch",
|
||||
"webdavSettingEmpty": "Webdav setting is empty",
|
||||
"webdavSettingEmpty": "WebDav setting is empty",
|
||||
"whenOpenApp": "When opening the app",
|
||||
"willTakEeffectImmediately": "Will take effect immediately",
|
||||
"wolTip": "After configuring WOL (Wake-on-LAN), a WOL request is sent each time the server is connected.",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Dirección",
|
||||
"all": "Todos",
|
||||
"alreadyLastDir": "Ya estás en el directorio superior",
|
||||
"alterUrl": "URL alternativa",
|
||||
"askContinue": "{msg}, ¿continuar?",
|
||||
"attention": "Atención",
|
||||
"authFailTip": "La autenticación ha fallado, por favor verifica si la contraseña/llave/host/usuario, etc., son incorrectos.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Los datos exportados solo están encriptados de manera básica, por favor guárdalos en un lugar seguro.",
|
||||
"backupVersionNotMatch": "La versión de la copia de seguridad no coincide, no se puede restaurar",
|
||||
"battery": "Batería",
|
||||
"beforeConnect": "ServerBox escribirá y ejecutará un script en `~/.config/server_box` después de la conexión. Para más detalles técnicos, por favor visite [Github]({url}).",
|
||||
"bgRun": "Ejecución en segundo plano",
|
||||
"bgRunTip": "Este interruptor solo indica que la aplicación intentará correr en segundo plano, si puede hacerlo o no depende de si tiene el permiso correspondiente. En Android puro, por favor desactiva la “optimización de batería” para esta app, en MIUI por favor cambia la estrategia de ahorro de energía a “Sin restricciones”.",
|
||||
"bioAuth": "Autenticación biométrica",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Decodificar",
|
||||
"decompress": "Descomprimir",
|
||||
"delete": "Eliminar",
|
||||
"deleteScripts": "Eliminar scripts del servidor simultáneamente",
|
||||
"deleteServers": "Eliminar servidores en lote",
|
||||
"deviceName": "Nombre del dispositivo",
|
||||
"dirEmpty": "Asegúrate de que el directorio esté vacío",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Exportar",
|
||||
"extraArgs": "Argumentos extra",
|
||||
"failed": "Fallido",
|
||||
"fallbackSshDest": "Destino SSH alternativo",
|
||||
"fdroidReleaseTip": "Si descargaste esta aplicación desde F-Droid, se recomienda desactivar esta opción.",
|
||||
"feedback": "Retroalimentación",
|
||||
"feedbackOnGithub": "Si tienes algún problema, por favor informa en GitHub",
|
||||
"fieldMustNotEmpty": "Estos campos no pueden estar vacíos.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Lista de imágenes",
|
||||
"import": "Importar",
|
||||
"inAppUpdate": "¿Actualizar dentro de la app? De lo contrario, descargar usando un navegador.",
|
||||
"init": "Inicializar",
|
||||
"inner": "Interno",
|
||||
"inputDomainHere": "Introduce el dominio aquí",
|
||||
"install": "Instalar",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Español",
|
||||
"lastTry": "Último intento",
|
||||
"launchPage": "Página de lanzamiento",
|
||||
"letterCache": "Caché de letras",
|
||||
"letterCacheTip": "Se recomienda activar, pero al activarlo se impide la introducción de caracteres CJK (chino, japonés, coreano)",
|
||||
"license": "Licencia de código abierto",
|
||||
"light": "Claro",
|
||||
"loadingFiles": "Cargando directorio...",
|
||||
@@ -179,6 +181,7 @@
|
||||
"noClient": "No hay conexión SSH",
|
||||
"noInterface": "No hay interfaz disponible",
|
||||
"noLineChart": "No utilice gráficos de líneas",
|
||||
"noLineChartForCpu": "No utilice gráficos lineales para la CPU",
|
||||
"noNotiPerm": "Sin permisos de notificación, posiblemente sin indicación de progreso al descargar actualizaciones de la aplicación.",
|
||||
"noOptions": "Sin opciones disponibles",
|
||||
"noPrivateKeyTip": "La clave privada no existe, puede haber sido eliminada o hay un error de configuración.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "Pegar",
|
||||
"path": "Ruta",
|
||||
"percentOfSize": "El {percent}% de {size}",
|
||||
"permission": "Permisos",
|
||||
"pickFile": "Seleccionar archivo",
|
||||
"pingAvg": "Promedio:",
|
||||
"pingInputIP": "Por favor, introduce la IP de destino o el dominio",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Recordar la selección",
|
||||
"rememberPwdInMem": "Recordar contraseña en la memoria",
|
||||
"rememberPwdInMemTip": "Utilizado para contenedores, suspensión, etc.",
|
||||
"rememberWindowSize": "Recordar el tamaño de la ventana",
|
||||
"remotePath": "Ruta remota",
|
||||
"rename": "Renombrar",
|
||||
"reportBugsOnGithubIssue": "Por favor, informa los problemas en {url}",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "Total",
|
||||
"traffic": "Tráfico",
|
||||
"trySudo": "Intentar con sudo",
|
||||
"ttl": "Tiempo de vida (TTL)",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Desconocido",
|
||||
"unknownError": "Error desconocido",
|
||||
"unkownConvertMode": "Modo de conversión desconocido",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Adresse",
|
||||
"all": "Tous",
|
||||
"alreadyLastDir": "Déjà dans le dernier répertoire.",
|
||||
"alterUrl": "Modifier l'URL",
|
||||
"askContinue": "{msg}. Continuer ?",
|
||||
"attention": "Attention",
|
||||
"authFailTip": "Échec de l'authentification. Veuillez vérifier si le mot de passe/clé/hôte/utilisateur, etc., est incorrect.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Les données exportées sont simplement chiffrées. \nVeuillez les garder en sécurité.",
|
||||
"backupVersionNotMatch": "La version de sauvegarde ne correspond pas.",
|
||||
"battery": "Batterie",
|
||||
"beforeConnect": "ServerBox écrira et exécutera un script dans `~/.config/server_box` après la connexion. Pour plus de détails techniques, veuillez visiter [Github]({url}).",
|
||||
"bgRun": "Exécution en arrière-plan",
|
||||
"bgRunTip": "Cette option signifie seulement que le programme essaiera de s'exécuter en arrière-plan, que cela soit possible dépend de l'autorisation activée ou non. Pour Android natif, veuillez désactiver l'« Optimisation de la batterie » dans cette application, et pour MIUI, veuillez changer la politique d'économie d'énergie en « Illimité ».",
|
||||
"bioAuth": "Authentification biométrique",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Décoder",
|
||||
"decompress": "Décompresser",
|
||||
"delete": "Supprimer",
|
||||
"deleteScripts": "Supprimer les scripts du serveur en même temps",
|
||||
"deleteServers": "Supprimer des serveurs en lot",
|
||||
"deviceName": "Nom de l'appareil",
|
||||
"dirEmpty": "Assurez-vous que le répertoire est vide.",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Exporter",
|
||||
"extraArgs": "Arguments supplémentaires",
|
||||
"failed": "Échoué",
|
||||
"fallbackSshDest": "Destino SSH alternativo",
|
||||
"fdroidReleaseTip": "Si vous avez téléchargé cette application depuis F-Droid, il est recommandé de désactiver cette option.",
|
||||
"feedback": "Retour",
|
||||
"feedbackOnGithub": "Si vous avez des questions, veuillez donner votre avis sur Github.",
|
||||
"fieldMustNotEmpty": "Ces champs ne doivent pas être vides.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Liste des images",
|
||||
"import": "Importer",
|
||||
"inAppUpdate": "Mettre à jour dans l'application ? Sinon, téléchargez en utilisant un navigateur.",
|
||||
"init": "Initialiser",
|
||||
"inner": "Interne",
|
||||
"inputDomainHere": "Saisissez le domaine ici",
|
||||
"install": "Installer",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Français",
|
||||
"lastTry": "Dernière tentative",
|
||||
"launchPage": "Page de lancement",
|
||||
"letterCache": "Mise en cache des lettres",
|
||||
"letterCacheTip": "Recommandé à activer, mais son activation empêche la saisie de caractères CJK (chinois, japonais, coréen)",
|
||||
"license": "Licence",
|
||||
"light": "Clair",
|
||||
"loadingFiles": "Chargement des fichiers...",
|
||||
@@ -179,6 +181,7 @@
|
||||
"noClient": "Pas de client",
|
||||
"noInterface": "Pas d'interface",
|
||||
"noLineChart": "Ne pas utiliser de graphiques linéaires",
|
||||
"noLineChartForCpu": "Ne pas utiliser de graphiques linéaires pour l'unité centrale",
|
||||
"noNotiPerm": "Pas de permissions de notification, peut-être pas d'indication de progression lors de la mise à jour des applications.",
|
||||
"noOptions": "Pas d'options",
|
||||
"noPrivateKeyTip": "La clé privée n'existe pas, elle a peut-être été supprimée ou il y a une erreur de configuration.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "Coller",
|
||||
"path": "Chemin",
|
||||
"percentOfSize": "{percent}% de {size}",
|
||||
"permission": "Permissions",
|
||||
"pickFile": "Choisir un fichier",
|
||||
"pingAvg": "Moy.:",
|
||||
"pingInputIP": "Veuillez saisir une adresse IP / un domaine cible.",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Se souvenir du choix",
|
||||
"rememberPwdInMem": "Mémoriser le mot de passe en mémoire",
|
||||
"rememberPwdInMemTip": "Utilisé pour les conteneurs, la suspension, etc.",
|
||||
"rememberWindowSize": "Se souvenir de la taille de la fenêtre",
|
||||
"remotePath": "Chemin distant",
|
||||
"rename": "Renommer",
|
||||
"reportBugsOnGithubIssue": "Veuillez signaler les bugs sur {url}",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "Total",
|
||||
"traffic": "Trafic",
|
||||
"trySudo": "Essayer d'utiliser sudo",
|
||||
"ttl": "ttl",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Inconnu",
|
||||
"unknownError": "Erreur inconnue",
|
||||
"unkownConvertMode": "Mode de conversion inconnu",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Alamat",
|
||||
"all": "Semua",
|
||||
"alreadyLastDir": "Sudah di direktori terakhir.",
|
||||
"alterUrl": "Alter url",
|
||||
"askContinue": "{msg}, lanjutkan?",
|
||||
"attention": "Perhatian",
|
||||
"authFailTip": "Otentikasi gagal, silakan periksa apakah kata sandi/kunci/host/pengguna, dll, salah.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Data yang diekspor hanya dienkripsi.\nTolong jaga keamanannya.",
|
||||
"backupVersionNotMatch": "Versi cadangan tidak cocok.",
|
||||
"battery": "Baterai",
|
||||
"beforeConnect": "ServerBox akan menulis dan menjalankan skrip di `~/.config/server_box` setelah koneksi. Untuk detail teknis lebih lanjut, silakan kunjungi [Github]({url}).",
|
||||
"bgRun": "Jalankan di Backgroud",
|
||||
"bgRunTip": "Sakelar ini hanya berarti aplikasi akan mencoba berjalan di latar belakang, apakah aplikasi dapat berjalan di latar belakang tergantung pada apakah izin diaktifkan atau tidak. Untuk Android asli, nonaktifkan \"Pengoptimalan Baterai\" di aplikasi ini, dan untuk miui, ubah kebijakan penghematan daya ke \"Tidak Terbatas\".",
|
||||
"bioAuth": "Biosertifikasi",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Membaca sandi",
|
||||
"decompress": "Dekompresi",
|
||||
"delete": "Menghapus",
|
||||
"deleteScripts": "Menghapus skrip server secara bersamaan",
|
||||
"deleteServers": "Penghapusan server secara batch",
|
||||
"deviceName": "Nama perangkat",
|
||||
"dirEmpty": "Pastikan dir kosong.",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Ekspor",
|
||||
"extraArgs": "Args ekstra",
|
||||
"failed": "Gagal",
|
||||
"fallbackSshDest": "Tujuan SSH mundur",
|
||||
"fdroidReleaseTip": "Jika Anda mengunduh aplikasi ini dari F-Droid, disarankan untuk mematikan opsi ini.",
|
||||
"feedback": "Masukan",
|
||||
"feedbackOnGithub": "Jika Anda memiliki pertanyaan, silakan umpan balik tentang GitHub.",
|
||||
"fieldMustNotEmpty": "Bidang -bidang ini tidak boleh kosong.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Daftar gambar",
|
||||
"import": "Impor",
|
||||
"inAppUpdate": "Perbarui di dalam aplikasi? Jika tidak, unduh menggunakan browser.",
|
||||
"init": "Menginisialisasi",
|
||||
"inner": "Batin",
|
||||
"inputDomainHere": "Input domain di sini",
|
||||
"install": "Install",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Indonesia",
|
||||
"lastTry": "Percobaan terakhir",
|
||||
"launchPage": "Halaman peluncuran",
|
||||
"letterCache": "Caching huruf",
|
||||
"letterCacheTip": "Disarankan untuk diaktifkan, tetapi mengaktifkannya mencegah input karakter CJK (Cina, Jepang, Korea)",
|
||||
"license": "Lisensi",
|
||||
"light": "Terang",
|
||||
"loadingFiles": "Memuat file ...",
|
||||
@@ -173,12 +175,13 @@
|
||||
"name": "Nama",
|
||||
"needHomeDir": "Jika Anda pengguna Synology, [lihat di sini](https://kb.synology.com/DSM/tutorial/user_enable_home_service). Pengguna sistem lain perlu mencari cara membuat direktori home.",
|
||||
"needRestart": "Perlu memulai ulang aplikasi",
|
||||
"net": "Net",
|
||||
"net": "Jaringan",
|
||||
"netViewType": "Jenis tampilan bersih",
|
||||
"newContainer": "Wadah baru",
|
||||
"noClient": "Tidak ada klien",
|
||||
"noInterface": "Tidak ada antarmuka",
|
||||
"noLineChart": "Jangan gunakan grafik garis",
|
||||
"noLineChartForCpu": "Jangan gunakan diagram garis untuk CPU",
|
||||
"noNotiPerm": "Tidak ada izin notifikasi, mungkin tidak ada indikasi kemajuan saat mengunduh pembaruan aplikasi.",
|
||||
"noOptions": "Tidak ada opsi",
|
||||
"noPrivateKeyTip": "Kunci privat tidak ada, mungkin telah dihapus atau ada kesalahan konfigurasi.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "Tempel",
|
||||
"path": "Jalur",
|
||||
"percentOfSize": "{percent}% dari {size}",
|
||||
"permission": "Izin",
|
||||
"pickFile": "Pilih file",
|
||||
"pingAvg": "Rata -rata:",
|
||||
"pingInputIP": "Harap masukkan IP / domain target.",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Ingat pilihan",
|
||||
"rememberPwdInMem": "Ingat kata sandi di dalam memori",
|
||||
"rememberPwdInMemTip": "Digunakan untuk kontainer, menangguhkan, dll.",
|
||||
"rememberWindowSize": "Ingat ukuran jendela",
|
||||
"remotePath": "Jalur jarak jauh",
|
||||
"rename": "Ganti nama",
|
||||
"reportBugsOnGithubIssue": "Harap laporkan bug di {url}",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "Total",
|
||||
"traffic": "Lalu lintas",
|
||||
"trySudo": "Cobalah menggunakan sudo",
|
||||
"ttl": "ttl",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Tidak dikenal",
|
||||
"unknownError": "Kesalahan yang tidak diketahui",
|
||||
"unkownConvertMode": "Mode Konversi Tidak Diketahui",
|
||||
|
||||
@@ -5,13 +5,12 @@
|
||||
"acceptBeta": "テストバージョンの更新を受け入れる",
|
||||
"add": "追加",
|
||||
"addAServer": "サーバーを追加する",
|
||||
"addPrivateKey": "プライベートキーを追加",
|
||||
"addSystemPrivateKeyTip": "現在プライベートキーがありません。システムのデフォルト(~/.ssh/id_rsa)を追加しますか?",
|
||||
"addPrivateKey": "秘密鍵を追加",
|
||||
"addSystemPrivateKeyTip": "現在秘密鍵がありません。システムのデフォルト(~/.ssh/id_rsa)を追加しますか?",
|
||||
"added2List": "タスクリストに追加されました",
|
||||
"addr": "住所",
|
||||
"addr": "アドレス",
|
||||
"all": "すべて",
|
||||
"alreadyLastDir": "すでに最上位のディレクトリです",
|
||||
"alterUrl": "代替リンク",
|
||||
"askContinue": "{msg}、続行しますか?",
|
||||
"attention": "注意",
|
||||
"authFailTip": "認証に失敗しました。パスワード/鍵/ホスト/ユーザーなどが間違っていないか確認してください。",
|
||||
@@ -26,9 +25,8 @@
|
||||
"backupTip": "エクスポートされたデータは簡単に暗号化されています。適切に保管してください。",
|
||||
"backupVersionNotMatch": "バックアップバージョンが一致しないため、復元できません",
|
||||
"battery": "バッテリー",
|
||||
"beforeConnect": "ServerBoxは接続後に`~/.config/server_box`にスクリプトを書き込み実行します。詳細な技術情報については[Github]({url})をご覧ください。",
|
||||
"bgRun": "バックグラウンド実行",
|
||||
"bgRunTip": "このスイッチはプログラムがバックグラウンドで実行を試みることを意味しますが、実際にバックグラウンドで実行できるかどうかは、権限が有効になっているかに依存します。ネイティブAndroidでは、このアプリの「バッテリー最適化」をオフにしてください。MIUIでは、省エネモードを「無制限」に変更してください。",
|
||||
"bgRunTip": "このスイッチはプログラムがバックグラウンドで実行を試みることを意味しますが、実際にバックグラウンドで実行できるかどうかは、権限が有効になっているかに依存します。AOSPベースのAndroid ROMでは、このアプリの「バッテリー最適化」をオフにしてください。MIUIでは、省エネモードを「無制限」に変更してください。",
|
||||
"bioAuth": "生体認証",
|
||||
"browser": "ブラウザ",
|
||||
"bulkImportServers": "サーバーを一括インポートする",
|
||||
@@ -37,7 +35,7 @@
|
||||
"cancel": "キャンセル",
|
||||
"choose": "選択",
|
||||
"chooseFontFile": "フォントファイルを選択",
|
||||
"choosePrivateKey": "プライベートキーを選択",
|
||||
"choosePrivateKey": "秘密鍵を選択",
|
||||
"clear": "クリア",
|
||||
"clipboard": "クリップボード",
|
||||
"close": "閉じる",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "デコード",
|
||||
"decompress": "解凍",
|
||||
"delete": "削除",
|
||||
"deleteScripts": "サーバースクリプトも削除",
|
||||
"deleteServers": "サーバーを一括削除",
|
||||
"deviceName": "デバイス名",
|
||||
"dirEmpty": "フォルダーが空であることを確認してください",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "エクスポート",
|
||||
"extraArgs": "追加引数",
|
||||
"failed": "失敗しました",
|
||||
"fallbackSshDest": "フォールバックSSH宛先",
|
||||
"fdroidReleaseTip": "このアプリをF-Droidからダウンロードした場合、このオプションをオフにすることをお勧めします。",
|
||||
"feedback": "フィードバック",
|
||||
"feedbackOnGithub": "問題がある場合は、GitHubでフィードバックしてください",
|
||||
"fieldMustNotEmpty": "これらの入力フィールドは空にできません。",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "イメージリスト",
|
||||
"import": "インポート",
|
||||
"inAppUpdate": "アプリ内で更新しますか?それ以外の場合は、ブラウザを使用してダウンロードしてください。",
|
||||
"init": "初期化する",
|
||||
"inner": "内蔵",
|
||||
"inputDomainHere": "ここにドメインを入力",
|
||||
"install": "インストール",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "日本語",
|
||||
"lastTry": "最後の試み",
|
||||
"launchPage": "起動ページ",
|
||||
"letterCache": "文字キャッシング",
|
||||
"letterCacheTip": "有効化を推奨しますが、有効にするとCJK(中国語、日本語、韓国語)の文字の入力ができなくなります",
|
||||
"license": "オープンソースライセンス",
|
||||
"light": "ライト",
|
||||
"loadingFiles": "ディレクトリを読み込んでいます...",
|
||||
@@ -179,12 +181,13 @@
|
||||
"noClient": "SSH接続がありません",
|
||||
"noInterface": "使用可能なインターフェースがありません",
|
||||
"noLineChart": "折れ線グラフを使用しない",
|
||||
"noLineChartForCpu": "CPUに折れ線グラフを使わない",
|
||||
"noNotiPerm": "通知の権限がないため、アプリの更新のダウンロード中に進行状況が表示されない場合があります。",
|
||||
"noOptions": "選択肢がありません",
|
||||
"noPrivateKeyTip": "私有鍵が存在しません。削除されたか、設定ミスがある可能性があります。",
|
||||
"noPrivateKeyTip": "秘密鍵が存在しません。削除されたか、設定ミスがある可能性があります。",
|
||||
"noPromptAgain": "再度確認しない",
|
||||
"noResult": "結果なし",
|
||||
"noSavedPrivateKey": "保存されたプライベートキーがありません。",
|
||||
"noSavedPrivateKey": "保存された秘密鍵がありません。",
|
||||
"noSavedSnippet": "保存されたスニペットがありません。",
|
||||
"noServerAvailable": "使用可能なサーバーがありません。",
|
||||
"noTask": "タスクがありません",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "貼り付け",
|
||||
"path": "パス",
|
||||
"percentOfSize": "{size} の {percent}%",
|
||||
"permission": "権限",
|
||||
"pickFile": "ファイルを選択",
|
||||
"pingAvg": "平均:",
|
||||
"pingInputIP": "対象のIPまたはドメインを入力してください",
|
||||
@@ -215,11 +219,11 @@
|
||||
"platformNotSupportUpdate": "現在のプラットフォームは更新をサポートしていません。最新のソースコードをコンパイルして手動でインストールしてください",
|
||||
"plugInType": "挿入タイプ",
|
||||
"plzEnterHost": "ホストを入力してください",
|
||||
"plzSelectKey": "プライベートキーを選択してください",
|
||||
"plzSelectKey": "秘密鍵を選択してください",
|
||||
"port": "ポート",
|
||||
"preview": "プレビュー",
|
||||
"primaryColorSeed": "プライマリーカラーシード",
|
||||
"privateKey": "プライベートキー",
|
||||
"privateKey": "秘密鍵",
|
||||
"process": "プロセス",
|
||||
"pushToken": "プッシュトークン",
|
||||
"pveIgnoreCertTip": "オプションを有効にすることは推奨されません、セキュリティリスクに注意してください!PVEのデフォルト証明書を使用している場合は、このオプションを有効にする必要があります。",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "選択を記憶する",
|
||||
"rememberPwdInMem": "メモリにパスワードを記憶する",
|
||||
"rememberPwdInMemTip": "コンテナ、一時停止などに使用されます。",
|
||||
"rememberWindowSize": "ウィンドウサイズを記憶する",
|
||||
"remotePath": "リモートパス",
|
||||
"rename": "名前を変更",
|
||||
"reportBugsOnGithubIssue": "{url}で問題を報告してください",
|
||||
@@ -255,7 +260,7 @@
|
||||
"serverTabEmpty": "現在サーバーはありません。\n右下のボタンをクリックして追加してください。",
|
||||
"serverTabFailed": "失敗",
|
||||
"serverTabLoading": "読み込み中...",
|
||||
"serverTabPlzSave": "このプライベートキーを再保存してください",
|
||||
"serverTabPlzSave": "この秘密鍵を再保存してください",
|
||||
"serverTabUnkown": "不明な状態",
|
||||
"setting": "設定",
|
||||
"sftpDlPrepare": "サーバーへの接続を準備中...",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Adres",
|
||||
"all": "Alle",
|
||||
"alreadyLastDir": "Al in de laatst gebruikte map.",
|
||||
"alterUrl": "Url wijzigen",
|
||||
"askContinue": "{msg}. Doorgaan?",
|
||||
"attention": "Let op",
|
||||
"authFailTip": "Authenticatie mislukt, controleer of het wachtwoord/sleutel/host/gebruiker, enz., incorrect zijn.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "De geëxporteerde gegevens zijn simpelweg versleuteld. \nBewaar deze aub veilig.",
|
||||
"backupVersionNotMatch": "Back-upversie komt niet overeen.",
|
||||
"battery": "Batterij",
|
||||
"beforeConnect": "ServerBox zal na verbinding een script schrijven en uitvoeren in `~/.config/server_box`. Voor meer technische details, bezoek [Github]({url}).",
|
||||
"bgRun": "Uitvoeren op de achtergrond",
|
||||
"bgRunTip": "Deze schakelaar betekent alleen dat het programma zal proberen op de achtergrond uit te voeren, of het in de achtergrond kan worden uitgevoerd, hangt af van of de toestemming is ingeschakeld of niet. Voor native Android, schakel \"Batterijoptimalisatie\" uit in deze app, en voor miui, wijzig de energiebesparingsbeleid naar \"Onbeperkt\".",
|
||||
"bioAuth": "Biometrische authenticatie",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Decoderen",
|
||||
"decompress": "Decomprimeren",
|
||||
"delete": "Verwijderen",
|
||||
"deleteScripts": "Verwijder tegelijkertijd serverscripts",
|
||||
"deleteServers": "Servers batchgewijs verwijderen",
|
||||
"deviceName": "Apparaatnaam",
|
||||
"dirEmpty": "Zorg ervoor dat de map leeg is.",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Exporteren",
|
||||
"extraArgs": "Extra argumenten",
|
||||
"failed": "Mislukt",
|
||||
"fallbackSshDest": "Fallback SSH-bestemming",
|
||||
"fdroidReleaseTip": "Als u deze app van F-Droid heeft gedownload, wordt aanbevolen deze optie uit te schakelen.",
|
||||
"feedback": "Feedback",
|
||||
"feedbackOnGithub": "Als je vragen hebt, geef dan feedback op Github.",
|
||||
"fieldMustNotEmpty": "Deze velden mogen niet leeg zijn.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Lijst met afbeeldingen",
|
||||
"import": "Importeren",
|
||||
"inAppUpdate": "Bijwerken binnen de app? Anders downloaden via een browser.",
|
||||
"init": "Initialiseren",
|
||||
"inner": "Intern",
|
||||
"inputDomainHere": "Voer hier domein in",
|
||||
"install": "Installeren",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Nederlands",
|
||||
"lastTry": "Laatste poging",
|
||||
"launchPage": "Startpagina",
|
||||
"letterCache": "Lettercaching",
|
||||
"letterCacheTip": "Aanbevolen om in te schakelen, maar bij inschakeling wordt de invoer van CJK (Chinees, Japans, Koreaans) tekens voorkomen",
|
||||
"license": "Licentie",
|
||||
"light": "Licht",
|
||||
"loadingFiles": "Bestanden laden...",
|
||||
@@ -178,6 +180,8 @@
|
||||
"newContainer": "Nieuwe container",
|
||||
"noClient": "Geen client",
|
||||
"noInterface": "Geen interface",
|
||||
"noLineChart": "lijndiagrammen gebruiken",
|
||||
"noLineChartForCpu": "Gebruik geen lijndiagrammen voor CPU",
|
||||
"noNotiPerm": "Geen meldingsmachtigingen, mogelijk geen voortgangsindicatie bij het downloaden van app-updates.",
|
||||
"noOptions": "Geen opties",
|
||||
"noPrivateKeyTip": "De privésleutel bestaat niet, deze is mogelijk verwijderd of er is een configuratiefout.",
|
||||
@@ -205,6 +209,7 @@
|
||||
"paste": "Plakken",
|
||||
"path": "Pad",
|
||||
"percentOfSize": "{percent}% van {size}",
|
||||
"permission": "Machtigingen",
|
||||
"pickFile": "Bestand kiezen",
|
||||
"pingAvg": "Gem:",
|
||||
"pingInputIP": "Voer een doel-IP / domein in.",
|
||||
@@ -230,6 +235,7 @@
|
||||
"rememberChoice": "Selectie onthouden",
|
||||
"rememberPwdInMem": "Wachtwoord onthouden in geheugen",
|
||||
"rememberPwdInMemTip": "Gebruikt voor containers, opschorting, enz.",
|
||||
"rememberWindowSize": "Venstergrootte onthouden",
|
||||
"remotePath": "Extern pad",
|
||||
"rename": "Hernoemen",
|
||||
"reportBugsOnGithubIssue": "Meld alstublieft bugs op {url}",
|
||||
@@ -298,7 +304,7 @@
|
||||
"total": "Totaal",
|
||||
"traffic": "Verkeer",
|
||||
"trySudo": "Probeer sudo te gebruiken",
|
||||
"ttl": "ttl",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Onbekend",
|
||||
"unknownError": "Onbekende fout",
|
||||
"unkownConvertMode": "Onbekende conversiemodus",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Endereço",
|
||||
"all": "Todos",
|
||||
"alreadyLastDir": "Já é o diretório mais alto",
|
||||
"alterUrl": "URL alternativa",
|
||||
"askContinue": "{msg}, continuar?",
|
||||
"attention": "Atenção",
|
||||
"authFailTip": "Autenticação falhou, por favor verifique se a senha/chave/host/usuário, etc., estão incorretos.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Os dados exportados são criptografados de forma simples, por favor, guarde-os com segurança.",
|
||||
"backupVersionNotMatch": "Versão de backup não compatível, não é possível restaurar",
|
||||
"battery": "Bateria",
|
||||
"beforeConnect": "O ServerBox escreverá e executará um script em `~/.config/server_box` após a conexão. Para mais detalhes técnicos, por favor visite [Github]({url}).",
|
||||
"bgRun": "Execução em segundo plano",
|
||||
"bgRunTip": "Este interruptor indica que o programa tentará rodar em segundo plano, mas a capacidade de fazer isso depende das permissões concedidas. No Android nativo, desative a 'Otimização de bateria' para este app, no MIUI, altere a estratégia de economia de energia para 'Sem restrições'.",
|
||||
"bioAuth": "Autenticação biométrica",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "Decodificar",
|
||||
"decompress": "Descomprimir",
|
||||
"delete": "Excluir",
|
||||
"deleteScripts": "Excluir scripts do servidor simultaneamente",
|
||||
"deleteServers": "Excluir servidores em lote",
|
||||
"deviceName": "Nome do dispositivo",
|
||||
"dirEmpty": "Certifique-se de que a pasta está vazia",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "Exportar",
|
||||
"extraArgs": "Argumentos extras",
|
||||
"failed": "Falhou",
|
||||
"fallbackSshDest": "Destino SSH de fallback",
|
||||
"fdroidReleaseTip": "Se você baixou este aplicativo do F-Droid, é recomendado desativar esta opção.",
|
||||
"feedback": "Feedback",
|
||||
"feedbackOnGithub": "Se você tem qualquer problema, por favor, dê feedback no GitHub",
|
||||
"fieldMustNotEmpty": "Estes campos não podem estar vazios.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "Lista de imagens",
|
||||
"import": "Importar",
|
||||
"inAppUpdate": "Atualizar dentro do app? Caso contrário, baixe usando um navegador.",
|
||||
"init": "Inicializar",
|
||||
"inner": "Interno",
|
||||
"inputDomainHere": "Insira o domínio aqui",
|
||||
"install": "Instalar",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Português",
|
||||
"lastTry": "Última tentativa",
|
||||
"launchPage": "Página de lançamento",
|
||||
"letterCache": "Cache de letras",
|
||||
"letterCacheTip": "Recomendado para ativar, mas a ativação impede a entrada de caracteres CJK (chinês, japonês, coreano)",
|
||||
"license": "Licença de código aberto",
|
||||
"light": "Claro",
|
||||
"loadingFiles": "Carregando diretórios...",
|
||||
@@ -178,7 +180,8 @@
|
||||
"newContainer": "Novo contêiner",
|
||||
"noClient": "Sem conexão SSH",
|
||||
"noInterface": "Sem interface disponível",
|
||||
"noLineChart": "Gebruik geen lijndiagrammen",
|
||||
"noLineChart": "Não usar gráficos de linha",
|
||||
"noLineChartForCpu": "Não utilizar gráficos de linhas para a CPU",
|
||||
"noNotiPerm": "Sem permissão de notificação, possivelmente sem indicação de progresso ao baixar atualizações de aplicativos.",
|
||||
"noOptions": "Sem opções",
|
||||
"noPrivateKeyTip": "A chave privada não existe, pode ter sido deletada ou há um erro de configuração.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "Colar",
|
||||
"path": "Caminho",
|
||||
"percentOfSize": "{percent}% de {size}",
|
||||
"permission": "Permissões",
|
||||
"pickFile": "Escolher arquivo",
|
||||
"pingAvg": "Média:",
|
||||
"pingInputIP": "Por favor, insira o IP ou domínio alvo",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Lembrar da seleção",
|
||||
"rememberPwdInMem": "Lembrar senha na memória",
|
||||
"rememberPwdInMemTip": "Usado para contêineres, suspensão, etc.",
|
||||
"rememberWindowSize": "Lembrar o tamanho da janela",
|
||||
"remotePath": "Caminho remoto",
|
||||
"rename": "Renomear",
|
||||
"reportBugsOnGithubIssue": "Por favor, reporte problemas em {url}",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "Total",
|
||||
"traffic": "Tráfego",
|
||||
"trySudo": "Tentar usar sudo",
|
||||
"ttl": "Tempo de vida do cache",
|
||||
"ttl": "TTL",
|
||||
"unknown": "Desconhecido",
|
||||
"unknownError": "Erro desconhecido",
|
||||
"unkownConvertMode": "Modo de conversão desconhecido",
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"addr": "Адрес",
|
||||
"all": "все",
|
||||
"alreadyLastDir": "Уже в корневом каталоге",
|
||||
"alterUrl": "альтернативная ссылка",
|
||||
"askContinue": "{msg}, продолжить?",
|
||||
"attention": "внимание",
|
||||
"authFailTip": "Аутентификация не удалась, пожалуйста, проверьте, правильны ли пароль/ключ/хост/пользователь и т.д.",
|
||||
@@ -26,7 +25,6 @@
|
||||
"backupTip": "Экспортированные данные зашифрованы простым способом, пожалуйста, храните их в безопасности.",
|
||||
"backupVersionNotMatch": "Версия резервной копии не совпадает, восстановление невозможно",
|
||||
"battery": "батарея",
|
||||
"beforeConnect": "ServerBox запишет и выполнит скрипт в `~/.config/server_box` после подключения. Для получения дополнительных технических подробностей, пожалуйста, посетите [Github]({url}).",
|
||||
"bgRun": "работа в фоновом режиме",
|
||||
"bgRunTip": "Этот переключатель означает, что программа будет пытаться работать в фоновом режиме, но фактическое выполнение зависит от того, включено ли разрешение. Для нативного Android отключите «Оптимизацию батареи» для этого приложения, для MIUI измените стратегию энергосбережения на «Без ограничений».",
|
||||
"bioAuth": "биометрическая аутентификация",
|
||||
@@ -69,7 +67,6 @@
|
||||
"decode": "декодировать",
|
||||
"decompress": "разархивировать",
|
||||
"delete": "удалить",
|
||||
"deleteScripts": "удалить скрипты с сервера",
|
||||
"deleteServers": "удалить серверы пакетно",
|
||||
"deviceName": "Название устройства",
|
||||
"dirEmpty": "Пожалуйста, убедитесь, что папка пуста",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "экспорт",
|
||||
"extraArgs": "дополнительные аргументы",
|
||||
"failed": "неудача",
|
||||
"fallbackSshDest": "Резервное место назначения SSH",
|
||||
"fdroidReleaseTip": "Если вы скачали это приложение с F-Droid, рекомендуется отключить эту опцию.",
|
||||
"feedback": "обратная связь",
|
||||
"feedbackOnGithub": "Если у вас есть какие-либо вопросы, пожалуйста, отправьте отзыв на GitHub",
|
||||
"fieldMustNotEmpty": "Эти поля не могут быть пустыми.",
|
||||
@@ -135,6 +134,7 @@
|
||||
"imagesList": "список образов",
|
||||
"import": "импорт",
|
||||
"inAppUpdate": "Обновить в приложении? В противном случае загрузите с помощью браузера.",
|
||||
"init": "Инициализировать",
|
||||
"inner": "встроенный",
|
||||
"inputDomainHere": "введите домен здесь",
|
||||
"install": "установить",
|
||||
@@ -153,6 +153,8 @@
|
||||
"languageName": "Русский",
|
||||
"lastTry": "последняя попытка",
|
||||
"launchPage": "стартовая страница",
|
||||
"letterCache": "Кэширование букв",
|
||||
"letterCacheTip": "Рекомендуется включить, но его активация препятствует вводу символов CJK (китайский, японский, корейский)",
|
||||
"license": "лицензия",
|
||||
"light": "светлая",
|
||||
"loadingFiles": "Загрузка файлов...",
|
||||
@@ -178,7 +180,8 @@
|
||||
"newContainer": "создать контейнер",
|
||||
"noClient": "нет SSH соединения",
|
||||
"noInterface": "нет доступных интерфейсов",
|
||||
"noLineChart": "Não use gráficos de linha",
|
||||
"noLineChart": "Не использовать линейные графики",
|
||||
"noLineChartForCpu": "Не используйте линейные графики для ЦП",
|
||||
"noNotiPerm": "Нет разрешения на уведомления, возможно отсутствие индикации прогресса при загрузке обновлений приложений.",
|
||||
"noOptions": "нет доступных опций",
|
||||
"noPrivateKeyTip": "Приватный ключ не существует, возможно, он был удален или есть ошибка в настройках.",
|
||||
@@ -206,6 +209,7 @@
|
||||
"paste": "вставить",
|
||||
"path": "путь",
|
||||
"percentOfSize": "{percent}% от {size}",
|
||||
"permission": "Разрешения",
|
||||
"pickFile": "выбрать файл",
|
||||
"pingAvg": "Среднее:",
|
||||
"pingInputIP": "Пожалуйста, введите целевой IP или доменное имя",
|
||||
@@ -231,6 +235,7 @@
|
||||
"rememberChoice": "Запомнить выбор",
|
||||
"rememberPwdInMem": "Запомнить пароль в памяти",
|
||||
"rememberPwdInMemTip": "Используется для контейнеров, приостановки и т. д.",
|
||||
"rememberWindowSize": "Запомнить размер окна",
|
||||
"remotePath": "удаленный путь",
|
||||
"rename": "переименовать",
|
||||
"reportBugsOnGithubIssue": "Пожалуйста, сообщайте о проблемах на {url}",
|
||||
@@ -299,7 +304,7 @@
|
||||
"total": "всего",
|
||||
"traffic": "трафик",
|
||||
"trySudo": "попробовать использовать sudo",
|
||||
"ttl": "время жизни кеша",
|
||||
"ttl": "TTL",
|
||||
"unknown": "неизвестно",
|
||||
"unknownError": "неизвестная ошибка",
|
||||
"unkownConvertMode": "неизвестный режим конвертации",
|
||||
|
||||
@@ -5,13 +5,12 @@
|
||||
"acceptBeta": "接受测试版更新推送",
|
||||
"add": "新增",
|
||||
"addAServer": "添加服务器",
|
||||
"addPrivateKey": "添加一个私钥",
|
||||
"addPrivateKey": "添加私钥",
|
||||
"addSystemPrivateKeyTip": "当前没有任何私钥,是否添加系统自带的(~/.ssh/id_rsa)?",
|
||||
"added2List": "已添加至任务列表",
|
||||
"addr": "地址",
|
||||
"all": "所有",
|
||||
"alreadyLastDir": "已经是最上层目录了",
|
||||
"alterUrl": "备选链接",
|
||||
"askContinue": "{msg},继续吗?",
|
||||
"attention": "注意",
|
||||
"authFailTip": "认证失败,请检查密码/密钥/主机/用户等是否错误",
|
||||
@@ -26,9 +25,8 @@
|
||||
"backupTip": "导出的数据仅进行了简单加密,请妥善保管。",
|
||||
"backupVersionNotMatch": "备份版本不匹配,无法恢复",
|
||||
"battery": "电池",
|
||||
"beforeConnect": "ServerBox 将在连接后,在 `~/.config/server_box` 写入脚本并执行,更多的技术细节请访问 [Github]({url})。",
|
||||
"bgRun": "后台运行",
|
||||
"bgRunTip": "此开关只代表程序会尝试在后台运行,具体能否后台运行取决于是否开启了权限。原生 Android 请关闭本 App 的“电池优化”,MIUI 请修改省电策略为“无限制”。",
|
||||
"bgRunTip": "此开关只代表程序会尝试在后台运行,具体能否后台运行取决于是否开启了权限。原生 Android 请关闭本 App 的“电池优化”,MIUI / HyperOS 请修改省电策略为“无限制”。",
|
||||
"bioAuth": "生物认证",
|
||||
"browser": "浏览器",
|
||||
"bulkImportServers": "批量导入服务器",
|
||||
@@ -42,21 +40,21 @@
|
||||
"clipboard": "剪切板",
|
||||
"close": "关闭",
|
||||
"cmd": "命令",
|
||||
"cnKeyboardComp": "中国Android兼容性",
|
||||
"cnKeyboardComp": "中国 Android 兼容性",
|
||||
"cnKeyboardCompTip": "如果终端弹出安全键盘,可以开启",
|
||||
"collapseUI": "折叠",
|
||||
"collapseUITip": "是否默认折叠UI中存在的长列表",
|
||||
"collapseUITip": "是否默认折叠 UI 中的长列表",
|
||||
"conn": "连接",
|
||||
"connected": "已连接",
|
||||
"container": "容器",
|
||||
"containerName": "容器名",
|
||||
"containerStatus": "容器状态",
|
||||
"containerTrySudoTip": "例如:在应用内将用户设置为aaa,但是Docker安装在root用户下,这时就需要启用此选项",
|
||||
"containerTrySudoTip": "例如:在应用内将用户设置为 aaa,但是 Docker 安装在root用户下,这时就需要启用此选项",
|
||||
"content": "内容",
|
||||
"convert": "转换",
|
||||
"copy": "复制",
|
||||
"copyPath": "复制路径",
|
||||
"cpuViewAsProgressTip": "以进度条样式显示每个CPU的使用率(旧版样式)",
|
||||
"cpuViewAsProgressTip": "以进度条样式显示每个 CPU 的使用率(旧版样式)",
|
||||
"createFile": "创建文件",
|
||||
"createFolder": "创建文件夹",
|
||||
"cursorType": "光标类型",
|
||||
@@ -69,24 +67,23 @@
|
||||
"decode": "解码",
|
||||
"decompress": "解压缩",
|
||||
"delete": "删除",
|
||||
"deleteScripts": "同时删除服务器脚本",
|
||||
"deleteServers": "批量删除服务器",
|
||||
"deviceName": "设备名",
|
||||
"dirEmpty": "请确保文件夹为空",
|
||||
"disabled": "已禁用",
|
||||
"disconnected": "连接断开",
|
||||
"disk": "硬盘",
|
||||
"disk": "磁盘",
|
||||
"diskIgnorePath": "忽略的磁盘路径",
|
||||
"displayCpuIndex": "显示CPU索引",
|
||||
"displayCpuIndex": "显示 CPU 索引",
|
||||
"displayName": "显示名称",
|
||||
"dl2Local": "下载 {fileName} 到本地?",
|
||||
"doc": "文档",
|
||||
"dockerEditHost": "编辑 DOCKER_HOST",
|
||||
"dockerEmptyRunningItems": "没有正在运行的容器。\n这可能是因为:\n- Docker 安装用户与 App 内配置的用户名不同\n- 环境变量 DOCKER_HOST 没有被正确读取。你可以通过在终端内运行 `echo $DOCKER_HOST` 来获取。",
|
||||
"dockerEmptyRunningItems": "没有正在运行的容器。\n这可能是因为:\n- Docker 安装用户与 App 内配置的用户名不同\n- 环境变量 DOCKER_HOST 没有被正确读取。可以通过在终端内运行 `echo $DOCKER_HOST` 来获取。",
|
||||
"dockerImagesFmt": "共 {count} 个镜像",
|
||||
"dockerNotInstalled": "Docker 未安装",
|
||||
"dockerStatusRunningAndStoppedFmt": "{runningCount}个正在运行, {stoppedCount}个已停止",
|
||||
"dockerStatusRunningFmt": "{count}个容器正在运行",
|
||||
"dockerStatusRunningAndStoppedFmt": "{runningCount} 个正在运行, {stoppedCount} 个已停止",
|
||||
"dockerStatusRunningFmt": "{count} 个容器正在运行",
|
||||
"doubleColumnMode": "双列模式",
|
||||
"doubleColumnTip": "此选项仅开启功能,实际是否能开启还取决于设备的宽度",
|
||||
"download": "下载",
|
||||
@@ -101,6 +98,8 @@
|
||||
"export": "导出",
|
||||
"extraArgs": "额外参数",
|
||||
"failed": "失败",
|
||||
"fallbackSshDest": "备选 SSH 目标",
|
||||
"fdroidReleaseTip": "如果你是从 F-Droid 下载的本应用,推荐关闭此选项",
|
||||
"feedback": "反馈",
|
||||
"feedbackOnGithub": "如果你有任何问题,请在GitHub反馈",
|
||||
"fieldMustNotEmpty": "这些输入框不能为空。",
|
||||
@@ -117,9 +116,9 @@
|
||||
"fullScreen": "全屏模式",
|
||||
"fullScreenJitter": "全屏模式抖动",
|
||||
"fullScreenJitterHelp": "防止烧屏",
|
||||
"fullScreenTip": "当设备旋转为横屏时,是否开启全屏模式。此选项仅作用于服务器Tab页。",
|
||||
"getPushTokenFailed": "未能获取到推送token",
|
||||
"gettingToken": "正在获取Token...",
|
||||
"fullScreenTip": "当设备旋转为横屏时,是否开启全屏模式。此选项仅作用于服务器 Tab 页。",
|
||||
"getPushTokenFailed": "未能获取到推送 token",
|
||||
"gettingToken": "正在获取 Token...",
|
||||
"goBackQ": "返回?",
|
||||
"goto": "前往",
|
||||
"hideTitleBar": "隐藏标题栏",
|
||||
@@ -129,12 +128,13 @@
|
||||
"host": "主机",
|
||||
"hour": "小时",
|
||||
"httpFailedWithCode": "请求失败, 状态码: {code}",
|
||||
"icloudSynced": "iCloud已同步,某些设置可能需要重启才能生效。",
|
||||
"icloudSynced": "iCloud 已同步,某些设置可能需要重启才能生效。",
|
||||
"ignoreCert": "忽略证书",
|
||||
"image": "镜像",
|
||||
"imagesList": "镜像列表",
|
||||
"import": "导入",
|
||||
"inAppUpdate": "在App内更新?否则使用浏览器下载",
|
||||
"inAppUpdate": "在 App 内更新?否则使用浏览器下载",
|
||||
"init": "初始化",
|
||||
"inner": "内置",
|
||||
"inputDomainHere": "在这里输入域名",
|
||||
"install": "安装",
|
||||
@@ -142,7 +142,7 @@
|
||||
"invalid": "无效",
|
||||
"invalidJson": "无效的 JSON",
|
||||
"invalidVersion": "不支持的版本",
|
||||
"invalidVersionHelp": "请确保正确安装了docker,或者使用的非自编译版本。如果没有以上问题,请在 {url} 提交问题。",
|
||||
"invalidVersionHelp": "请确保正确安装了 docker,或者使用的非自编译版本。如果没有以上问题,请在 {url} 提交问题。",
|
||||
"isBusy": "当前正忙",
|
||||
"jumpServer": "跳板服务器",
|
||||
"keepForeground": "请保持应用处于前台!",
|
||||
@@ -153,7 +153,9 @@
|
||||
"languageName": "简体中文",
|
||||
"lastTry": "最后尝试",
|
||||
"launchPage": "启动页",
|
||||
"license": "开源证书",
|
||||
"letterCache": "输入法字符缓存",
|
||||
"letterCacheTip": "推荐开启,但是开启后无法输入 CJK 等文字",
|
||||
"license": "开源许可证",
|
||||
"light": "亮",
|
||||
"loadingFiles": "正在加载目录。。。",
|
||||
"location": "位置",
|
||||
@@ -176,10 +178,11 @@
|
||||
"net": "网络",
|
||||
"netViewType": "网络视图类型",
|
||||
"newContainer": "新建容器",
|
||||
"noClient": "没有SSH连接",
|
||||
"noClient": "没有 SSH 连接",
|
||||
"noInterface": "没有可用的接口",
|
||||
"noLineChart": "不使用折线图",
|
||||
"noNotiPerm": "无通知权限,可能下载App更新时无进度提示。",
|
||||
"noLineChartForCpu": "CPU 不使用折线图",
|
||||
"noNotiPerm": "无通知权限,可能下载 App 更新时无进度提示。",
|
||||
"noOptions": "无可选项",
|
||||
"noPrivateKeyTip": "私钥不存在,可能已被删除/配置错误",
|
||||
"noPromptAgain": "不再提示",
|
||||
@@ -193,23 +196,24 @@
|
||||
"notAvailable": "不可用",
|
||||
"notSelected": "未选择",
|
||||
"note": "备注",
|
||||
"nullToken": "无Token",
|
||||
"nullToken": "无 Token",
|
||||
"ok": "好",
|
||||
"onServerDetailPage": "在服务器详情页",
|
||||
"onlyOneLine": "仅显示为一行(可滚动)",
|
||||
"onlyWhenCoreBiggerThan8": "仅当核心数>8时生效",
|
||||
"onlyWhenCoreBiggerThan8": "仅当核心数大于 8 时生效",
|
||||
"open": "打开",
|
||||
"openLastPath": "打开上次的路径",
|
||||
"openLastPathTip": "不同的服务器会有不同的记录,且记录的是退出时的路径",
|
||||
"parseContainerStats": "解析容器占用状态",
|
||||
"parseContainerStatsTip": "Docker解析占用状态较为缓慢",
|
||||
"parseContainerStatsTip": "Docker 解析占用状态较为缓慢",
|
||||
"paste": "粘贴",
|
||||
"path": "路径",
|
||||
"percentOfSize": "{size} 的 {percent}%",
|
||||
"permission": "权限",
|
||||
"pickFile": "选择文件",
|
||||
"pingAvg": "平均:",
|
||||
"pingInputIP": "请输入目标IP或域名",
|
||||
"pingNoServer": "没有服务器可用于Ping\n请在服务器tab添加服务器后再试",
|
||||
"pingNoServer": "没有服务器可用于 Ping\n请在服务器 tab 添加服务器后再试",
|
||||
"pkg": "包管理",
|
||||
"pkgUpgradeTip": "请在更新前备份系统。",
|
||||
"platformNotSupportUpdate": "当前平台不支持更新,请编译最新源码后手动安装",
|
||||
@@ -222,21 +226,22 @@
|
||||
"privateKey": "私钥",
|
||||
"process": "进程",
|
||||
"pushToken": "消息推送 Token",
|
||||
"pveIgnoreCertTip": "不推荐开启,注意安全隐患!如果你使用的PVE默认证书,需要开启该选项",
|
||||
"pveLoginFailed": "登录失败。无法使用服务器配置内的用户/密码,以Linux PAM方式登录。",
|
||||
"pveVersionLow": "当前该功能处于测试阶段,仅在PVE 8+上测试过,请谨慎使用",
|
||||
"pveIgnoreCertTip": "不推荐开启,注意安全隐患!如果你使用的 PVE 默认证书,需要开启该选项",
|
||||
"pveLoginFailed": "登录失败。无法使用服务器配置内的用户/密码,以 Linux PAM 方式登录。",
|
||||
"pveVersionLow": "当前该功能处于测试阶段,仅在 PVE 8+ 上测试过,请谨慎使用",
|
||||
"pwd": "密码",
|
||||
"read": "读",
|
||||
"reboot": "重启",
|
||||
"rememberChoice": "记住选择",
|
||||
"rememberPwdInMem": "在内存中记住密码",
|
||||
"rememberPwdInMemTip": "用于容器、挂起等",
|
||||
"rememberWindowSize": "记住窗口大小",
|
||||
"remotePath": "远端路径",
|
||||
"rename": "重命名",
|
||||
"reportBugsOnGithubIssue": "请到 {url} 提交问题",
|
||||
"restart": "重启",
|
||||
"restore": "恢复",
|
||||
"restoreSuccess": "恢复成功,需要重启App来应用更改",
|
||||
"restoreSuccess": "恢复成功,需要重启 App 来应用更改",
|
||||
"result": "结果",
|
||||
"rotateAngel": "旋转角度",
|
||||
"route": "路由",
|
||||
@@ -269,7 +274,7 @@
|
||||
"softWrap": "自动换行",
|
||||
"speed": "速度",
|
||||
"spentTime": "耗时: {time}",
|
||||
"sshTermHelp": "在终端可滚动时,横向拖动可以选中文字。点击键盘按钮可以开启/关闭键盘。文件图标会打开当前路径SFTP。粘贴板按钮会在有选中文字时复制内容,在未选中并且剪切板有内容时粘贴内容到终端。代码图标会粘贴代码片段到终端并执行。",
|
||||
"sshTermHelp": "在终端可滚动时,横向拖动可以选中文字。点击键盘按钮可以开启/关闭键盘。文件图标会打开当前路径 SFTP。剪切板按钮会在有选中文字时复制内容,在未选中并且剪切板有内容时粘贴内容到终端。代码图标会粘贴代码片段到终端并执行。",
|
||||
"sshTip": "该功能目前处于测试阶段。\n\n请在 {url} 反馈问题,或者加入我们开发。",
|
||||
"sshVirtualKeyAutoOff": "虚拟按键自动切换",
|
||||
"start": "开始",
|
||||
@@ -287,7 +292,7 @@
|
||||
"system": "系统",
|
||||
"tag": "标签",
|
||||
"temperature": "温度",
|
||||
"termFontSizeTip": "此设置会影响终端大小(宽高)。可以在终端页面缩放来调整当前会话的字体大小",
|
||||
"termFontSizeTip": "此设置会影响终端大小(宽和高)。可以在终端页面缩放来调整当前会话的字体大小",
|
||||
"terminal": "终端",
|
||||
"test": "测试",
|
||||
"textScaler": "字体缩放",
|
||||
@@ -298,23 +303,23 @@
|
||||
"times": "次",
|
||||
"total": "总共",
|
||||
"traffic": "流量",
|
||||
"trySudo": "尝试使用sudo",
|
||||
"ttl": "缓存时间",
|
||||
"trySudo": "尝试使用 sudo",
|
||||
"ttl": "TTL",
|
||||
"unknown": "未知",
|
||||
"unknownError": "未知错误",
|
||||
"unkownConvertMode": "未知转换模式",
|
||||
"update": "更新",
|
||||
"updateAll": "更新全部",
|
||||
"updateIntervalEqual0": "你设置为0,服务器状态不会自动刷新。\n且不能计算CPU使用情况。",
|
||||
"updateIntervalEqual0": "你设置为 0,服务器状态不会自动刷新。\n且不能计算 CPU 使用情况。",
|
||||
"updateServerStatusInterval": "服务器状态刷新间隔",
|
||||
"updateTip": "新版本: v1.0.{newest}",
|
||||
"updateTipTooLow": "当前版本过低,请升级至 v1.0.{newest}",
|
||||
"upload": "上传",
|
||||
"upsideDown": "上下交换",
|
||||
"uptime": "启动时长",
|
||||
"urlOrJson": "链接或JSON",
|
||||
"useCdn": "使用CDN",
|
||||
"useCdnTip": "非中国大陆用户推荐使用CDN,是否使用?",
|
||||
"urlOrJson": "链接或 JSON",
|
||||
"useCdn": "使用 CDN",
|
||||
"useCdnTip": "非中国大陆用户推荐使用 CDN,是否使用?",
|
||||
"useNoPwd": "将会使用无密码",
|
||||
"usePodmanByDefault": "默认使用 Podman",
|
||||
"used": "已用",
|
||||
@@ -330,10 +335,10 @@
|
||||
"waitConnection": "请等待连接建立",
|
||||
"wakeLock": "保持唤醒",
|
||||
"watchNotPaired": "没有已配对的 Apple Watch",
|
||||
"webdavSettingEmpty": "Webdav 设置项为空",
|
||||
"webdavSettingEmpty": "WebDav 设置项为空",
|
||||
"whenOpenApp": "当打开 App 时",
|
||||
"willTakEeffectImmediately": "更改将会立即生效",
|
||||
"wolTip": "在配置 WOL 后,每次连接服务器都会先发送一次 WOl 请求",
|
||||
"wolTip": "在配置 WOL 后,每次连接服务器都会先发送一次 WOL 请求",
|
||||
"write": "写",
|
||||
"writeScriptFailTip": "写入脚本失败,可能是没有权限/目录不存在等"
|
||||
}
|
||||
@@ -4,31 +4,29 @@
|
||||
"aboutThanks": "感謝以下參與的各位。",
|
||||
"acceptBeta": "接受測試版更新推送",
|
||||
"add": "新增",
|
||||
"addAServer": "新增服務器",
|
||||
"addPrivateKey": "新增一個私鑰",
|
||||
"addSystemPrivateKeyTip": "當前沒有任何私鑰,是否添加系統自帶的(~/.ssh/id_rsa)?",
|
||||
"addAServer": "新增伺服器",
|
||||
"addPrivateKey": "新增私鑰",
|
||||
"addSystemPrivateKeyTip": "當前沒有任何私鑰,是否添加系統自帶的 (~/.ssh/id_rsa)?",
|
||||
"added2List": "已添加至任務列表",
|
||||
"addr": "地址",
|
||||
"addr": "位址",
|
||||
"all": "所有",
|
||||
"alreadyLastDir": "已經是最上層目錄了",
|
||||
"alterUrl": "備選鏈接",
|
||||
"askContinue": "{msg},繼續嗎?",
|
||||
"attention": "注意",
|
||||
"authFailTip": "認證失敗,請檢查密碼/密鑰/主機/用戶等是否錯誤。",
|
||||
"authRequired": "需要認證",
|
||||
"auto": "自動",
|
||||
"autoBackupConflict": "只能同時開啓壹個自動備份",
|
||||
"autoBackupConflict": "只能同時開啓一個自動備份",
|
||||
"autoCheckUpdate": "自動檢查更新",
|
||||
"autoConnect": "自動連接",
|
||||
"autoRun": "自動運行",
|
||||
"autoUpdateHomeWidget": "自動更新桌面小部件",
|
||||
"backup": "備份",
|
||||
"backupTip": "導出的數據僅進行了簡單加密,請妥善保管。",
|
||||
"backupTip": "匯出的資料僅進行了簡單加密,請妥善保管。",
|
||||
"backupVersionNotMatch": "備份版本不匹配,無法還原",
|
||||
"battery": "電池",
|
||||
"beforeConnect": "ServerBox將在連接後,在`~/.config/server_box`寫入腳本並執行,更多的技術細節請訪問[Github]({url})。",
|
||||
"bgRun": "背景運行",
|
||||
"bgRunTip": "此開關只代表程式會嘗試在背景執行,具體能否背景運行取決於是否開啟了權限。 原生 Android 請關閉本 App 的“電池優化”,MIUI 請修改省電策略為“無限制”。",
|
||||
"bgRun": "後台運行",
|
||||
"bgRunTip": "此開關只代表程式會嘗試在後台運行,具體能否在後臺運行取決於是否開啟了權限。 原生 Android 請關閉本 App 的“電池優化”,MIUI / HyperOS 請修改省電策略為“無限制”。",
|
||||
"bioAuth": "生物認證",
|
||||
"browser": "瀏覽器",
|
||||
"bulkImportServers": "批量導入伺服器",
|
||||
@@ -36,48 +34,47 @@
|
||||
"canPullRefresh": "可以下拉更新",
|
||||
"cancel": "取消",
|
||||
"choose": "選擇",
|
||||
"chooseFontFile": "選擇字體文件",
|
||||
"chooseFontFile": "選擇字型檔",
|
||||
"choosePrivateKey": "選擇私鑰",
|
||||
"clear": "清除",
|
||||
"clipboard": "剪切板",
|
||||
"clipboard": "剪貼簿",
|
||||
"close": "關閉",
|
||||
"cmd": "命令",
|
||||
"cnKeyboardComp": "中國Android兼容性",
|
||||
"cnKeyboardComp": "中國 Android 兼容性",
|
||||
"cnKeyboardCompTip": "如果終端彈出安全鍵盤,您可以啟用它。",
|
||||
"collapseUI": "折疊",
|
||||
"collapseUITip": "是否預設折疊UI中存在的長列表",
|
||||
"collapseUITip": "是否預設折疊 UI 中存在的長列表",
|
||||
"conn": "連接",
|
||||
"connected": "已連接",
|
||||
"container": "容器",
|
||||
"containerName": "容器名稱",
|
||||
"containerStatus": "容器狀態",
|
||||
"containerTrySudoTip": "例如:App内设置用户为aaa,但是Docker安装在root用户,这时就需要开启此选项",
|
||||
"containerTrySudoTip": "例如:App 內設置使用者為 aaa,但是 Docker 安裝在 root 使用者,這時就需要開啟此選項",
|
||||
"content": "內容",
|
||||
"convert": "轉換",
|
||||
"copy": "複製",
|
||||
"copyPath": "複製路徑",
|
||||
"cpuViewAsProgressTip": "以進度條樣式顯示每個CPU的使用率(舊版樣式)",
|
||||
"createFile": "創建文件",
|
||||
"createFolder": "創建文件夾",
|
||||
"cursorType": "光標類型",
|
||||
"customCmd": "自定義命令",
|
||||
"createFile": "創建檔案",
|
||||
"createFolder": "創建資料夾",
|
||||
"cursorType": "游標類型",
|
||||
"customCmd": "自訂命令",
|
||||
"customCmdDocUrl": "https://github.com/lollipopkit/flutter_server_box/wiki/主页#自定义命令",
|
||||
"customCmdHint": "\"命令名稱\": \"命令\"",
|
||||
"dark": "暗",
|
||||
"day": "日",
|
||||
"debug": "調試",
|
||||
"day": "亮",
|
||||
"debug": "除錯",
|
||||
"decode": "解碼",
|
||||
"decompress": "解壓縮",
|
||||
"delete": "刪除",
|
||||
"deleteScripts": "同時刪除服務器腳本",
|
||||
"deleteServers": "批量刪除服務器",
|
||||
"deleteServers": "批量刪除伺服器",
|
||||
"deviceName": "設備名",
|
||||
"dirEmpty": "請確保文件夾為空",
|
||||
"dirEmpty": "請確保資料夾為空",
|
||||
"disabled": "已禁用",
|
||||
"disconnected": "連接斷開",
|
||||
"disk": "硬盤",
|
||||
"diskIgnorePath": "忽略的磁盤路徑",
|
||||
"displayCpuIndex": "顯示CPU索引",
|
||||
"disk": "磁碟",
|
||||
"diskIgnorePath": "忽略的磁碟路徑",
|
||||
"displayCpuIndex": "顯示 CPU 索引",
|
||||
"displayName": "顯示名稱",
|
||||
"dl2Local": "下載 {fileName} 到本地?",
|
||||
"doc": "文檔",
|
||||
@@ -85,8 +82,8 @@
|
||||
"dockerEmptyRunningItems": "沒有正在運行的容器。\n這可能是因為:\n- Docker 安裝使用者與 App 內配置的使用者名稱不同\n- 環境變量 DOCKER_HOST 沒有被正確讀取。你可以通過在終端內運行 `echo $DOCKER_HOST` 來獲取。",
|
||||
"dockerImagesFmt": "共 {count} 個鏡像",
|
||||
"dockerNotInstalled": "Docker 未安裝",
|
||||
"dockerStatusRunningAndStoppedFmt": "{runningCount}個正在運行, {stoppedCount}個已停止",
|
||||
"dockerStatusRunningFmt": "{count}個容器正在運行",
|
||||
"dockerStatusRunningAndStoppedFmt": "{runningCount} 個正在運行, {stoppedCount} 個已停止",
|
||||
"dockerStatusRunningFmt": "{count} 個容器正在運行",
|
||||
"doubleColumnMode": "雙列模式",
|
||||
"doubleColumnTip": "此選項僅開啟功能,實際是否能開啟還取決於設備的寬度",
|
||||
"download": "下載",
|
||||
@@ -98,28 +95,30 @@
|
||||
"error": "錯誤",
|
||||
"exampleName": "名稱範例",
|
||||
"experimentalFeature": "實驗性功能",
|
||||
"export": "導出",
|
||||
"export": "匯出",
|
||||
"extraArgs": "額外參數",
|
||||
"failed": "失敗",
|
||||
"fallbackSshDest": "備選 SSH 目標",
|
||||
"fdroidReleaseTip": "如果你是從 F-Droid 下載的本應用,推薦關閉此選項",
|
||||
"feedback": "反饋",
|
||||
"feedbackOnGithub": "如果你有任何問題,請在GitHub反饋",
|
||||
"feedbackOnGithub": "如果你有任何問題,請在 GitHub 反饋",
|
||||
"fieldMustNotEmpty": "這些輸入框不能為空。",
|
||||
"fileNotExist": "{file} 不存在",
|
||||
"fileTooLarge": "文件 '{file}' 過大 '{size}',超過了 {sizeMax}",
|
||||
"files": "文件",
|
||||
"finished": "已完成",
|
||||
"followSystem": "跟隨系統",
|
||||
"font": "字體",
|
||||
"fontSize": "字體大小",
|
||||
"font": "字型",
|
||||
"fontSize": "字型大小",
|
||||
"forExample": "例如",
|
||||
"force": "強制",
|
||||
"foundNUpdate": "找到 {count} 個更新",
|
||||
"fullScreen": "全屏模式",
|
||||
"fullScreenJitter": "全屏模式抖動",
|
||||
"fullScreen": "全螢幕模式",
|
||||
"fullScreenJitter": "全螢幕模式抖動",
|
||||
"fullScreenJitterHelp": "防止燒屏",
|
||||
"fullScreenTip": "當設備旋轉為橫屏時,是否開啟全屏模式?此選項僅適用於伺服器選項卡。",
|
||||
"getPushTokenFailed": "未能獲取到推送token",
|
||||
"gettingToken": "正在獲取Token...",
|
||||
"fullScreenTip": "當設備旋轉為橫屏時,是否開啟全熒幕模式?此選項僅適用於伺服器選項卡。",
|
||||
"getPushTokenFailed": "未能獲取到推送 token",
|
||||
"gettingToken": "正在獲取 Token...",
|
||||
"goBackQ": "返回?",
|
||||
"goto": "前往",
|
||||
"hideTitleBar": "隱藏標題欄",
|
||||
@@ -129,56 +128,60 @@
|
||||
"host": "主機",
|
||||
"hour": "小時",
|
||||
"httpFailedWithCode": "請求失敗, 狀態碼: {code}",
|
||||
"icloudSynced": "iCloud已同步,某些設置可能需要重啟才能生效。",
|
||||
"icloudSynced": "iCloud 已同步,某些設置可能需要重啟才能生效。",
|
||||
"ignoreCert": "忽略證書",
|
||||
"image": "鏡像",
|
||||
"imagesList": "鏡像列表",
|
||||
"import": "導入",
|
||||
"inAppUpdate": "在App內更新?否則使用瀏覽器下載。",
|
||||
"inner": "內置",
|
||||
"inAppUpdate": "在 App 內更新?否則使用瀏覽器下載。",
|
||||
"init": "初始化",
|
||||
"inner": "內建",
|
||||
"inputDomainHere": "在這裡輸入域名",
|
||||
"install": "安裝",
|
||||
"installDockerWithUrl": "請先 https://docs.docker.com/engine/install docker",
|
||||
"invalid": "無效",
|
||||
"invalidJson": "無效的 JSON",
|
||||
"invalidVersion": "不支持的版本",
|
||||
"invalidVersionHelp": "請確保正確安裝了docker,或者使用的非自編譯版本。如果沒有以上問題,請在 {url} 提交問題。",
|
||||
"invalidVersionHelp": "請確保正確安裝了 docker,或者使用的非自編譯版本。如果沒有以上問題,請在 {url} 提交問題。",
|
||||
"isBusy": "當前正忙",
|
||||
"jumpServer": "跳板服務器",
|
||||
"jumpServer": "跳板伺服器",
|
||||
"keepForeground": "請保持應用處於前台!",
|
||||
"keepStatusWhenErr": "保留上次的伺服器狀態",
|
||||
"keepStatusWhenErrTip": "仅在执行脚本时出错时",
|
||||
"keepStatusWhenErrTip": "僅在執行腳本出錯時",
|
||||
"keyAuth": "密鑰認證",
|
||||
"language": "語言",
|
||||
"languageName": "繁體中文",
|
||||
"lastTry": "最後嘗試",
|
||||
"launchPage": "啓動頁",
|
||||
"license": "開源證書",
|
||||
"letterCache": "输入法字符緩存",
|
||||
"letterCacheTip": "推薦開啟,但是開啟後無法輸入CJK(中文、日文、韓文)等文字",
|
||||
"license": "開源許可證",
|
||||
"light": "亮",
|
||||
"loadingFiles": "正在加載目錄。。。",
|
||||
"loadingFiles": "正在加載目錄...",
|
||||
"location": "位置",
|
||||
"log": "日誌",
|
||||
"loss": "丟包率",
|
||||
"madeWithLove": "用❤️製作 by {myGithub}",
|
||||
"manual": "手動",
|
||||
"max": "最大",
|
||||
"maxRetryCount": "服務器嘗試重連次數",
|
||||
"maxRetryCount": "伺服器嘗試重連次數",
|
||||
"maxRetryCountEqual0": "會無限重試",
|
||||
"min": "最小",
|
||||
"minute": "分鐘",
|
||||
"mission": "任務",
|
||||
"more": "更多",
|
||||
"moveOutServerFuncBtnsHelp": "開啟:可以在服務器 Tab 頁的每個卡片下方顯示。關閉:在服務器詳情頁頂部顯示。",
|
||||
"moveOutServerFuncBtnsHelp": "開啟:可以在伺服器 Tab 頁的每個卡片下方顯示。關閉:在伺服器詳情頁頂部顯示。",
|
||||
"ms": "毫秒",
|
||||
"name": "名稱",
|
||||
"needHomeDir": "如果你是群暉用戶,[看這裡](https://kb.synology.com/DSM/tutorial/user_enable_home_service)。其他系統用戶,需搜索如何創建家目錄(home directory)。",
|
||||
"needRestart": "需要重啓 App",
|
||||
"net": "網絡",
|
||||
"netViewType": "網絡視圖類型",
|
||||
"net": "網路",
|
||||
"netViewType": "網路視圖類型",
|
||||
"newContainer": "新建容器",
|
||||
"noClient": "沒有SSH連接",
|
||||
"noInterface": "沒有可用的接口",
|
||||
"noClient": "沒有 SSH 連接",
|
||||
"noInterface": "沒有可用的介面",
|
||||
"noLineChart": "不使用折線圖",
|
||||
"noLineChartForCpu": "CPU 不使用折線圖",
|
||||
"noNotiPerm": "無通知權限,可能在下載應用程式更新時沒有進度提示。",
|
||||
"noOptions": "無可選項",
|
||||
"noPrivateKeyTip": "私鑰不存在,可能已被刪除/配置錯誤。",
|
||||
@@ -186,57 +189,59 @@
|
||||
"noResult": "無結果",
|
||||
"noSavedPrivateKey": "沒有已保存的私鑰。",
|
||||
"noSavedSnippet": "沒有已保存的程式片段。",
|
||||
"noServerAvailable": "沒有可用的服務器。",
|
||||
"noServerAvailable": "沒有可用的伺服器。",
|
||||
"noTask": "沒有任務",
|
||||
"noUpdateAvailable": "沒有可用更新",
|
||||
"node": "節點",
|
||||
"notAvailable": "不可用",
|
||||
"notSelected": "未選擇",
|
||||
"note": "備註",
|
||||
"nullToken": "無Token",
|
||||
"nullToken": "無 Token",
|
||||
"ok": "好",
|
||||
"onServerDetailPage": "在服務器詳情頁",
|
||||
"onServerDetailPage": "在伺服器詳情頁",
|
||||
"onlyOneLine": "僅顯示為一行(可滾動)",
|
||||
"onlyWhenCoreBiggerThan8": "僅當核心數>8時生效",
|
||||
"onlyWhenCoreBiggerThan8": "僅當核心數大於 8 時生效",
|
||||
"open": "打開",
|
||||
"openLastPath": "打開上次的路徑",
|
||||
"openLastPathTip": "不同的服務器會有不同的記錄,且記錄的是退出時的路徑",
|
||||
"openLastPathTip": "不同的伺服器會有不同的記錄,且記錄的是退出時的路徑",
|
||||
"parseContainerStats": "解析容器佔用狀態",
|
||||
"parseContainerStatsTip": "Docker解析佔用狀態較為緩慢",
|
||||
"parseContainerStatsTip": "Docker 解析佔用狀態較為緩慢",
|
||||
"paste": "貼上",
|
||||
"path": "路徑",
|
||||
"percentOfSize": "{size} 的 {percent}%",
|
||||
"pickFile": "選擇文件",
|
||||
"permission": "權限",
|
||||
"pickFile": "選擇檔案",
|
||||
"pingAvg": "平均:",
|
||||
"pingInputIP": "請輸入目標IP或域名",
|
||||
"pingNoServer": "沒有服務器可用於Ping\n請在服務器tab新增服務器後再試",
|
||||
"pingInputIP": "請輸入目標 IP 或域名",
|
||||
"pingNoServer": "沒有伺服器可用於 Ping\n請在伺服器 Tab 新增伺服器後再試",
|
||||
"pkg": "包管理",
|
||||
"pkgUpgradeTip": "請在更新前備份系統。",
|
||||
"platformNotSupportUpdate": "當前平台不支持更新,請編譯最新源碼後手動安裝",
|
||||
"platformNotSupportUpdate": "當前平台不支持更新,請編譯最新原始碼後手動安裝",
|
||||
"plugInType": "插入類型",
|
||||
"plzEnterHost": "請輸入主機",
|
||||
"plzSelectKey": "請選擇私鑰",
|
||||
"port": "端口",
|
||||
"port": "埠",
|
||||
"preview": "預覽",
|
||||
"primaryColorSeed": "主要色調種子",
|
||||
"privateKey": "私鑰",
|
||||
"process": "進程",
|
||||
"process": "行程",
|
||||
"pushToken": "消息推送 Token",
|
||||
"pveIgnoreCertTip": "不建議啟用,請注意安全風險!如果您使用的是 PVE 的默認證書,則需要啟用此選項。",
|
||||
"pveLoginFailed": "登錄失敗。無法使用伺服器配置中的使用者名稱/密碼以Linux PAM方式登錄。",
|
||||
"pveVersionLow": "此功能目前處於測試階段,僅在PVE 8+上進行過測試。請謹慎使用。",
|
||||
"pveLoginFailed": "登錄失敗。無法使用伺服器配置中的使用者名稱/密碼以 Linux PAM 方式登錄。",
|
||||
"pveVersionLow": "此功能目前處於測試階段,僅在 PVE 8+ 上進行過測試。請謹慎使用。",
|
||||
"pwd": "密碼",
|
||||
"read": "读",
|
||||
"reboot": "重启",
|
||||
"rememberChoice": "記住選擇",
|
||||
"rememberPwdInMem": "在記憶體中記住密碼",
|
||||
"rememberPwdInMemTip": "用於容器、暫停等",
|
||||
"rememberWindowSize": "記住窗口大小",
|
||||
"remotePath": "遠端路徑",
|
||||
"rename": "重命名",
|
||||
"reportBugsOnGithubIssue": "請到 {url} 提交問題",
|
||||
"restart": "重啓",
|
||||
"restore": "恢復",
|
||||
"restoreSuccess": "恢復成功,需要重啓App來應用更改",
|
||||
"restoreSuccess": "恢復成功,需要重啓 App 來應用更改",
|
||||
"result": "結果",
|
||||
"rotateAngel": "旋轉角度",
|
||||
"route": "路由",
|
||||
@@ -245,31 +250,31 @@
|
||||
"save": "保存",
|
||||
"saved": "已保存",
|
||||
"second": "秒",
|
||||
"sensors": "传感器",
|
||||
"sensors": "感測器",
|
||||
"sequence": "順序",
|
||||
"server": "服務器",
|
||||
"server": "伺服器",
|
||||
"serverDetailOrder": "詳情頁部件順序",
|
||||
"serverFuncBtns": "服務器功能按鈕",
|
||||
"serverOrder": "服務器順序",
|
||||
"serverFuncBtns": "伺服器功能按鈕",
|
||||
"serverOrder": "伺服器順序",
|
||||
"serverTabConnecting": "連接中...",
|
||||
"serverTabEmpty": "現在沒有服務器。\n點擊右下方按鈕來新增。",
|
||||
"serverTabEmpty": "現在沒有伺服器。\n點擊右下方按鈕來新增。",
|
||||
"serverTabFailed": "失敗",
|
||||
"serverTabLoading": "加載中...",
|
||||
"serverTabPlzSave": "請再次保存該私鑰",
|
||||
"serverTabUnkown": "未知狀態",
|
||||
"setting": "設置",
|
||||
"sftpDlPrepare": "準備連接至服務器...",
|
||||
"sftpDlPrepare": "準備連接至伺服器...",
|
||||
"sftpRmrDirSummary": "在 SFTP 中使用 `rm -r` 來刪除文件夾",
|
||||
"sftpSSHConnected": "SFTP 已連接...",
|
||||
"sftpShowFoldersFirst": "文件夾顯示在前",
|
||||
"sftpShowFoldersFirst": "資料夾顯示在前",
|
||||
"showDistLogo": "顯示發行版 Logo",
|
||||
"shutdown": "关机",
|
||||
"shutdown": "關機",
|
||||
"size": "大小",
|
||||
"snippet": "程式片段",
|
||||
"softWrap": "軟換行",
|
||||
"speed": "速度",
|
||||
"spentTime": "耗時: {time}",
|
||||
"sshTermHelp": "在終端可滾動時,橫向拖動可以選中文字。點擊鍵盤按鈕可以開啟/關閉鍵盤。文件圖標會打開當前路徑SFTP。剪貼板按鈕會在有選中文字時複製內容,在未選中並且剪貼板有內容時貼上內容到終端。代碼圖標會貼上代碼片段到終端並執行。",
|
||||
"sshTermHelp": "在終端可滾動時,橫向拖動可以選中文字。點擊鍵盤按鈕可以開啟/關閉鍵盤。文件圖標會打開當前路徑 SFTP。剪貼簿按鈕會在有選中文字時複製內容,在未選中並且剪貼簿有內容時貼上內容到終端。代碼圖標會貼上代碼片段到終端並執行。",
|
||||
"sshTip": "該功能目前處於測試階段。\n\n請在 {url} 反饋問題,或者加入我們開發。",
|
||||
"sshVirtualKeyAutoOff": "虛擬按鍵自動切換",
|
||||
"start": "開始",
|
||||
@@ -287,53 +292,53 @@
|
||||
"system": "系統",
|
||||
"tag": "标签",
|
||||
"temperature": "溫度",
|
||||
"termFontSizeTip": "此設置將影響終端大小(寬度和高度)。您可以在終端頁面縮放,來調整當前會話的字體大小。",
|
||||
"termFontSizeTip": "此設置將影響終端大小(寬度和高度)。您可以在終端頁面縮放,來調整當前會話的字型大小。",
|
||||
"terminal": "终端機",
|
||||
"test": "測試",
|
||||
"textScaler": "字體縮放",
|
||||
"textScalerTip": "1.0 => 100%(原大小),僅作用於伺服器頁面部分字體,不建議修改。",
|
||||
"textScaler": "字型縮放",
|
||||
"textScalerTip": "1.0 => 100%(原大小),僅作用於伺服器頁面部分字型,不建議修改。",
|
||||
"theme": "主題",
|
||||
"themeMode": "主題模式",
|
||||
"time": "時間",
|
||||
"times": "次",
|
||||
"total": "總共",
|
||||
"traffic": "流量",
|
||||
"trySudo": "嘗試使用sudo",
|
||||
"ttl": "緩存時間",
|
||||
"trySudo": "嘗試使用 sudo",
|
||||
"ttl": "TTL",
|
||||
"unknown": "未知",
|
||||
"unknownError": "未知錯誤",
|
||||
"unkownConvertMode": "未知轉換模式",
|
||||
"update": "更新",
|
||||
"updateAll": "更新全部",
|
||||
"updateIntervalEqual0": "你設置為0,服務器狀態不會自動更新。\n且不能計算CPU使用情況。",
|
||||
"updateServerStatusInterval": "服務器狀態更新間隔",
|
||||
"updateIntervalEqual0": "你設置為 0,伺服器狀態不會自動更新。\n且不能計算CPU使用情況。",
|
||||
"updateServerStatusInterval": "伺服器狀態更新間隔",
|
||||
"updateTip": "新版本: v1.0.{newest}",
|
||||
"updateTipTooLow": "當前版本過低,請升級至 v1.0.{newest}",
|
||||
"upload": "上傳",
|
||||
"upsideDown": "上下交換",
|
||||
"uptime": "啟動時長",
|
||||
"urlOrJson": "鏈接或JSON",
|
||||
"useCdn": "使用CDN",
|
||||
"useCdnTip": "非中國大陆用戶建議使用CDN,是否使用?",
|
||||
"urlOrJson": "鏈接或 JSON",
|
||||
"useCdn": "使用 CDN",
|
||||
"useCdnTip": "非中國大陸用戶建議使用 CDN,是否使用?",
|
||||
"useNoPwd": "将使用無密碼",
|
||||
"usePodmanByDefault": "默認使用 Podman",
|
||||
"used": "已用",
|
||||
"user": "用戶",
|
||||
"user": "使用者",
|
||||
"versionHaveUpdate": "找到新版本:v1.0.{build}, 點擊更新",
|
||||
"versionUnknownUpdate": "當前:v1.0.{build},點擊檢查更新",
|
||||
"versionUpdated": "當前:v1.0.{build}, 已是最新版本",
|
||||
"view": "視圖",
|
||||
"viewErr": "查看錯誤",
|
||||
"virtKeyHelpClipboard": "如果終端有選中字符,則復製選中字符至剪切板,否則粘貼剪切板內容至終端。",
|
||||
"virtKeyHelpClipboard": "如果終端有選中字元,則復製選中字元至剪貼簿,否則粘貼剪貼簿內容至終端。",
|
||||
"virtKeyHelpIME": "打開/關閉鍵盤",
|
||||
"virtKeyHelpSFTP": "在 SFTP 中打開當前路徑。",
|
||||
"waitConnection": "請等待連接建立",
|
||||
"wakeLock": "保持喚醒",
|
||||
"watchNotPaired": "沒有已配對的 Apple Watch",
|
||||
"webdavSettingEmpty": "Webdav 設置項爲空",
|
||||
"webdavSettingEmpty": "WebDav 設置項爲空",
|
||||
"whenOpenApp": "當打開 App 時",
|
||||
"willTakEeffectImmediately": "更改將會立即生效",
|
||||
"wolTip": "在配置WOL(網絡喚醒)後,每次連接伺服器都會先發送一次WOL請求。",
|
||||
"wolTip": "在配置 WOL(網絡喚醒)後,每次連接伺服器都會先發送一次 WOL 請求。",
|
||||
"write": "写",
|
||||
"writeScriptFailTip": "寫入腳本失敗,可能是沒有權限/目錄不存在等。"
|
||||
}
|
||||
@@ -68,7 +68,14 @@ Future<void> _initApp() async {
|
||||
await _initData();
|
||||
_setupDebug();
|
||||
|
||||
SystemUIs.initDesktopWindow(Stores.setting.hideTitleBar.fetch());
|
||||
final windowSize = Stores.setting.windowSize;
|
||||
final hideTitleBar = Stores.setting.hideTitleBar.fetch();
|
||||
await SystemUIs.initDesktopWindow(
|
||||
hideTitleBar: hideTitleBar,
|
||||
size: windowSize.fetch().toSize(),
|
||||
listener: WindowSizeListener(windowSize),
|
||||
);
|
||||
|
||||
FontUtils.loadFrom(Stores.setting.fontPath.fetch());
|
||||
|
||||
_doPlatformRelated();
|
||||
|
||||
@@ -66,18 +66,7 @@ class BackupPage extends StatelessWidget {
|
||||
trailing: const Icon(Icons.save),
|
||||
onTap: () async {
|
||||
final path = await Backup.backup();
|
||||
debugPrint("Backup path: $path");
|
||||
|
||||
/// Issue #188
|
||||
switch (Pfs.type) {
|
||||
case Pfs.windows:
|
||||
final backslashPath = path.replaceAll('/', '\\');
|
||||
await Process.run('explorer', ['/select,$backslashPath']);
|
||||
case Pfs.linux:
|
||||
await Process.run('xdg-open', [path]);
|
||||
default:
|
||||
await Pfs.sharePath(path);
|
||||
}
|
||||
await Pfs.share(path: path);
|
||||
},
|
||||
),
|
||||
ListTile(
|
||||
|
||||
@@ -14,6 +14,8 @@ final class _AppBar extends CustomAppBar {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
if (isDesktop) return super.build(context);
|
||||
|
||||
final placeholder = SizedBox(
|
||||
height: CustomAppBar.barHeight ?? 0 + MediaQuery.of(context).padding.top,
|
||||
);
|
||||
@@ -25,7 +27,7 @@ final class _AppBar extends CustomAppBar {
|
||||
return ValBuilder(
|
||||
listenable: selectIndex,
|
||||
builder: (idx) {
|
||||
if (idx == AppTab.ssh.index && !isWindows && !isLinux) {
|
||||
if (idx == AppTab.ssh.index) {
|
||||
return placeholder;
|
||||
}
|
||||
return super.build(context);
|
||||
|
||||
@@ -1,9 +1,7 @@
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
import 'package:server_box/core/channel/home_widget.dart';
|
||||
import 'package:server_box/core/extension/build.dart';
|
||||
@@ -60,9 +58,6 @@ class _HomePageState extends State<HomePage>
|
||||
@override
|
||||
void didChangeDependencies() {
|
||||
super.didChangeDependencies();
|
||||
context.setLibL10n();
|
||||
final appL10n = AppLocalizations.of(context);
|
||||
if (appL10n != null) l10n = appL10n;
|
||||
_isLandscape.value =
|
||||
MediaQuery.of(context).orientation == Orientation.landscape;
|
||||
}
|
||||
@@ -224,17 +219,10 @@ class _HomePageState extends State<HomePage>
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
_buildIcon(),
|
||||
TextButton(
|
||||
onPressed: () => context.showRoundDialog(
|
||||
title: BuildDataX.versionStr,
|
||||
child: const Text(
|
||||
'${BuildData.buildAt}\nFlutter ${BuildData.engine}'),
|
||||
),
|
||||
child: const Text(
|
||||
'${BuildData.name}\n${BuildDataX.versionStr}',
|
||||
textAlign: TextAlign.center,
|
||||
style: UIs.text15,
|
||||
),
|
||||
const Text(
|
||||
'${BuildData.name}\n${BuildDataX.versionStr}',
|
||||
textAlign: TextAlign.center,
|
||||
style: UIs.text15,
|
||||
),
|
||||
const SizedBox(height: 37),
|
||||
_buildTiles(),
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import 'dart:io';
|
||||
import 'dart:async';
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
|
||||
@@ -82,6 +82,7 @@ class _ServerDetailPageState extends State<ServerDetailPage>
|
||||
final s = widget.spi.server;
|
||||
if (s == null) {
|
||||
return Scaffold(
|
||||
appBar: const CustomAppBar(),
|
||||
body: Center(
|
||||
child: Text(l10n.noClient),
|
||||
),
|
||||
|
||||
@@ -5,12 +5,9 @@ import 'package:flutter/material.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
import 'package:server_box/core/extension/context/locale.dart';
|
||||
import 'package:server_box/data/model/app/shell_func.dart';
|
||||
import 'package:server_box/data/model/server/custom.dart';
|
||||
import 'package:server_box/data/model/server/wol_cfg.dart';
|
||||
import 'package:server_box/data/res/provider.dart';
|
||||
import 'package:server_box/data/res/store.dart';
|
||||
import 'package:server_box/data/res/url.dart';
|
||||
|
||||
import '../../../core/route.dart';
|
||||
import '../../../data/model/server/server_private_info.dart';
|
||||
@@ -152,44 +149,17 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
Widget _buildDelBtn() {
|
||||
return IconButton(
|
||||
onPressed: () {
|
||||
var delScripts = false;
|
||||
context.showRoundDialog(
|
||||
title: l10n.attention,
|
||||
child: StatefulBuilder(builder: (ctx, setState) {
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Text(l10n.askContinue(
|
||||
'${l10n.delete} ${l10n.server}(${widget.spi!.name})',
|
||||
)),
|
||||
UIs.height13,
|
||||
if (widget.spi?.server?.canViewDetails ?? false)
|
||||
CheckboxListTile(
|
||||
value: delScripts,
|
||||
onChanged: (_) => setState(
|
||||
() => delScripts = !delScripts,
|
||||
),
|
||||
controlAffinity: ListTileControlAffinity.leading,
|
||||
title: Text(l10n.deleteScripts),
|
||||
tileColor: Colors.transparent,
|
||||
contentPadding: EdgeInsets.zero,
|
||||
)
|
||||
],
|
||||
);
|
||||
return Text(l10n.askContinue(
|
||||
'${l10n.delete} ${l10n.server}(${widget.spi!.name})',
|
||||
));
|
||||
}),
|
||||
actions: [
|
||||
TextButton(
|
||||
onPressed: () async {
|
||||
context.pop();
|
||||
if (delScripts) {
|
||||
await context.showLoadingDialog(
|
||||
fn: () async {
|
||||
const cmd = 'rm ${ShellFunc.srvBoxDir}/mobile_v*.sh';
|
||||
return widget.spi?.server?.client?.run(cmd);
|
||||
},
|
||||
);
|
||||
}
|
||||
Pros.server.delServer(widget.spi!.id);
|
||||
context.pop(true);
|
||||
},
|
||||
@@ -248,7 +218,7 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
controller: _altUrlController,
|
||||
type: TextInputType.url,
|
||||
node: _alterUrlFocus,
|
||||
label: l10n.alterUrl,
|
||||
label: l10n.fallbackSshDest,
|
||||
icon: MingCute.link_line,
|
||||
hint: 'user@ip:port',
|
||||
),
|
||||
@@ -381,7 +351,7 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
controller: _logoUrlCtrl,
|
||||
type: TextInputType.url,
|
||||
icon: Icons.image,
|
||||
label: 'Url',
|
||||
label: 'URL',
|
||||
hint: 'https://example.com/logo.png',
|
||||
),
|
||||
UIs.height7,
|
||||
@@ -423,7 +393,7 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
type: TextInputType.url,
|
||||
icon: MingCute.web_line,
|
||||
node: node,
|
||||
label: l10n.addr,
|
||||
label: 'URL',
|
||||
hint: addr,
|
||||
),
|
||||
),
|
||||
@@ -486,7 +456,7 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
Input(
|
||||
controller: _wolMacCtrl,
|
||||
type: TextInputType.text,
|
||||
label: 'Mac ${l10n.addr}',
|
||||
label: 'MAC ${l10n.addr}',
|
||||
icon: Icons.computer,
|
||||
hint: '00:11:22:33:44:55',
|
||||
),
|
||||
@@ -649,16 +619,16 @@ class _ServerEditPageState extends State<ServerEditPage> {
|
||||
wolCfg: wol,
|
||||
);
|
||||
|
||||
final tipShown = Stores.history.writeScriptTipShown;
|
||||
if (!tipShown.fetch()) {
|
||||
final ok = await context.showRoundDialog(
|
||||
title: l10n.attention,
|
||||
child: SimpleMarkdown(data: l10n.beforeConnect(Urls.thisRepo)),
|
||||
actions: Btns.oks(onTap: () => context.pop(true)),
|
||||
);
|
||||
if (ok != true) return;
|
||||
tipShown.put(true);
|
||||
}
|
||||
// final tipShown = Stores.history.writeScriptTipShown;
|
||||
// if (!tipShown.fetch()) {
|
||||
// final ok = await context.showRoundDialog(
|
||||
// title: l10n.attention,
|
||||
// child: SimpleMarkdown(data: l10n.beforeConnect(Urls.thisRepo)),
|
||||
// actions: Btns.oks(onTap: () => context.pop(true)),
|
||||
// );
|
||||
// if (ok != true) return;
|
||||
// tipShown.put(true);
|
||||
// }
|
||||
|
||||
if (widget.spi == null) {
|
||||
Pros.server.addServer(spi);
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import 'dart:async';
|
||||
import 'dart:math' as math;
|
||||
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
|
||||
@@ -5,16 +5,14 @@ import 'package:flutter/material.dart';
|
||||
import 'package:flutter_highlight/theme_map.dart';
|
||||
import 'package:flutter_gen/gen_l10n/l10n.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
import 'package:server_box/core/extension/context/locale.dart';
|
||||
import 'package:server_box/data/res/provider.dart';
|
||||
import 'package:server_box/data/res/rebuild.dart';
|
||||
import 'package:server_box/data/res/store.dart';
|
||||
import 'package:server_box/data/res/url.dart';
|
||||
import 'package:server_box/view/page/setting/platform/platform_pub.dart';
|
||||
|
||||
import '../../../core/route.dart';
|
||||
import '../../../data/model/app/net_view.dart';
|
||||
import '../../../data/provider/app.dart';
|
||||
import '../../../data/res/build_data.dart';
|
||||
|
||||
const _kIconSize = 23.0;
|
||||
@@ -156,6 +154,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
Widget _buildSSH() {
|
||||
return Column(
|
||||
children: [
|
||||
_buildLetterCache(),
|
||||
_buildSSHWakeLock(),
|
||||
_buildTermTheme(),
|
||||
_buildFont(),
|
||||
@@ -183,12 +182,13 @@ class _SettingPageState extends State<SettingPage> {
|
||||
return ListTile(
|
||||
leading: const Icon(Icons.update),
|
||||
title: Text(l10n.autoCheckUpdate),
|
||||
subtitle: Consumer<AppProvider>(
|
||||
builder: (ctx, app, __) {
|
||||
subtitle: ValBuilder(
|
||||
listenable: AppUpdateIface.newestBuild,
|
||||
builder: (val) {
|
||||
String display;
|
||||
if (app.newestBuild != null) {
|
||||
if (app.newestBuild! > BuildData.build) {
|
||||
display = l10n.versionHaveUpdate(app.newestBuild!);
|
||||
if (val != null) {
|
||||
if (val > BuildData.build) {
|
||||
display = l10n.versionHaveUpdate(val);
|
||||
} else {
|
||||
display = l10n.versionUpdated(BuildData.build);
|
||||
}
|
||||
@@ -305,7 +305,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
_setting.primaryColor.put(color.value);
|
||||
context.pop();
|
||||
context.pop();
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
}
|
||||
|
||||
// Widget _buildLaunchPage() {
|
||||
@@ -393,7 +393,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
);
|
||||
if (selected != null) {
|
||||
_setting.themeMode.put(selected);
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
}
|
||||
},
|
||||
trailing: ValBuilder(
|
||||
@@ -442,7 +442,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
onPressed: () {
|
||||
_setting.fontPath.delete();
|
||||
context.pop();
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
},
|
||||
child: Text(l10n.clear),
|
||||
)
|
||||
@@ -466,7 +466,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
}
|
||||
|
||||
context.pop();
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
}
|
||||
|
||||
Widget _buildTermFontSize() {
|
||||
@@ -536,7 +536,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
if (selected != null) {
|
||||
_setting.locale.put(selected.code);
|
||||
context.pop();
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
}
|
||||
},
|
||||
trailing: ListenBuilder(
|
||||
@@ -609,7 +609,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
subtitle: Text(l10n.fullScreenTip, style: UIs.textGrey),
|
||||
trailing: StoreSwitch(
|
||||
prop: _setting.fullScreen,
|
||||
callback: (_) => RNodes.app.build(),
|
||||
callback: (_) => RNodes.app.notify(),
|
||||
),
|
||||
);
|
||||
}
|
||||
@@ -736,47 +736,29 @@ class _SettingPageState extends State<SettingPage> {
|
||||
leading: const Icon(Icons.delete_forever),
|
||||
trailing: const Icon(Icons.keyboard_arrow_right),
|
||||
onTap: () async {
|
||||
context.showRoundDialog<List<String>>(
|
||||
title: l10n.choose,
|
||||
child: SingleChildScrollView(
|
||||
child: StatefulBuilder(builder: (ctx, setState) {
|
||||
final keys = Stores.server.box.keys.toList();
|
||||
keys.removeWhere((element) => element == BoxX.lastModifiedKey);
|
||||
final all = keys.map(
|
||||
(e) {
|
||||
final name = Pros.server.pick(id: e)?.spi.name;
|
||||
return ListTile(
|
||||
title: Text(name ?? e),
|
||||
subtitle: name != null ? Text(e) : null,
|
||||
onTap: () => context.showRoundDialog(
|
||||
title: l10n.attention,
|
||||
child: Text(l10n.askContinue(
|
||||
'${l10n.delete} ${l10n.server}($e)',
|
||||
)),
|
||||
actions: [
|
||||
TextButton(
|
||||
onPressed: () {
|
||||
Pros.server.delServer(e);
|
||||
ctx.pop();
|
||||
setState(() {});
|
||||
},
|
||||
child: Text(l10n.ok),
|
||||
)
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
return ConstrainedBox(
|
||||
constraints: const BoxConstraints(maxHeight: 377),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: all.toList(),
|
||||
),
|
||||
);
|
||||
}),
|
||||
),
|
||||
final keys = Stores.server.box.keys.toList();
|
||||
keys.removeWhere((element) => element == BoxX.lastModifiedKey);
|
||||
final strKeys = List<String>.empty(growable: true);
|
||||
for (final key in keys) {
|
||||
if (key is String) strKeys.add(key);
|
||||
}
|
||||
final deleteKeys = await context.showPickDialog<String>(
|
||||
clearable: true,
|
||||
items: strKeys,
|
||||
);
|
||||
if (deleteKeys == null) return;
|
||||
|
||||
final md = deleteKeys.map((e) => '- $e').join('\n');
|
||||
final sure = await context.showRoundDialog(
|
||||
title: l10n.attention,
|
||||
child: SimpleMarkdown(data: md),
|
||||
);
|
||||
|
||||
if (sure != true) return;
|
||||
for (final key in deleteKeys) {
|
||||
Stores.server.box.delete(key);
|
||||
}
|
||||
context.showSnackBar(l10n.success);
|
||||
},
|
||||
);
|
||||
}
|
||||
@@ -820,7 +802,7 @@ class _SettingPageState extends State<SettingPage> {
|
||||
return;
|
||||
}
|
||||
_setting.textFactor.put(val);
|
||||
RNodes.app.build();
|
||||
RNodes.app.notify();
|
||||
context.pop();
|
||||
}
|
||||
|
||||
@@ -1067,10 +1049,11 @@ class _SettingPageState extends State<SettingPage> {
|
||||
title: Text(l10n.more),
|
||||
children: [
|
||||
_buildBeta(),
|
||||
_buildWakeLock(),
|
||||
if (isMobile) _buildWakeLock(),
|
||||
_buildCollapseUI(),
|
||||
_buildCupertinoRoute(),
|
||||
if (isDesktop) _buildHideTitleBar(),
|
||||
if (isDesktop) PlatformPublicSettings.buildSaveWindowSize(),
|
||||
],
|
||||
);
|
||||
}
|
||||
@@ -1152,13 +1135,13 @@ class _SettingPageState extends State<SettingPage> {
|
||||
|
||||
return ListTile(
|
||||
leading: const Icon(Icons.image),
|
||||
title: Text('Logo ${l10n.addr}'),
|
||||
title: const Text('Logo URL'),
|
||||
trailing: const Icon(Icons.keyboard_arrow_right),
|
||||
onTap: () {
|
||||
final ctrl =
|
||||
TextEditingController(text: _setting.serverLogoUrl.fetch());
|
||||
context.showRoundDialog(
|
||||
title: 'Logo ${l10n.addr}',
|
||||
title: 'Logo URL',
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
@@ -1195,4 +1178,16 @@ class _SettingPageState extends State<SettingPage> {
|
||||
trailing: StoreSwitch(prop: _setting.betaTest),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildLetterCache() {
|
||||
return ListTile(
|
||||
leading: const Icon(Bootstrap.input_cursor),
|
||||
title: Text(l10n.letterCache),
|
||||
subtitle: Text(
|
||||
'${l10n.letterCacheTip}\n${l10n.needRestart}',
|
||||
style: UIs.textGrey,
|
||||
),
|
||||
trailing: StoreSwitch(prop: _setting.letterCache),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -82,9 +82,7 @@ class _IOSSettingsPageState extends State<IOSSettingsPage> {
|
||||
Widget _buildWatchApp() {
|
||||
return FutureWidget(
|
||||
future: () async {
|
||||
if (!await wc.isPaired) {
|
||||
return null;
|
||||
}
|
||||
if (!await wc.isPaired) return null;
|
||||
return await wc.applicationContext;
|
||||
}(),
|
||||
loading: UIs.centerLoading,
|
||||
@@ -114,16 +112,15 @@ class _IOSSettingsPageState extends State<IOSSettingsPage> {
|
||||
void _onTapWatchApp(Map<String, dynamic> map) async {
|
||||
final urls = Map<String, String>.from(map['urls'] as Map? ?? {});
|
||||
final result = await AppRoutes.kvEditor(data: urls).go(context);
|
||||
if (result == null || result! is Map<String, String>) return;
|
||||
if (result == null || result is! Map<String, String>) return;
|
||||
|
||||
try {
|
||||
await wc.updateApplicationContext({'urls': result});
|
||||
} catch (e, trace) {
|
||||
context.showRoundDialog(
|
||||
title: l10n.error,
|
||||
child: Text('${l10n.save}:\n$e'),
|
||||
);
|
||||
Loggers.app.warning('Update watch config failed', e, trace);
|
||||
await context.showLoadingDialog(fn: () async {
|
||||
await wc.updateApplicationContext({'urls': result});
|
||||
});
|
||||
} catch (e, s) {
|
||||
context.showErrDialog(e: e, s: s, operation: 'Watch Context');
|
||||
Loggers.app.warning('Update watch config failed', e, s);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2,6 +2,7 @@ import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:server_box/core/extension/context/locale.dart';
|
||||
import 'package:server_box/data/res/store.dart';
|
||||
import 'package:window_manager/window_manager.dart';
|
||||
|
||||
abstract final class PlatformPublicSettings {
|
||||
static Widget buildBioAuth() {
|
||||
@@ -45,4 +46,49 @@ abstract final class PlatformPublicSettings {
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
static Widget buildSaveWindowSize() {
|
||||
final isBusy = false.vn;
|
||||
// Only show [FadeIn] when previous state is busy.
|
||||
var lastIsBusy = false;
|
||||
final prop = Stores.setting.windowSize;
|
||||
|
||||
return ListTile(
|
||||
title: Text(l10n.rememberWindowSize),
|
||||
|
||||
/// Copied from `fl_build/view/store_switch`
|
||||
trailing: ValBuilder(
|
||||
listenable: isBusy,
|
||||
builder: (busy) {
|
||||
return ValBuilder(
|
||||
listenable: prop.listenable(),
|
||||
builder: (value) {
|
||||
if (busy) {
|
||||
lastIsBusy = true;
|
||||
return UIs.centerSizedLoadingSmall.paddingOnly(right: 17);
|
||||
}
|
||||
|
||||
final switcher = Switch(
|
||||
value: value.isNotEmpty,
|
||||
onChanged: (value) async {
|
||||
isBusy.value = true;
|
||||
final size = await windowManager.getSize();
|
||||
isBusy.value = false;
|
||||
prop.put(size.toIntStr());
|
||||
},
|
||||
);
|
||||
|
||||
if (lastIsBusy) {
|
||||
final ret = FadeIn(child: switcher);
|
||||
lastIsBusy = false;
|
||||
return ret;
|
||||
}
|
||||
|
||||
return switcher;
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_markdown/flutter_markdown.dart';
|
||||
@@ -173,6 +172,7 @@ class _SnippetEditPageState extends State<SnippetEditPage>
|
||||
: Text(
|
||||
subtitle,
|
||||
maxLines: 1,
|
||||
style: UIs.textGrey,
|
||||
overflow: TextOverflow.ellipsis,
|
||||
),
|
||||
onTap: () async {
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import 'dart:async';
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:dartssh2/dartssh2.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
@@ -130,6 +129,7 @@ class SSHPageState extends State<SSHPage>
|
||||
}
|
||||
|
||||
Widget _buildBody() {
|
||||
final letterCache = Stores.setting.letterCache.fetch();
|
||||
return SizedBox(
|
||||
height: _media.size.height -
|
||||
_virtKeysHeight -
|
||||
@@ -145,8 +145,9 @@ class SSHPageState extends State<SSHPage>
|
||||
_terminal,
|
||||
key: _termKey,
|
||||
controller: _terminalController,
|
||||
keyboardType: TextInputType.text,
|
||||
enableSuggestions: true,
|
||||
keyboardType:
|
||||
letterCache ? TextInputType.text : TextInputType.visiblePassword,
|
||||
enableSuggestions: !letterCache,
|
||||
textStyle: _terminalStyle,
|
||||
theme: _terminalTheme,
|
||||
deleteDetection: isMobile,
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
import 'package:provider/provider.dart';
|
||||
@@ -89,7 +90,7 @@ class _SSHTabPageState extends State<SSHTabPage>
|
||||
if (confirm != true) return;
|
||||
|
||||
_tabMap.remove(name);
|
||||
_tabRN.build();
|
||||
_tabRN.notify();
|
||||
_pageCtrl.previousPage(
|
||||
duration: Durations.medium1, curve: Curves.fastEaseInToSlowEaseOut);
|
||||
}
|
||||
@@ -108,16 +109,27 @@ class _SSHTabPageState extends State<SSHTabPage>
|
||||
}
|
||||
return GridView.builder(
|
||||
padding: const EdgeInsets.all(7),
|
||||
itemBuilder: (_, idx) {
|
||||
itemBuilder: (context, idx) {
|
||||
final spi = Pros.server.pick(id: pro.serverOrder[idx])?.spi;
|
||||
if (spi == null) return UIs.placeholder;
|
||||
return CardX(
|
||||
child: ListTile(
|
||||
contentPadding: const EdgeInsets.only(left: 17, right: 7),
|
||||
title: Text(spi.name),
|
||||
trailing: const Icon(Icons.chevron_right),
|
||||
child: InkWell(
|
||||
onTap: () => _onTapInitCard(spi),
|
||||
).center(),
|
||||
child: Container(
|
||||
alignment: Alignment.centerLeft,
|
||||
padding: const EdgeInsets.only(left: 17, right: 7),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Text(
|
||||
spi.name,
|
||||
style: Theme.of(context).textTheme.bodyLarge,
|
||||
),
|
||||
const Icon(Icons.chevron_right)
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
itemCount: pro.servers.length,
|
||||
@@ -180,7 +192,7 @@ class _SSHTabPageState extends State<SSHTabPage>
|
||||
),
|
||||
key: key,
|
||||
);
|
||||
_tabRN.build();
|
||||
_tabRN.notify();
|
||||
// Wait for the page to be built
|
||||
await Future.delayed(Durations.short3);
|
||||
final idx = _tabMap.keys.toList().indexOf(name);
|
||||
@@ -202,7 +214,7 @@ final class _TabBar extends StatelessWidget implements PreferredSizeWidget {
|
||||
required this.onClose,
|
||||
});
|
||||
|
||||
final ValueNotifier<int> idxVN;
|
||||
final ValueListenable<int> idxVN;
|
||||
final _TabMap map;
|
||||
final void Function(int idx) onTap;
|
||||
final void Function(String name) onClose;
|
||||
|
||||
@@ -314,7 +314,7 @@ class _LocalStoragePageState extends State<LocalStoragePage> {
|
||||
leading: const Icon(Icons.open_in_new),
|
||||
title: Text(l10n.open),
|
||||
onTap: () {
|
||||
Pfs.sharePath(file.absolute.path);
|
||||
Pfs.share(path: file.absolute.path);
|
||||
},
|
||||
),
|
||||
],
|
||||
|
||||
@@ -1,23 +1,24 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:dartssh2/dartssh2.dart';
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:server_box/core/extension/context/locale.dart';
|
||||
import 'package:server_box/core/extension/sftpfile.dart';
|
||||
import 'package:server_box/core/route.dart';
|
||||
import 'package:server_box/core/utils/comparator.dart';
|
||||
import 'package:server_box/data/model/server/server_private_info.dart';
|
||||
import 'package:server_box/data/model/sftp/absolute_path.dart';
|
||||
import 'package:server_box/data/model/sftp/browser_status.dart';
|
||||
import 'package:server_box/data/model/sftp/req.dart';
|
||||
import 'package:server_box/data/res/misc.dart';
|
||||
import 'package:server_box/data/res/provider.dart';
|
||||
import 'package:server_box/data/res/store.dart';
|
||||
import 'package:server_box/view/widget/omit_start_text.dart';
|
||||
|
||||
import '../../../core/route.dart';
|
||||
import '../../../data/model/server/server_private_info.dart';
|
||||
import '../../../data/model/sftp/absolute_path.dart';
|
||||
import '../../../data/model/sftp/browser_status.dart';
|
||||
import '../../../data/model/sftp/req.dart';
|
||||
import '../../widget/two_line_text.dart';
|
||||
import 'package:icons_plus/icons_plus.dart';
|
||||
import 'package:server_box/view/widget/two_line_text.dart';
|
||||
import 'package:server_box/view/widget/unix_perm.dart';
|
||||
|
||||
class SftpPage extends StatefulWidget {
|
||||
final ServerPrivateInfo spi;
|
||||
@@ -175,49 +176,50 @@ class _SftpPageState extends State<SftpPage> with AfterLayoutMixin {
|
||||
|
||||
Widget _buildUploadBtn() {
|
||||
return IconButton(
|
||||
onPressed: () async {
|
||||
final idx = await context.showRoundDialog(
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
ListTile(
|
||||
leading: const Icon(Icons.open_in_new),
|
||||
title: Text(l10n.system),
|
||||
onTap: () => context.pop(1),
|
||||
),
|
||||
ListTile(
|
||||
leading: const Icon(Icons.folder),
|
||||
title: Text(l10n.inner),
|
||||
onTap: () => context.pop(0),
|
||||
),
|
||||
],
|
||||
));
|
||||
final path = await () async {
|
||||
switch (idx) {
|
||||
case 0:
|
||||
return await AppRoutes.localStorage(isPickFile: true)
|
||||
.go<String>(context);
|
||||
case 1:
|
||||
return await Pfs.pickFilePath();
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}();
|
||||
if (path == null) {
|
||||
return;
|
||||
onPressed: () async {
|
||||
final idx = await context.showRoundDialog(
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
ListTile(
|
||||
leading: const Icon(Icons.open_in_new),
|
||||
title: Text(l10n.system),
|
||||
onTap: () => context.pop(1),
|
||||
),
|
||||
ListTile(
|
||||
leading: const Icon(Icons.folder),
|
||||
title: Text(l10n.inner),
|
||||
onTap: () => context.pop(0),
|
||||
),
|
||||
],
|
||||
));
|
||||
final path = await () async {
|
||||
switch (idx) {
|
||||
case 0:
|
||||
return await AppRoutes.localStorage(isPickFile: true)
|
||||
.go<String>(context);
|
||||
case 1:
|
||||
return await Pfs.pickFilePath();
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
final remoteDir = _status.path?.path;
|
||||
if (remoteDir == null) {
|
||||
context.showSnackBar('remote path is null');
|
||||
return;
|
||||
}
|
||||
final remotePath = '$remoteDir/${path.split('/').last}';
|
||||
Loggers.app.info('SFTP upload local: $path, remote: $remotePath');
|
||||
Pros.sftp.add(
|
||||
SftpReq(widget.spi, remotePath, path, SftpReqType.upload),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.upload_file));
|
||||
}();
|
||||
if (path == null) {
|
||||
return;
|
||||
}
|
||||
final remoteDir = _status.path?.path;
|
||||
if (remoteDir == null) {
|
||||
context.showSnackBar('remote path is null');
|
||||
return;
|
||||
}
|
||||
final remotePath = '$remoteDir/${path.split('/').last}';
|
||||
Loggers.app.info('SFTP upload local: $path, remote: $remotePath');
|
||||
Pros.sftp.add(
|
||||
SftpReq(widget.spi, remotePath, path, SftpReqType.upload),
|
||||
);
|
||||
},
|
||||
icon: const Icon(Icons.upload_file),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildAddBtn() {
|
||||
@@ -372,6 +374,42 @@ class _SftpPageState extends State<SftpPage> with AfterLayoutMixin {
|
||||
title: Text(l10n.rename),
|
||||
onTap: () => _rename(file),
|
||||
),
|
||||
ListTile(
|
||||
leading: const Icon(MingCute.copy_line),
|
||||
title: Text(l10n.copyPath),
|
||||
onTap: () {
|
||||
Pfs.copy(_getRemotePath(file));
|
||||
context.pop();
|
||||
context.showSnackBar(l10n.success);
|
||||
},
|
||||
),
|
||||
ListTile(
|
||||
leading: const Icon(Icons.security),
|
||||
title: Text(l10n.permission),
|
||||
onTap: () async {
|
||||
context.pop();
|
||||
|
||||
final perm = file.attr.mode?.toUnixPerm() ?? UnixPerm.empty;
|
||||
var newPerm = perm.copyWith();
|
||||
final ok = await context.showRoundDialog(
|
||||
child: UnixPermEditor(perm: perm, onChanged: (p) => newPerm = p),
|
||||
actions: Btns.oks(onTap: () => context.pop(true)),
|
||||
);
|
||||
|
||||
final permStr = newPerm.perm;
|
||||
if (ok == true && permStr != perm.perm) {
|
||||
await context.showLoadingDialog(
|
||||
fn: () async {
|
||||
await _client!.run('chmod $permStr "${_getRemotePath(file)}"');
|
||||
await _listDir();
|
||||
},
|
||||
onErr: (e, s) {
|
||||
context.showErrDialog(e: e, s: s, operation: l10n.permission);
|
||||
},
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
];
|
||||
if (notDir) {
|
||||
children.addAll([
|
||||
|
||||
@@ -59,65 +59,84 @@ class _SftpMissionPageState extends State<SftpMissionPage> {
|
||||
),
|
||||
);
|
||||
}
|
||||
switch (status.status) {
|
||||
case SftpWorkerStatus.finished:
|
||||
final time = status.spentTime.toString();
|
||||
final str = '${l10n.finished} ${l10n.spentTime(
|
||||
time == 'null' ? l10n.unknown : (time.substring(0, time.length - 7)),
|
||||
)}';
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: str,
|
||||
trailing: Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
final idx = status.req.localPath.lastIndexOf('/');
|
||||
final dir = status.req.localPath.substring(0, idx);
|
||||
AppRoutes.localStorage(initDir: dir).go(context);
|
||||
},
|
||||
icon: const Icon(Icons.file_open)),
|
||||
IconButton(
|
||||
onPressed: () => Pfs.sharePath(status.req.localPath),
|
||||
icon: const Icon(Icons.open_in_new),
|
||||
)
|
||||
],
|
||||
),
|
||||
);
|
||||
case SftpWorkerStatus.loading:
|
||||
final percentStr = (status.progress ?? 0.0).toStringAsFixed(2);
|
||||
final size = (status.size ?? 0).bytes2Str;
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.percentOfSize(percentStr, size),
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
case SftpWorkerStatus.preparing:
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.sftpDlPrepare,
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
case SftpWorkerStatus.sshConnectted:
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.sftpSSHConnected,
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
default:
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.unknown,
|
||||
trailing: IconButton(
|
||||
onPressed: () => context.showRoundDialog(
|
||||
title: l10n.error,
|
||||
child: Text((status.error ?? l10n.unknown).toString()),
|
||||
),
|
||||
icon: const Icon(Icons.error),
|
||||
),
|
||||
);
|
||||
}
|
||||
return switch (status.status) {
|
||||
const (SftpWorkerStatus.finished) => _buildFinished(status),
|
||||
const (SftpWorkerStatus.loading) => _buildLoading(status),
|
||||
const (SftpWorkerStatus.sshConnectted) => _buildConnected(status),
|
||||
const (SftpWorkerStatus.preparing) => _buildPreparing(status),
|
||||
_ => _buildDefault(status),
|
||||
};
|
||||
}
|
||||
|
||||
Widget _buildPreparing(SftpReqStatus status) {
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.sftpDlPrepare,
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildDefault(SftpReqStatus status) {
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.unknown,
|
||||
trailing: IconButton(
|
||||
onPressed: () => context.showRoundDialog(
|
||||
title: l10n.error,
|
||||
child: Text((status.error ?? l10n.unknown).toString()),
|
||||
),
|
||||
icon: const Icon(Icons.error),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildConnected(SftpReqStatus status) {
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.sftpSSHConnected,
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildLoading(SftpReqStatus status) {
|
||||
final percentStr = (status.progress ?? 0.0).toStringAsFixed(2);
|
||||
final size = (status.size ?? 0).bytes2Str;
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: l10n.percentOfSize(percentStr, size),
|
||||
trailing: _buildDelete(status.fileName, status.id),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildFinished(SftpReqStatus status) {
|
||||
final time = status.spentTime.toString();
|
||||
final str = '${l10n.finished} ${l10n.spentTime(
|
||||
time == 'null' ? l10n.unknown : (time.substring(0, time.length - 7)),
|
||||
)}';
|
||||
|
||||
final btns = Row(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
final idx = status.req.localPath.lastIndexOf('/');
|
||||
final dir = status.req.localPath.substring(0, idx);
|
||||
AppRoutes.localStorage(initDir: dir).go(context);
|
||||
},
|
||||
icon: const Icon(Icons.file_open),
|
||||
),
|
||||
IconButton(
|
||||
onPressed: () => Pfs.share(path: status.req.localPath),
|
||||
icon: const Icon(Icons.open_in_new),
|
||||
)
|
||||
],
|
||||
);
|
||||
|
||||
return _wrapInCard(
|
||||
status: status,
|
||||
subtitle: str,
|
||||
trailing: btns,
|
||||
);
|
||||
}
|
||||
|
||||
Widget _wrapInCard({
|
||||
|
||||
128
lib/view/widget/unix_perm.dart
Normal file
@@ -0,0 +1,128 @@
|
||||
import 'package:fl_lib/fl_lib.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
final class RWX {
|
||||
final bool r;
|
||||
final bool w;
|
||||
final bool x;
|
||||
|
||||
const RWX({
|
||||
required this.r,
|
||||
required this.w,
|
||||
required this.x,
|
||||
});
|
||||
|
||||
RWX copyWith({bool? r, bool? w, bool? x}) {
|
||||
return RWX(r: r ?? this.r, w: w ?? this.w, x: x ?? this.x);
|
||||
}
|
||||
|
||||
int get value {
|
||||
return (r ? 4 : 0) + (w ? 2 : 0) + (x ? 1 : 0);
|
||||
}
|
||||
}
|
||||
|
||||
final class UnixPerm {
|
||||
final RWX user;
|
||||
final RWX group;
|
||||
final RWX other;
|
||||
|
||||
const UnixPerm({
|
||||
required this.user,
|
||||
required this.group,
|
||||
required this.other,
|
||||
});
|
||||
|
||||
UnixPerm copyWith({RWX? user, RWX? group, RWX? other}) {
|
||||
return UnixPerm(
|
||||
user: user ?? this.user,
|
||||
group: group ?? this.group,
|
||||
other: other ?? this.other,
|
||||
);
|
||||
}
|
||||
|
||||
/// eg.: 744
|
||||
String get perm {
|
||||
return '${user.value}${group.value}${other.value}';
|
||||
}
|
||||
|
||||
static UnixPerm get empty => const UnixPerm(
|
||||
user: RWX(r: false, w: false, x: false),
|
||||
group: RWX(r: false, w: false, x: false),
|
||||
other: RWX(r: false, w: false, x: false),
|
||||
);
|
||||
}
|
||||
|
||||
final class UnixPermEditor extends StatefulWidget {
|
||||
final UnixPerm perm;
|
||||
final void Function(UnixPerm) onChanged;
|
||||
const UnixPermEditor(
|
||||
{super.key, required this.perm, required this.onChanged});
|
||||
|
||||
@override
|
||||
_UnixPermEditorState createState() => _UnixPermEditorState();
|
||||
}
|
||||
|
||||
final class _UnixPermEditorState extends State<UnixPermEditor> {
|
||||
late UnixPerm perm;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
perm = widget.perm;
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
const Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceAround,
|
||||
children: [
|
||||
Text('R'),
|
||||
Text('W'),
|
||||
Text('X'),
|
||||
],
|
||||
).paddingOnly(left: 13),
|
||||
UIs.height7,
|
||||
_buildRow('U', perm.user),
|
||||
_buildRow('G', perm.group),
|
||||
_buildRow('O', perm.other),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildRow(String title, RWX rwx) {
|
||||
return Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
SizedBox(width: 7, child: Text(title)),
|
||||
_buildSwitch(rwx.r, (v) {
|
||||
setState(() {
|
||||
perm = perm.copyWith(user: rwx.copyWith(r: v));
|
||||
});
|
||||
widget.onChanged(perm);
|
||||
}),
|
||||
_buildSwitch(rwx.w, (v) {
|
||||
setState(() {
|
||||
perm = perm.copyWith(user: rwx.copyWith(w: v));
|
||||
});
|
||||
widget.onChanged(perm);
|
||||
}),
|
||||
_buildSwitch(rwx.x, (v) {
|
||||
setState(() {
|
||||
perm = perm.copyWith(user: rwx.copyWith(x: v));
|
||||
});
|
||||
widget.onChanged(perm);
|
||||
}),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildSwitch(bool value, void Function(bool) onChanged) {
|
||||
return Switch(
|
||||
value: value,
|
||||
onChanged: onChanged,
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,11 +1,19 @@
|
||||
# Project-level configuration.
|
||||
cmake_minimum_required(VERSION 3.10)
|
||||
project(runner LANGUAGES CXX)
|
||||
|
||||
# The name of the executable created for the application. Change this to change
|
||||
# the on-disk name of your application.
|
||||
set(BINARY_NAME "ServerBox")
|
||||
# The unique GTK application identifier for this application. See:
|
||||
# https://wiki.gnome.org/HowDoI/ChooseApplicationID
|
||||
set(APPLICATION_ID "tech.lolli.toolbox")
|
||||
|
||||
# Explicitly opt in to modern CMake behaviors to avoid warnings with recent
|
||||
# versions of CMake.
|
||||
cmake_policy(SET CMP0063 NEW)
|
||||
|
||||
# Load bundled libraries from the lib/ directory relative to the binary.
|
||||
set(CMAKE_INSTALL_RPATH "$ORIGIN/lib")
|
||||
|
||||
# Root filesystem for cross-building.
|
||||
@@ -18,7 +26,7 @@ if(FLUTTER_TARGET_PLATFORM_SYSROOT)
|
||||
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
|
||||
endif()
|
||||
|
||||
# Configure build options.
|
||||
# Define build configuration options.
|
||||
if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
|
||||
set(CMAKE_BUILD_TYPE "Debug" CACHE
|
||||
STRING "Flutter build mode" FORCE)
|
||||
@@ -27,6 +35,10 @@ if(NOT CMAKE_BUILD_TYPE AND NOT CMAKE_CONFIGURATION_TYPES)
|
||||
endif()
|
||||
|
||||
# Compilation settings that should be applied to most targets.
|
||||
#
|
||||
# Be cautious about adding new options here, as plugins use this function by
|
||||
# default. In most cases, you should add new options to specific targets instead
|
||||
# of modifying this function.
|
||||
function(APPLY_STANDARD_SETTINGS TARGET)
|
||||
target_compile_features(${TARGET} PUBLIC cxx_std_14)
|
||||
target_compile_options(${TARGET} PRIVATE -Wall -Werror)
|
||||
@@ -34,9 +46,8 @@ function(APPLY_STANDARD_SETTINGS TARGET)
|
||||
target_compile_definitions(${TARGET} PRIVATE "$<$<NOT:$<CONFIG:Debug>>:NDEBUG>")
|
||||
endfunction()
|
||||
|
||||
set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter")
|
||||
|
||||
# Flutter library and tool build rules.
|
||||
set(FLUTTER_MANAGED_DIR "${CMAKE_CURRENT_SOURCE_DIR}/flutter")
|
||||
add_subdirectory(${FLUTTER_MANAGED_DIR})
|
||||
|
||||
# System-level dependencies.
|
||||
@@ -45,16 +56,27 @@ pkg_check_modules(GTK REQUIRED IMPORTED_TARGET gtk+-3.0)
|
||||
|
||||
add_definitions(-DAPPLICATION_ID="${APPLICATION_ID}")
|
||||
|
||||
# Application build
|
||||
# Define the application target. To change its name, change BINARY_NAME above,
|
||||
# not the value here, or `flutter run` will no longer work.
|
||||
#
|
||||
# Any new source files that you add to the application should be added here.
|
||||
add_executable(${BINARY_NAME}
|
||||
"main.cc"
|
||||
"my_application.cc"
|
||||
"${FLUTTER_MANAGED_DIR}/generated_plugin_registrant.cc"
|
||||
)
|
||||
|
||||
# Apply the standard set of build settings. This can be removed for applications
|
||||
# that need different build settings.
|
||||
apply_standard_settings(${BINARY_NAME})
|
||||
|
||||
# Add dependency libraries. Add any application-specific dependencies here.
|
||||
target_link_libraries(${BINARY_NAME} PRIVATE flutter)
|
||||
target_link_libraries(${BINARY_NAME} PRIVATE PkgConfig::GTK)
|
||||
|
||||
# Run the Flutter tool portions of the build. This must not be removed.
|
||||
add_dependencies(${BINARY_NAME} flutter_assemble)
|
||||
|
||||
# Only the install-generated bundle's copy of the executable will launch
|
||||
# correctly, since the resources must in the right relative locations. To avoid
|
||||
# people trying to run the unbundled copy, put it in a subdirectory instead of
|
||||
@@ -64,6 +86,7 @@ set_target_properties(${BINARY_NAME}
|
||||
RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/intermediates_do_not_run"
|
||||
)
|
||||
|
||||
|
||||
# Generated plugin build rules, which manage building the plugins and adding
|
||||
# them to the application.
|
||||
include(flutter/generated_plugins.cmake)
|
||||
@@ -94,11 +117,17 @@ install(FILES "${FLUTTER_ICU_DATA_FILE}" DESTINATION "${INSTALL_BUNDLE_DATA_DIR}
|
||||
install(FILES "${FLUTTER_LIBRARY}" DESTINATION "${INSTALL_BUNDLE_LIB_DIR}"
|
||||
COMPONENT Runtime)
|
||||
|
||||
if(PLUGIN_BUNDLED_LIBRARIES)
|
||||
install(FILES "${PLUGIN_BUNDLED_LIBRARIES}"
|
||||
foreach(bundled_library ${PLUGIN_BUNDLED_LIBRARIES})
|
||||
install(FILES "${bundled_library}"
|
||||
DESTINATION "${INSTALL_BUNDLE_LIB_DIR}"
|
||||
COMPONENT Runtime)
|
||||
endif()
|
||||
endforeach(bundled_library)
|
||||
|
||||
# Copy the native assets provided by the build.dart from all packages.
|
||||
set(NATIVE_ASSETS_DIR "${PROJECT_BUILD_DIR}native_assets/linux/")
|
||||
install(DIRECTORY "${NATIVE_ASSETS_DIR}"
|
||||
DESTINATION "${INSTALL_BUNDLE_LIB_DIR}"
|
||||
COMPONENT Runtime)
|
||||
|
||||
# Fully re-copy the assets directory on each build to avoid having stale files
|
||||
# from a previous install.
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
# This file controls Flutter-level build steps. It should not be edited.
|
||||
cmake_minimum_required(VERSION 3.10)
|
||||
|
||||
set(EPHEMERAL_DIR "${CMAKE_CURRENT_SOURCE_DIR}/ephemeral")
|
||||
|
||||
@@ -20,6 +20,33 @@ static void my_application_activate(GApplication* application) {
|
||||
GtkWindow* window =
|
||||
GTK_WINDOW(gtk_application_window_new(GTK_APPLICATION(application)));
|
||||
|
||||
// Use a header bar when running in GNOME as this is the common style used
|
||||
// by applications and is the setup most users will be using (e.g. Ubuntu
|
||||
// desktop).
|
||||
// If running on X and not using GNOME then just use a traditional title bar
|
||||
// in case the window manager does more exotic layout, e.g. tiling.
|
||||
// If running on Wayland assume the header bar will work (may need changing
|
||||
// if future cases occur).
|
||||
gboolean use_header_bar = TRUE;
|
||||
#ifdef GDK_WINDOWING_X11
|
||||
GdkScreen* screen = gtk_window_get_screen(window);
|
||||
if (GDK_IS_X11_SCREEN(screen)) {
|
||||
const gchar* wm_name = gdk_x11_screen_get_window_manager_name(screen);
|
||||
if (g_strcmp0(wm_name, "GNOME Shell") != 0) {
|
||||
use_header_bar = FALSE;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
if (use_header_bar) {
|
||||
GtkHeaderBar* header_bar = GTK_HEADER_BAR(gtk_header_bar_new());
|
||||
gtk_widget_show(GTK_WIDGET(header_bar));
|
||||
gtk_header_bar_set_title(header_bar, "ServerBox");
|
||||
gtk_header_bar_set_show_close_button(header_bar, TRUE);
|
||||
gtk_window_set_titlebar(window, GTK_WIDGET(header_bar));
|
||||
} else {
|
||||
gtk_window_set_title(window, "ServerBox");
|
||||
}
|
||||
|
||||
gtk_window_set_default_size(window, 400, 777);
|
||||
gtk_widget_show(GTK_WIDGET(window));
|
||||
|
||||
@@ -54,6 +81,24 @@ static gboolean my_application_local_command_line(GApplication* application, gch
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
// Implements GApplication::startup.
|
||||
static void my_application_startup(GApplication* application) {
|
||||
//MyApplication* self = MY_APPLICATION(object);
|
||||
|
||||
// Perform any actions required at application startup.
|
||||
|
||||
G_APPLICATION_CLASS(my_application_parent_class)->startup(application);
|
||||
}
|
||||
|
||||
// Implements GApplication::shutdown.
|
||||
static void my_application_shutdown(GApplication* application) {
|
||||
//MyApplication* self = MY_APPLICATION(object);
|
||||
|
||||
// Perform any actions required at application shutdown.
|
||||
|
||||
G_APPLICATION_CLASS(my_application_parent_class)->shutdown(application);
|
||||
}
|
||||
|
||||
// Implements GObject::dispose.
|
||||
static void my_application_dispose(GObject* object) {
|
||||
MyApplication* self = MY_APPLICATION(object);
|
||||
@@ -64,6 +109,8 @@ static void my_application_dispose(GObject* object) {
|
||||
static void my_application_class_init(MyApplicationClass* klass) {
|
||||
G_APPLICATION_CLASS(klass)->activate = my_application_activate;
|
||||
G_APPLICATION_CLASS(klass)->local_command_line = my_application_local_command_line;
|
||||
G_APPLICATION_CLASS(klass)->startup = my_application_startup;
|
||||
G_APPLICATION_CLASS(klass)->shutdown = my_application_shutdown;
|
||||
G_OBJECT_CLASS(klass)->dispose = my_application_dispose;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,9 +1,13 @@
|
||||
PODS:
|
||||
- device_info_plus (0.0.1):
|
||||
- FlutterMacOS
|
||||
- dynamic_color (0.0.2):
|
||||
- FlutterMacOS
|
||||
- FlutterMacOS (1.0.0)
|
||||
- icloud_storage (0.0.1):
|
||||
- FlutterMacOS
|
||||
- package_info_plus (0.0.1):
|
||||
- FlutterMacOS
|
||||
- path_provider_foundation (0.0.1):
|
||||
- Flutter
|
||||
- FlutterMacOS
|
||||
@@ -16,27 +20,36 @@ PODS:
|
||||
- FlutterMacOS
|
||||
- url_launcher_macos (0.0.1):
|
||||
- FlutterMacOS
|
||||
- wakelock_plus (0.0.1):
|
||||
- FlutterMacOS
|
||||
- window_manager (0.2.0):
|
||||
- FlutterMacOS
|
||||
|
||||
DEPENDENCIES:
|
||||
- device_info_plus (from `Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos`)
|
||||
- dynamic_color (from `Flutter/ephemeral/.symlinks/plugins/dynamic_color/macos`)
|
||||
- FlutterMacOS (from `Flutter/ephemeral`)
|
||||
- icloud_storage (from `Flutter/ephemeral/.symlinks/plugins/icloud_storage/macos`)
|
||||
- package_info_plus (from `Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos`)
|
||||
- path_provider_foundation (from `Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin`)
|
||||
- screen_retriever (from `Flutter/ephemeral/.symlinks/plugins/screen_retriever/macos`)
|
||||
- share_plus (from `Flutter/ephemeral/.symlinks/plugins/share_plus/macos`)
|
||||
- shared_preferences_foundation (from `Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin`)
|
||||
- url_launcher_macos (from `Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos`)
|
||||
- wakelock_plus (from `Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos`)
|
||||
- window_manager (from `Flutter/ephemeral/.symlinks/plugins/window_manager/macos`)
|
||||
|
||||
EXTERNAL SOURCES:
|
||||
device_info_plus:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/device_info_plus/macos
|
||||
dynamic_color:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/dynamic_color/macos
|
||||
FlutterMacOS:
|
||||
:path: Flutter/ephemeral
|
||||
icloud_storage:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/icloud_storage/macos
|
||||
package_info_plus:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/package_info_plus/macos
|
||||
path_provider_foundation:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/path_provider_foundation/darwin
|
||||
screen_retriever:
|
||||
@@ -47,18 +60,23 @@ EXTERNAL SOURCES:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/shared_preferences_foundation/darwin
|
||||
url_launcher_macos:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/url_launcher_macos/macos
|
||||
wakelock_plus:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/wakelock_plus/macos
|
||||
window_manager:
|
||||
:path: Flutter/ephemeral/.symlinks/plugins/window_manager/macos
|
||||
|
||||
SPEC CHECKSUMS:
|
||||
device_info_plus: ce1b7762849d3ec103d0e0517299f2db7ad60720
|
||||
dynamic_color: 2eaa27267de1ca20d879fbd6e01259773fb1670f
|
||||
FlutterMacOS: 8f6f14fa908a6fb3fba0cd85dbd81ec4b251fb24
|
||||
icloud_storage: 33b05299e26d1391d724da8d62860e702380a1cd
|
||||
path_provider_foundation: 3784922295ac71e43754bd15e0653ccfd36a147c
|
||||
package_info_plus: fa739dd842b393193c5ca93c26798dff6e3d0e0c
|
||||
path_provider_foundation: 2b6b4c569c0fb62ec74538f866245ac84301af46
|
||||
screen_retriever: 59634572a57080243dd1bf715e55b6c54f241a38
|
||||
share_plus: 36537c04ce0c3e3f5bd297ce4318b6d5ee5fd6cf
|
||||
shared_preferences_foundation: b4c3b4cddf1c21f02770737f147a3f5da9d39695
|
||||
url_launcher_macos: d2691c7dd33ed713bf3544850a623080ec693d95
|
||||
shared_preferences_foundation: fcdcbc04712aee1108ac7fda236f363274528f78
|
||||
url_launcher_macos: 5f437abeda8c85500ceb03f5c1938a8c5a705399
|
||||
wakelock_plus: 4783562c9a43d209c458cb9b30692134af456269
|
||||
window_manager: 3a1844359a6295ab1e47659b1a777e36773cd6e8
|
||||
|
||||
PODFILE CHECKSUM: 8cdf29216ea1ab6b9743188287968d22b4579c1d
|
||||
|
||||
@@ -471,7 +471,7 @@
|
||||
CODE_SIGN_IDENTITY = "Apple Development";
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
INFOPLIST_FILE = Runner/Info.plist;
|
||||
INFOPLIST_KEY_CFBundleDisplayName = "Server Box";
|
||||
@@ -481,7 +481,7 @@
|
||||
"@executable_path/../Frameworks",
|
||||
);
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.15;
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "Server Box";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
@@ -608,7 +608,7 @@
|
||||
CODE_SIGN_IDENTITY = "Apple Development";
|
||||
CODE_SIGN_STYLE = Automatic;
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = BA88US33G6;
|
||||
INFOPLIST_FILE = Runner/Info.plist;
|
||||
INFOPLIST_KEY_CFBundleDisplayName = "Server Box";
|
||||
@@ -618,7 +618,7 @@
|
||||
"@executable_path/../Frameworks",
|
||||
);
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.15;
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "Server Box";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
@@ -638,7 +638,7 @@
|
||||
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "3rd Party Mac Developer Application";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
CURRENT_PROJECT_VERSION = 970;
|
||||
CURRENT_PROJECT_VERSION = 1018;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
"DEVELOPMENT_TEAM[sdk=macosx*]" = BA88US33G6;
|
||||
INFOPLIST_FILE = Runner/Info.plist;
|
||||
@@ -649,7 +649,7 @@
|
||||
"@executable_path/../Frameworks",
|
||||
);
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.15;
|
||||
MARKETING_VERSION = 1.0.970;
|
||||
MARKETING_VERSION = 1.0.1018;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.lollipopkit.toolbox;
|
||||
PRODUCT_NAME = "Server Box";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
|
||||
40
pubspec.lock
@@ -9,14 +9,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "67.0.0"
|
||||
after_layout:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: after_layout
|
||||
sha256: "95a1cb2ca1464f44f14769329fbf15987d20ab6c88f8fc5d359bd362be625f29"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.2.0"
|
||||
analyzer:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -376,8 +368,8 @@ packages:
|
||||
dependency: "direct dev"
|
||||
description:
|
||||
path: "."
|
||||
ref: "v1.0.17"
|
||||
resolved-ref: bcb7019cc8bb3ab8c9c36653cd13936909c6e075
|
||||
ref: "v1.0.34"
|
||||
resolved-ref: "9d8afa6b0bc72223213ca30f67c3be2eb129f928"
|
||||
url: "https://github.com/lppcg/fl_build.git"
|
||||
source: git
|
||||
version: "1.0.0"
|
||||
@@ -393,8 +385,8 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: "v1.0.40"
|
||||
resolved-ref: "1f547b45bc9083558ee88eafa61df92eb0abf552"
|
||||
ref: "v1.0.72"
|
||||
resolved-ref: "7b57c8e08ff199247bb174d499876627b10f86b5"
|
||||
url: "https://github.com/lppcg/fl_lib"
|
||||
source: git
|
||||
version: "0.0.1"
|
||||
@@ -1404,19 +1396,11 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: "v1.0.84"
|
||||
resolved-ref: "50405d87bea86aece143c235b8b17263d37de3ef"
|
||||
ref: "v1.0.85"
|
||||
resolved-ref: "13e42750a8f8dbf9a6c7890198b0dd18283a0692"
|
||||
url: "https://github.com/lollipopkit/watch_connectivity"
|
||||
source: git
|
||||
version: "0.1.5"
|
||||
watch_connectivity_platform_interface:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: watch_connectivity_platform_interface
|
||||
sha256: "9074115391bd764c08a17346fcbc4d5c0b555672defbe6928ac648503b54aa9c"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "0.1.2"
|
||||
watcher:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -1450,14 +1434,14 @@ packages:
|
||||
source: hosted
|
||||
version: "3.0.0"
|
||||
webdav_client:
|
||||
dependency: transitive
|
||||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: main
|
||||
resolved-ref: "88de97ad783c624d81b0dbcc09927b10aabd5580"
|
||||
ref: "v1.0.66"
|
||||
resolved-ref: "1908cd0f4909730d9ae4d4fc4c05fb2576b3f674"
|
||||
url: "https://github.com/lollipopkit/webdav_client"
|
||||
source: git
|
||||
version: "1.2.1"
|
||||
version: "1.2.2"
|
||||
win32:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -1502,8 +1486,8 @@ packages:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
path: "."
|
||||
ref: master
|
||||
resolved-ref: "13a280e77dd077b439af24ad3d054d318ae5df4a"
|
||||
ref: "v1.0.586"
|
||||
resolved-ref: b8c73bec722055f24c5724cd2f2297859e95b6af
|
||||
url: "https://github.com/lollipopkit/xterm.dart"
|
||||
source: git
|
||||
version: "4.0.0"
|
||||
|
||||
15
pubspec.yaml
@@ -1,7 +1,7 @@
|
||||
name: server_box
|
||||
description: server status & toolbox app.
|
||||
publish_to: 'none'
|
||||
version: 1.0.971+971
|
||||
version: 1.0.1018+1018
|
||||
|
||||
environment:
|
||||
sdk: ">=3.0.0"
|
||||
@@ -14,7 +14,6 @@ dependencies:
|
||||
provider: ^6.0.0
|
||||
hive_flutter: ^1.1.0
|
||||
dio: ^5.2.1
|
||||
after_layout: ^1.1.0
|
||||
easy_isolate: ^1.3.0
|
||||
intl: ^0.19.0
|
||||
highlight: ^0.7.0
|
||||
@@ -43,7 +42,7 @@ dependencies:
|
||||
xterm:
|
||||
git:
|
||||
url: https://github.com/lollipopkit/xterm.dart
|
||||
ref: master
|
||||
ref: v1.0.586
|
||||
computer:
|
||||
git:
|
||||
url: https://github.com/lollipopkit/dart_computer
|
||||
@@ -51,15 +50,19 @@ dependencies:
|
||||
watch_connectivity:
|
||||
git:
|
||||
url: https://github.com/lollipopkit/watch_connectivity
|
||||
ref: v1.0.84
|
||||
ref: v1.0.85
|
||||
plain_notification_token:
|
||||
git:
|
||||
url: https://github.com/lollipopkit/plain_notification_token
|
||||
ref: v1.0.23
|
||||
webdav_client:
|
||||
git:
|
||||
url: https://github.com/lollipopkit/webdav_client
|
||||
ref: v1.0.66
|
||||
fl_lib:
|
||||
git:
|
||||
url: https://github.com/lppcg/fl_lib
|
||||
ref: v1.0.40
|
||||
ref: v1.0.72
|
||||
|
||||
dependency_overrides:
|
||||
# dartssh2:
|
||||
@@ -80,7 +83,7 @@ dev_dependencies:
|
||||
# path: ../fl_build
|
||||
git:
|
||||
url: https://github.com/lppcg/fl_build.git
|
||||
ref: v1.0.17
|
||||
ref: v1.0.34
|
||||
|
||||
flutter:
|
||||
generate: true
|
||||
|
||||
@@ -117,7 +117,7 @@ bool Win32Window::CreateAndShow(const std::wstring& title,
|
||||
double scale_factor = dpi / 96.0;
|
||||
|
||||
HWND window = CreateWindow(
|
||||
window_class, title.c_str(), WS_OVERLAPPEDWINDOW | WS_VISIBLE,
|
||||
window_class, title.c_str(), WS_OVERLAPPEDWINDOW,
|
||||
Scale(origin.x, scale_factor), Scale(origin.y, scale_factor),
|
||||
Scale(size.width, scale_factor), Scale(size.height, scale_factor),
|
||||
nullptr, nullptr, GetModuleHandle(nullptr), this);
|
||||
|
||||