Compare commits
14 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
91e9c0b02b | ||
|
|
658ea26ab7 | ||
|
|
77b736541e | ||
|
|
843b881da6 | ||
|
|
3ca8acc805 | ||
|
|
63809d4f16 | ||
|
|
557660b16b | ||
|
|
12be8bda52 | ||
|
|
81efd25e0a | ||
|
|
7037009ce4 | ||
|
|
4a0902d4c8 | ||
|
|
ed25ac1748 | ||
|
|
55e09ed062 | ||
|
|
babb548c22 |
61
.github/workflows/build.yml
vendored
Normal file
61
.github/workflows/build.yml
vendored
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
name: release
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
branches: [ "master" ]
|
||||||
|
pull_request:
|
||||||
|
branches: [ "master" ]
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
strategy:
|
||||||
|
matrix:
|
||||||
|
configuration: [Release]
|
||||||
|
|
||||||
|
runs-on: windows-latest
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- name: Checkout
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
|
||||||
|
- name: 删除工作流运行
|
||||||
|
uses: Mattraks/delete-workflow-runs@v2
|
||||||
|
with:
|
||||||
|
token: ${{ github.token }}
|
||||||
|
repository: ${{ github.repository }}
|
||||||
|
retain_days: 0
|
||||||
|
keep_minimum_runs: 1
|
||||||
|
|
||||||
|
- name: Build
|
||||||
|
run: cd v2rayN &&
|
||||||
|
.\build.ps1
|
||||||
|
|
||||||
|
# - name: Package
|
||||||
|
# shell: pwsh
|
||||||
|
# run: |
|
||||||
|
# 7z a -mx9 ..\v2rayN.7z $env:Wap_Project_Directory
|
||||||
|
|
||||||
|
- name: Upload build artifacts
|
||||||
|
uses: actions/upload-artifact@v3
|
||||||
|
with:
|
||||||
|
name: v2rayN
|
||||||
|
path:
|
||||||
|
.\v2rayN\v2rayN.zip
|
||||||
|
|
||||||
|
|
||||||
|
# - name: Release
|
||||||
|
# uses: softprops/action-gh-release@v1
|
||||||
|
# env:
|
||||||
|
# GITHUB_TOKEN: ${{ secrets.ACCESS_TOKEN }}
|
||||||
|
# with:
|
||||||
|
# prerelease: ${{ contains(github.ref, '-') }}
|
||||||
|
# draft: false
|
||||||
|
# files: |
|
||||||
|
# .\v2rayN\v2rayN.zip
|
||||||
|
# body: |
|
||||||
|
# [](https://t.me/netch_channel) [](https://t.me/netch_group)
|
||||||
|
# ## Changelogs
|
||||||
|
# * This is an automated deployment of GitHub Actions, the change log should be updated manually soon
|
||||||
|
|
||||||
|
# ## 更新日志
|
||||||
|
# * 这是 GitHub Actions 自动化部署,更新日志应该很快会手动更新
|
||||||
106
.github/workflows/dotnet-desktop.yml
vendored
106
.github/workflows/dotnet-desktop.yml
vendored
@@ -1,106 +0,0 @@
|
|||||||
# This workflow uses actions that are not certified by GitHub.
|
|
||||||
# They are provided by a third-party and are governed by
|
|
||||||
# separate terms of service, privacy policy, and support
|
|
||||||
# documentation.
|
|
||||||
|
|
||||||
# This workflow will build, test, sign and package a WPF or Windows Forms desktop application
|
|
||||||
# built on .NET Core.
|
|
||||||
# To learn how to migrate your existing application to .NET Core,
|
|
||||||
# refer to https://docs.microsoft.com/en-us/dotnet/desktop-wpf/migration/convert-project-from-net-framework
|
|
||||||
#
|
|
||||||
# To configure this workflow:
|
|
||||||
#
|
|
||||||
# 1. Configure environment variables
|
|
||||||
# GitHub sets default environment variables for every workflow run.
|
|
||||||
# Replace the variables relative to your project in the "env" section below.
|
|
||||||
#
|
|
||||||
# 2. Signing
|
|
||||||
# Generate a signing certificate in the Windows Application
|
|
||||||
# Packaging Project or add an existing signing certificate to the project.
|
|
||||||
# Next, use PowerShell to encode the .pfx file using Base64 encoding
|
|
||||||
# by running the following Powershell script to generate the output string:
|
|
||||||
#
|
|
||||||
# $pfx_cert = Get-Content '.\SigningCertificate.pfx' -Encoding Byte
|
|
||||||
# [System.Convert]::ToBase64String($pfx_cert) | Out-File 'SigningCertificate_Encoded.txt'
|
|
||||||
#
|
|
||||||
# Open the output file, SigningCertificate_Encoded.txt, and copy the
|
|
||||||
# string inside. Then, add the string to the repo as a GitHub secret
|
|
||||||
# and name it "Base64_Encoded_Pfx."
|
|
||||||
# For more information on how to configure your signing certificate for
|
|
||||||
# this workflow, refer to https://github.com/microsoft/github-actions-for-desktop-apps#signing
|
|
||||||
#
|
|
||||||
# Finally, add the signing certificate password to the repo as a secret and name it "Pfx_Key".
|
|
||||||
# See "Build the Windows Application Packaging project" below to see how the secret is used.
|
|
||||||
#
|
|
||||||
# For more information on GitHub Actions, refer to https://github.com/features/actions
|
|
||||||
# For a complete CI/CD sample to get started with GitHub Action workflows for Desktop Applications,
|
|
||||||
# refer to https://github.com/microsoft/github-actions-for-desktop-apps
|
|
||||||
|
|
||||||
name: .NET Core Desktop
|
|
||||||
|
|
||||||
on:
|
|
||||||
push:
|
|
||||||
branches: [ "master" ]
|
|
||||||
pull_request:
|
|
||||||
branches: [ "master" ]
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
|
|
||||||
build:
|
|
||||||
|
|
||||||
strategy:
|
|
||||||
matrix:
|
|
||||||
configuration: [Release]
|
|
||||||
|
|
||||||
runs-on: windows-latest # For a list of available runner types, refer to
|
|
||||||
# https://help.github.com/en/actions/reference/workflow-syntax-for-github-actions#jobsjob_idruns-on
|
|
||||||
|
|
||||||
env:
|
|
||||||
Solution_Name: v2rayN\v2rayN.sln
|
|
||||||
#Test_Project_Path: your-test-project-path # Replace with the path to your test project, i.e. MyWpfApp.Tests\MyWpfApp.Tests.csproj.
|
|
||||||
Wap_Project_Directory: v2rayN\v2rayN\bin
|
|
||||||
#Wap_Project_Path: your-wap-project-path # Replace with the path to your Wap project, i.e. MyWpf.App.Package\MyWpfApp.Package.wapproj.
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- name: Checkout
|
|
||||||
uses: actions/checkout@v3
|
|
||||||
with:
|
|
||||||
fetch-depth: 0
|
|
||||||
|
|
||||||
# Install the .NET Core workload
|
|
||||||
- name: Install .NET Core
|
|
||||||
uses: actions/setup-dotnet@v3
|
|
||||||
with:
|
|
||||||
dotnet-version: 6.0.x
|
|
||||||
|
|
||||||
# Add MSBuild to the PATH: https://github.com/microsoft/setup-msbuild
|
|
||||||
- name: Setup MSBuild.exe
|
|
||||||
uses: microsoft/setup-msbuild@v1.0.2
|
|
||||||
|
|
||||||
# Restore the application to populate the obj folder with RuntimeIdentifiers
|
|
||||||
- name: Restore the application
|
|
||||||
run: msbuild $env:Solution_Name /t:Restore /p:Configuration=$env:Configuration
|
|
||||||
env:
|
|
||||||
Configuration: ${{ matrix.configuration }}
|
|
||||||
|
|
||||||
|
|
||||||
# Create the app package by building and packaging the Windows Application Packaging project
|
|
||||||
- name: Create the app package
|
|
||||||
run: msbuild $env:Solution_Name /p:Configuration=$env:Configuration
|
|
||||||
env:
|
|
||||||
Appx_Bundle: Always
|
|
||||||
Appx_Bundle_Platforms: x86|x64
|
|
||||||
Appx_Package_Build_Mode: StoreUpload
|
|
||||||
Configuration: ${{ matrix.configuration }}
|
|
||||||
|
|
||||||
- name: check output
|
|
||||||
run: ls ${{ env.Wap_Project_Directory }}
|
|
||||||
env:
|
|
||||||
Configuration: ${{ matrix.configuration }}
|
|
||||||
|
|
||||||
# Upload the MSIX package: https://github.com/marketplace/actions/upload-a-build-artifact
|
|
||||||
- name: Upload build artifacts
|
|
||||||
uses: actions/upload-artifact@v3
|
|
||||||
with:
|
|
||||||
name: MSIX Package
|
|
||||||
path: ${{ env.Wap_Project_Directory }}\Release\net6.0-windows
|
|
||||||
39
v2rayN/build.ps1
Normal file
39
v2rayN/build.ps1
Normal file
@@ -0,0 +1,39 @@
|
|||||||
|
param (
|
||||||
|
[Parameter()]
|
||||||
|
[ValidateNotNullOrEmpty()]
|
||||||
|
[string]
|
||||||
|
$OutputPath = '.\bin\v2rayN'
|
||||||
|
)
|
||||||
|
|
||||||
|
Write-Host 'Building'
|
||||||
|
|
||||||
|
dotnet publish `
|
||||||
|
.\v2rayN\v2rayN.csproj `
|
||||||
|
-c Release `
|
||||||
|
--self-contained false `
|
||||||
|
-p:PublishReadyToRun=true `
|
||||||
|
-p:PublishSingleFile=true `
|
||||||
|
-o $OutputPath
|
||||||
|
|
||||||
|
dotnet publish `
|
||||||
|
.\v2rayUpgrade\v2rayUpgrade.csproj `
|
||||||
|
-c Release `
|
||||||
|
--self-contained false `
|
||||||
|
-p:PublishReadyToRun=true `
|
||||||
|
-p:PublishSingleFile=true `
|
||||||
|
-o $OutputPath
|
||||||
|
|
||||||
|
if ( -Not $? ) {
|
||||||
|
exit $lastExitCode
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( Test-Path -Path .\bin\v2rayN ) {
|
||||||
|
rm -Force "$OutputPath\*.pdb"
|
||||||
|
rm -Force "$OutputPath\*.xml"
|
||||||
|
}
|
||||||
|
|
||||||
|
Write-Host 'Build done'
|
||||||
|
|
||||||
|
ls $OutputPath
|
||||||
|
7z a v2rayN.zip $OutputPath
|
||||||
|
exit 0
|
||||||
@@ -74,6 +74,9 @@
|
|||||||
public const string vlessProtocolLite = "vless";
|
public const string vlessProtocolLite = "vless";
|
||||||
public const string trojanProtocol = "trojan://";
|
public const string trojanProtocol = "trojan://";
|
||||||
public const string trojanProtocolLite = "trojan";
|
public const string trojanProtocolLite = "trojan";
|
||||||
|
public const string hysteria2Protocol = "hysteria2://";
|
||||||
|
public const string hysteria2Protocol2 = "hy2://";
|
||||||
|
public const string hysteria2ProtocolLite = "hysteria2";
|
||||||
|
|
||||||
public const string userEMail = "t@t.tt";
|
public const string userEMail = "t@t.tt";
|
||||||
public const string MyRegPath = "Software\\v2rayNGUI";
|
public const string MyRegPath = "Software\\v2rayNGUI";
|
||||||
@@ -154,7 +157,7 @@
|
|||||||
public static readonly List<string> allowInsecures = new() { "true", "false", "" };
|
public static readonly List<string> allowInsecures = new() { "true", "false", "" };
|
||||||
public static readonly List<string> domainStrategy4Freedoms = new() { "AsIs", "UseIP", "UseIPv4", "UseIPv6", "" };
|
public static readonly List<string> domainStrategy4Freedoms = new() { "AsIs", "UseIP", "UseIPv4", "UseIPv6", "" };
|
||||||
public static readonly List<string> Languages = new() { "zh-Hans", "zh-Hant", "en", "fa-Ir", "ru" };
|
public static readonly List<string> Languages = new() { "zh-Hans", "zh-Hant", "en", "fa-Ir", "ru" };
|
||||||
public static readonly List<string> alpns = new() { "h2", "http/1.1", "h2,http/1.1", "" };
|
public static readonly List<string> alpns = new() { "h2", "http/1.1", "h2,http/1.1", "h3", "" };
|
||||||
public static readonly List<string> LogLevel = new() { "debug", "info", "warning", "error", "none" };
|
public static readonly List<string> LogLevel = new() { "debug", "info", "warning", "error", "none" };
|
||||||
public static readonly List<string> InboundTags = new() { "socks", "http", "socks2", "http2" };
|
public static readonly List<string> InboundTags = new() { "socks", "http", "socks2", "http2" };
|
||||||
public static readonly List<string> Protocols = new() { "http", "tls", "bittorrent" };
|
public static readonly List<string> Protocols = new() { "http", "tls", "bittorrent" };
|
||||||
|
|||||||
@@ -184,9 +184,9 @@ namespace v2rayN.Handler
|
|||||||
config.speedTestItem.speedPingTestUrl = Global.SpeedPingTestUrl;
|
config.speedTestItem.speedPingTestUrl = Global.SpeedPingTestUrl;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (config.mux4Sbox == null)
|
if (config.mux4SboxItem == null)
|
||||||
{
|
{
|
||||||
config.mux4Sbox = new()
|
config.mux4SboxItem = new()
|
||||||
{
|
{
|
||||||
protocol = Global.SingboxMuxs[0],
|
protocol = Global.SingboxMuxs[0],
|
||||||
max_connections = 4,
|
max_connections = 4,
|
||||||
@@ -196,6 +196,15 @@ namespace v2rayN.Handler
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (config.hysteriaItem == null)
|
||||||
|
{
|
||||||
|
config.hysteriaItem = new()
|
||||||
|
{
|
||||||
|
up_mbps = 100,
|
||||||
|
down_mbps = 100
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
LazyConfig.Instance.SetConfig(config);
|
LazyConfig.Instance.SetConfig(config);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -347,7 +356,7 @@ namespace v2rayN.Handler
|
|||||||
#region Server
|
#region Server
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -603,7 +612,7 @@ namespace v2rayN.Handler
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -623,7 +632,7 @@ namespace v2rayN.Handler
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -651,7 +660,7 @@ namespace v2rayN.Handler
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -668,7 +677,7 @@ namespace v2rayN.Handler
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -693,6 +702,33 @@ namespace v2rayN.Handler
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Add or edit server
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="config"></param>
|
||||||
|
/// <param name="profileItem"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public static int AddHysteria2Server(ref Config config, ProfileItem profileItem, bool toFile = true)
|
||||||
|
{
|
||||||
|
profileItem.configType = EConfigType.Hysteria2;
|
||||||
|
profileItem.coreType = ECoreType.sing_box;
|
||||||
|
|
||||||
|
profileItem.address = profileItem.address.TrimEx();
|
||||||
|
profileItem.id = profileItem.id.TrimEx();
|
||||||
|
if (Utils.IsNullOrEmpty(profileItem.streamSecurity))
|
||||||
|
{
|
||||||
|
profileItem.streamSecurity = Global.StreamSecurity;
|
||||||
|
}
|
||||||
|
if (profileItem.id.IsNullOrEmpty())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
AddServerCommon(ref config, profileItem, toFile);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
public static int SortServers(ref Config config, string subId, string colName, bool asc)
|
public static int SortServers(ref Config config, string subId, string colName, bool asc)
|
||||||
{
|
{
|
||||||
var lstModel = LazyConfig.Instance.ProfileItems(subId, "");
|
var lstModel = LazyConfig.Instance.ProfileItems(subId, "");
|
||||||
@@ -790,7 +826,7 @@ namespace v2rayN.Handler
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// 添加服务器或编辑
|
/// Add or edit server
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="config"></param>
|
/// <param name="config"></param>
|
||||||
/// <param name="profileItem"></param>
|
/// <param name="profileItem"></param>
|
||||||
@@ -856,7 +892,7 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
profileItem.allowInsecure = config.coreBasicItem.defAllowInsecure.ToString().ToLower();
|
profileItem.allowInsecure = config.coreBasicItem.defAllowInsecure.ToString().ToLower();
|
||||||
}
|
}
|
||||||
if (Utils.IsNullOrEmpty(profileItem.fingerprint))
|
if (Utils.IsNullOrEmpty(profileItem.fingerprint) && profileItem.streamSecurity == Global.StreamSecurityReality)
|
||||||
{
|
{
|
||||||
profileItem.fingerprint = config.coreBasicItem.defFingerprint;
|
profileItem.fingerprint = config.coreBasicItem.defFingerprint;
|
||||||
}
|
}
|
||||||
@@ -1042,6 +1078,10 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
addStatus = AddVlessServer(ref config, profileItem, false);
|
addStatus = AddVlessServer(ref config, profileItem, false);
|
||||||
}
|
}
|
||||||
|
else if (profileItem.configType == EConfigType.Hysteria2)
|
||||||
|
{
|
||||||
|
addStatus = AddHysteria2Server(ref config, profileItem, false);
|
||||||
|
}
|
||||||
|
|
||||||
if (addStatus == 0)
|
if (addStatus == 0)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -283,6 +283,17 @@ namespace v2rayN.Handler
|
|||||||
|
|
||||||
outboundMux(node, outbound);
|
outboundMux(node, outbound);
|
||||||
}
|
}
|
||||||
|
else if (node.configType == EConfigType.Hysteria2)
|
||||||
|
{
|
||||||
|
outbound.type = Global.hysteria2ProtocolLite;
|
||||||
|
|
||||||
|
outbound.password = node.id;
|
||||||
|
|
||||||
|
outbound.up_mbps = _config.hysteriaItem.up_mbps > 0 ? _config.hysteriaItem.up_mbps : null;
|
||||||
|
outbound.down_mbps = _config.hysteriaItem.down_mbps > 0 ? _config.hysteriaItem.down_mbps : null;
|
||||||
|
|
||||||
|
outboundMux(node, outbound);
|
||||||
|
}
|
||||||
|
|
||||||
outboundTls(node, outbound);
|
outboundTls(node, outbound);
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
using System.Net;
|
using Newtonsoft.Json.Linq;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
using System.Net.NetworkInformation;
|
using System.Net.NetworkInformation;
|
||||||
using v2rayN.Base;
|
using v2rayN.Base;
|
||||||
using v2rayN.Mode;
|
using v2rayN.Mode;
|
||||||
@@ -718,29 +720,50 @@ namespace v2rayN.Handler
|
|||||||
outbound.settings.userLevel = 0;
|
outbound.settings.userLevel = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
var obj = Utils.ParseJson(normalDNS);
|
var obj = Utils.ParseJson(normalDNS) ?? new JObject();
|
||||||
if (obj?.ContainsKey("servers") == true)
|
|
||||||
{
|
if (!obj.ContainsKey("servers"))
|
||||||
v2rayConfig.dns = obj;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
List<string> servers = new();
|
List<string> servers = new();
|
||||||
|
|
||||||
string[] arrDNS = normalDNS.Split(',');
|
string[] arrDNS = normalDNS.Split(',');
|
||||||
foreach (string str in arrDNS)
|
foreach (string str in arrDNS)
|
||||||
{
|
{
|
||||||
//if (Utils.IsIP(str))
|
|
||||||
//{
|
|
||||||
servers.Add(str);
|
servers.Add(str);
|
||||||
//}
|
|
||||||
}
|
}
|
||||||
//servers.Add("localhost");
|
obj["servers"] = JArray.FromObject(servers);
|
||||||
v2rayConfig.dns = new Mode.Dns4Ray
|
}
|
||||||
|
|
||||||
|
if (item.useSystemHosts)
|
||||||
{
|
{
|
||||||
servers = servers
|
var hostfile = @"C:\Windows\System32\drivers\etc\hosts";
|
||||||
};
|
|
||||||
|
if (File.Exists(hostfile))
|
||||||
|
{
|
||||||
|
var hosts = File.ReadAllText(hostfile).Replace("\r", "");
|
||||||
|
var hostsList = hosts.Split(new[] { '\n' }, StringSplitOptions.RemoveEmptyEntries);
|
||||||
|
|
||||||
|
// 获取系统hosts
|
||||||
|
var systemHosts = new Dictionary<string, string>();
|
||||||
|
foreach (var host in hostsList)
|
||||||
|
{
|
||||||
|
if (host.StartsWith("#")) continue;
|
||||||
|
var hostItem = host.Split(new[] { ' ', '\t' }, StringSplitOptions.RemoveEmptyEntries);
|
||||||
|
if (hostItem.Length < 2) continue;
|
||||||
|
systemHosts.Add(hostItem[1], hostItem[0]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 追加至 dns 设置
|
||||||
|
var normalHost = obj["hosts"] ?? new JObject();
|
||||||
|
foreach (var host in systemHosts)
|
||||||
|
{
|
||||||
|
if (normalHost[host.Key] != null) continue;
|
||||||
|
normalHost[host.Key] = host.Value;
|
||||||
|
}
|
||||||
|
obj["hosts"] = normalHost;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
v2rayConfig.dns = obj;
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -62,7 +62,6 @@ namespace v2rayN.Handler
|
|||||||
Utils.SaveLog("Tun mode restart the core once");
|
Utils.SaveLog("Tun mode restart the core once");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,37 +1,68 @@
|
|||||||
using Microsoft.Win32;
|
using Microsoft.Win32;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
using static v2rayN.Handler.ProxySetting.InternetConnectionOption;
|
||||||
|
|
||||||
namespace v2rayN.Handler
|
namespace v2rayN.Handler
|
||||||
{
|
{
|
||||||
internal class ProxySetting
|
internal class ProxySetting
|
||||||
{
|
{
|
||||||
|
/// <summary>
|
||||||
|
// set to use no proxy
|
||||||
|
/// </summary>
|
||||||
|
/// <exception cref="ApplicationException">Error message with win32 error code</exception>
|
||||||
public static bool UnsetProxy()
|
public static bool UnsetProxy()
|
||||||
{
|
{
|
||||||
return SetProxy(null, null, 1);
|
return SetProxy(null, null, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Set system proxy settings
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="strProxy"> proxy address</param>
|
||||||
|
/// <param name="exceptions">exception addresses that do not use proxy</param>
|
||||||
|
/// <param name="type">type of proxy defined in PerConnFlags
|
||||||
|
/// PROXY_TYPE_DIRECT = 0x00000001, // direct connection (no proxy)
|
||||||
|
/// PROXY_TYPE_PROXY = 0x00000002, // via named proxy
|
||||||
|
/// PROXY_TYPE_AUTO_PROXY_URL = 0x00000004, // autoproxy script URL
|
||||||
|
/// PROXY_TYPE_AUTO_DETECT = 0x00000008 // use autoproxy detection
|
||||||
|
/// </param>
|
||||||
|
/// <exception cref="ApplicationException">Error message with win32 error code</exception>
|
||||||
|
/// <returns>true: one of connnection is successfully updated proxy settings</returns>
|
||||||
public static bool SetProxy(string? strProxy, string? exceptions, int type)
|
public static bool SetProxy(string? strProxy, string? exceptions, int type)
|
||||||
|
{
|
||||||
|
// set proxy for LAN
|
||||||
|
bool result = SetConnectionProxy(null, strProxy, exceptions, type);
|
||||||
|
// set proxy for dial up connections
|
||||||
|
var connections = EnumerateRasEntries();
|
||||||
|
foreach (var connection in connections)
|
||||||
|
{
|
||||||
|
result |= SetConnectionProxy(connection, strProxy, exceptions, type);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static bool SetConnectionProxy(string? connectionName, string? strProxy, string? exceptions, int type)
|
||||||
{
|
{
|
||||||
InternetPerConnOptionList list = new();
|
InternetPerConnOptionList list = new();
|
||||||
|
|
||||||
int optionCount = 1;
|
int optionCount = 1;
|
||||||
if (type == 1)
|
if (type == 1) // No proxy
|
||||||
{
|
{
|
||||||
optionCount = 1;
|
optionCount = 1;
|
||||||
}
|
}
|
||||||
else if (type is 2 or 4)
|
else if (type is 2 or 4) // named proxy or autoproxy script URL
|
||||||
{
|
{
|
||||||
optionCount = Utils.IsNullOrEmpty(exceptions) ? 2 : 3;
|
optionCount = Utils.IsNullOrEmpty(exceptions) ? 2 : 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
int m_Int = (int)PerConnFlags.PROXY_TYPE_DIRECT;
|
int m_Int = (int)PerConnFlags.PROXY_TYPE_DIRECT;
|
||||||
PerConnOption m_Option = PerConnOption.INTERNET_PER_CONN_FLAGS;
|
PerConnOption m_Option = PerConnOption.INTERNET_PER_CONN_FLAGS;
|
||||||
if (type == 2)
|
if (type == 2) // named proxy
|
||||||
{
|
{
|
||||||
m_Int = (int)(PerConnFlags.PROXY_TYPE_DIRECT | PerConnFlags.PROXY_TYPE_PROXY);
|
m_Int = (int)(PerConnFlags.PROXY_TYPE_DIRECT | PerConnFlags.PROXY_TYPE_PROXY);
|
||||||
m_Option = PerConnOption.INTERNET_PER_CONN_PROXY_SERVER;
|
m_Option = PerConnOption.INTERNET_PER_CONN_PROXY_SERVER;
|
||||||
}
|
}
|
||||||
else if (type == 4)
|
else if (type == 4) // autoproxy script url
|
||||||
{
|
{
|
||||||
m_Int = (int)(PerConnFlags.PROXY_TYPE_DIRECT | PerConnFlags.PROXY_TYPE_AUTO_PROXY_URL);
|
m_Int = (int)(PerConnFlags.PROXY_TYPE_DIRECT | PerConnFlags.PROXY_TYPE_AUTO_PROXY_URL);
|
||||||
m_Option = PerConnOption.INTERNET_PER_CONN_AUTOCONFIG_URL;
|
m_Option = PerConnOption.INTERNET_PER_CONN_AUTOCONFIG_URL;
|
||||||
@@ -47,24 +78,31 @@ namespace v2rayN.Handler
|
|||||||
if (optionCount > 1)
|
if (optionCount > 1)
|
||||||
{
|
{
|
||||||
options[1].m_Option = m_Option;
|
options[1].m_Option = m_Option;
|
||||||
options[1].m_Value.m_StringPtr = Marshal.StringToHGlobalAuto(strProxy);
|
options[1].m_Value.m_StringPtr = Marshal.StringToHGlobalAuto(strProxy); // !! remember to deallocate memory 1
|
||||||
// except for these addresses ...
|
// except for these addresses ...
|
||||||
if (optionCount > 2)
|
if (optionCount > 2)
|
||||||
{
|
{
|
||||||
options[2].m_Option = PerConnOption.INTERNET_PER_CONN_PROXY_BYPASS;
|
options[2].m_Option = PerConnOption.INTERNET_PER_CONN_PROXY_BYPASS;
|
||||||
options[2].m_Value.m_StringPtr = Marshal.StringToHGlobalAuto(exceptions);
|
options[2].m_Value.m_StringPtr = Marshal.StringToHGlobalAuto(exceptions); // !! remember to deallocate memory 2
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// default stuff
|
// default stuff
|
||||||
list.dwSize = Marshal.SizeOf(list);
|
list.dwSize = Marshal.SizeOf(list);
|
||||||
|
if (connectionName != null)
|
||||||
|
{
|
||||||
|
list.szConnection = Marshal.StringToHGlobalAuto(connectionName); // !! remember to deallocate memory 3
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
list.szConnection = IntPtr.Zero;
|
list.szConnection = IntPtr.Zero;
|
||||||
|
}
|
||||||
list.dwOptionCount = options.Length;
|
list.dwOptionCount = options.Length;
|
||||||
list.dwOptionError = 0;
|
list.dwOptionError = 0;
|
||||||
|
|
||||||
int optSize = Marshal.SizeOf(typeof(InternetConnectionOption));
|
int optSize = Marshal.SizeOf(typeof(InternetConnectionOption));
|
||||||
// make a pointer out of all that ...
|
// make a pointer out of all that ...
|
||||||
IntPtr optionsPtr = Marshal.AllocCoTaskMem(optSize * options.Length);
|
IntPtr optionsPtr = Marshal.AllocCoTaskMem(optSize * options.Length); // !! remember to deallocate memory 4
|
||||||
// copy the array over into that spot in memory ...
|
// copy the array over into that spot in memory ...
|
||||||
for (int i = 0; i < options.Length; ++i)
|
for (int i = 0; i < options.Length; ++i)
|
||||||
{
|
{
|
||||||
@@ -83,26 +121,82 @@ namespace v2rayN.Handler
|
|||||||
list.options = optionsPtr;
|
list.options = optionsPtr;
|
||||||
|
|
||||||
// and then make a pointer out of the whole list
|
// and then make a pointer out of the whole list
|
||||||
IntPtr ipcoListPtr = Marshal.AllocCoTaskMem(list.dwSize);
|
IntPtr ipcoListPtr = Marshal.AllocCoTaskMem(list.dwSize); // !! remember to deallocate memory 5
|
||||||
Marshal.StructureToPtr(list, ipcoListPtr, false);
|
Marshal.StructureToPtr(list, ipcoListPtr, false);
|
||||||
|
|
||||||
// and finally, call the API method!
|
// and finally, call the API method!
|
||||||
int returnvalue = NativeMethods.InternetSetOption(IntPtr.Zero,
|
bool isSuccess = NativeMethods.InternetSetOption(IntPtr.Zero,
|
||||||
InternetOption.INTERNET_OPTION_PER_CONNECTION_OPTION,
|
InternetOption.INTERNET_OPTION_PER_CONNECTION_OPTION,
|
||||||
ipcoListPtr, list.dwSize) ? -1 : 0;
|
ipcoListPtr, list.dwSize);
|
||||||
if (returnvalue == 0)
|
int returnvalue = 0; // ERROR_SUCCESS
|
||||||
|
if (!isSuccess)
|
||||||
{ // get the error codes, they might be helpful
|
{ // get the error codes, they might be helpful
|
||||||
returnvalue = Marshal.GetLastWin32Error();
|
returnvalue = Marshal.GetLastPInvokeError();
|
||||||
}
|
}
|
||||||
// FREE the data ASAP
|
else
|
||||||
Marshal.FreeCoTaskMem(optionsPtr);
|
{
|
||||||
Marshal.FreeCoTaskMem(ipcoListPtr);
|
// Notify the system that the registry settings have been changed and cause them to be refreshed
|
||||||
if (returnvalue > 0)
|
NativeMethods.InternetSetOption(IntPtr.Zero, InternetOption.INTERNET_OPTION_SETTINGS_CHANGED, IntPtr.Zero, 0);
|
||||||
{ // throw the error codes, they might be helpful
|
NativeMethods.InternetSetOption(IntPtr.Zero, InternetOption.INTERNET_OPTION_REFRESH, IntPtr.Zero, 0);
|
||||||
//throw new Win32Exception(Marshal.GetLastWin32Error());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return (returnvalue < 0);
|
// FREE the data ASAP
|
||||||
|
if (list.szConnection != IntPtr.Zero) Marshal.FreeHGlobal(list.szConnection); // release mem 3
|
||||||
|
if (optionCount > 1)
|
||||||
|
{
|
||||||
|
Marshal.FreeHGlobal(options[1].m_Value.m_StringPtr); // release mem 1
|
||||||
|
if (optionCount > 2)
|
||||||
|
{
|
||||||
|
Marshal.FreeHGlobal(options[2].m_Value.m_StringPtr); // release mem 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Marshal.FreeCoTaskMem(optionsPtr); // release mem 4
|
||||||
|
Marshal.FreeCoTaskMem(ipcoListPtr); // release mem 5
|
||||||
|
if (returnvalue != 0)
|
||||||
|
{
|
||||||
|
// throw the error codes, they might be helpful
|
||||||
|
throw new ApplicationException($"Set Internet Proxy failed with error code: {Marshal.GetLastWin32Error()}");
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Retrieve list of connections including LAN and WAN to support PPPoE connection
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>A list of RAS connection names. May be empty list if no dial up connection.</returns>
|
||||||
|
/// <exception cref="ApplicationException">Error message with win32 error code</exception>
|
||||||
|
private static IEnumerable<string> EnumerateRasEntries()
|
||||||
|
{
|
||||||
|
int entries = 0;
|
||||||
|
// attempt to query with 1 entry buffer
|
||||||
|
RASENTRYNAME[] rasEntryNames = new RASENTRYNAME[1];
|
||||||
|
int bufferSize = Marshal.SizeOf(typeof(RASENTRYNAME));
|
||||||
|
rasEntryNames[0].dwSize = Marshal.SizeOf(typeof(RASENTRYNAME));
|
||||||
|
|
||||||
|
uint result = NativeMethods.RasEnumEntries(null, null, rasEntryNames, ref bufferSize, ref entries);
|
||||||
|
// increase buffer if the buffer is not large enough
|
||||||
|
if (result == (uint)ErrorCode.ERROR_BUFFER_TOO_SMALL)
|
||||||
|
{
|
||||||
|
rasEntryNames = new RASENTRYNAME[bufferSize / Marshal.SizeOf(typeof(RASENTRYNAME))];
|
||||||
|
for (int i = 0; i < rasEntryNames.Length; i++)
|
||||||
|
{
|
||||||
|
rasEntryNames[i].dwSize = Marshal.SizeOf(typeof(RASENTRYNAME));
|
||||||
|
}
|
||||||
|
|
||||||
|
result = NativeMethods.RasEnumEntries(null, null, rasEntryNames, ref bufferSize, ref entries);
|
||||||
|
}
|
||||||
|
if (result == 0)
|
||||||
|
{
|
||||||
|
var entryNames = new List<string>();
|
||||||
|
for (int i = 0; i < entries; i++)
|
||||||
|
{
|
||||||
|
entryNames.Add(rasEntryNames[i].szEntryName);
|
||||||
|
}
|
||||||
|
|
||||||
|
return entryNames;
|
||||||
|
}
|
||||||
|
throw new ApplicationException($"RasEnumEntries failed with error code: {result}");
|
||||||
}
|
}
|
||||||
|
|
||||||
#region WinInet structures
|
#region WinInet structures
|
||||||
@@ -145,6 +239,25 @@ namespace v2rayN.Handler
|
|||||||
[FieldOffset(0)]
|
[FieldOffset(0)]
|
||||||
public IntPtr m_StringPtr;
|
public IntPtr m_StringPtr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
|
||||||
|
public struct RASENTRYNAME
|
||||||
|
{
|
||||||
|
public int dwSize;
|
||||||
|
|
||||||
|
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = RAS_MaxEntryName + 1)]
|
||||||
|
public string szEntryName;
|
||||||
|
|
||||||
|
public int dwFlags;
|
||||||
|
|
||||||
|
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = MAX_PATH + 1)]
|
||||||
|
public string szPhonebookPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Constants
|
||||||
|
public const int RAS_MaxEntryName = 256;
|
||||||
|
|
||||||
|
public const int MAX_PATH = 260; // Standard MAX_PATH value in Windows
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion WinInet structures
|
#endregion WinInet structures
|
||||||
@@ -156,7 +269,9 @@ namespace v2rayN.Handler
|
|||||||
//
|
//
|
||||||
public enum InternetOption : uint
|
public enum InternetOption : uint
|
||||||
{
|
{
|
||||||
INTERNET_OPTION_PER_CONNECTION_OPTION = 75
|
INTERNET_OPTION_PER_CONNECTION_OPTION = 75,
|
||||||
|
INTERNET_OPTION_REFRESH = 37,
|
||||||
|
INTERNET_OPTION_SETTINGS_CHANGED = 39
|
||||||
}
|
}
|
||||||
|
|
||||||
//
|
//
|
||||||
@@ -182,6 +297,12 @@ namespace v2rayN.Handler
|
|||||||
PROXY_TYPE_AUTO_DETECT = 0x00000008 // use autoproxy detection
|
PROXY_TYPE_AUTO_DETECT = 0x00000008 // use autoproxy detection
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public enum ErrorCode : uint
|
||||||
|
{
|
||||||
|
ERROR_BUFFER_TOO_SMALL = 603,
|
||||||
|
ERROR_INVALID_SIZE = 632
|
||||||
|
}
|
||||||
|
|
||||||
#endregion WinInet enums
|
#endregion WinInet enums
|
||||||
|
|
||||||
internal static class NativeMethods
|
internal static class NativeMethods
|
||||||
@@ -189,6 +310,15 @@ namespace v2rayN.Handler
|
|||||||
[DllImport("WinInet.dll", SetLastError = true, CharSet = CharSet.Auto)]
|
[DllImport("WinInet.dll", SetLastError = true, CharSet = CharSet.Auto)]
|
||||||
[return: MarshalAs(UnmanagedType.Bool)]
|
[return: MarshalAs(UnmanagedType.Bool)]
|
||||||
public static extern bool InternetSetOption(IntPtr hInternet, InternetOption dwOption, IntPtr lpBuffer, int dwBufferLength);
|
public static extern bool InternetSetOption(IntPtr hInternet, InternetOption dwOption, IntPtr lpBuffer, int dwBufferLength);
|
||||||
|
|
||||||
|
[DllImport("Rasapi32.dll", CharSet = CharSet.Auto)]
|
||||||
|
public static extern uint RasEnumEntries(
|
||||||
|
string? reserved, // Reserved, must be null
|
||||||
|
string? lpszPhonebook, // Pointer to full path and filename of phone-book file. If this parameter is NULL, the entries are enumerated from all the remote access phone-book files
|
||||||
|
[In, Out] RASENTRYNAME[]? lprasentryname, // Buffer to receive RAS entry names
|
||||||
|
ref int lpcb, // Size of the buffer
|
||||||
|
ref int lpcEntries // Number of entries written to the buffer
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
//判断是否使用代理
|
//判断是否使用代理
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ namespace v2rayN.Handler
|
|||||||
EConfigType.Socks => ShareSocks(item),
|
EConfigType.Socks => ShareSocks(item),
|
||||||
EConfigType.Trojan => ShareTrojan(item),
|
EConfigType.Trojan => ShareTrojan(item),
|
||||||
EConfigType.VLESS => ShareVLESS(item),
|
EConfigType.VLESS => ShareVLESS(item),
|
||||||
|
EConfigType.Hysteria2 => ShareHysteria2(item),
|
||||||
_ => null,
|
_ => null,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -162,6 +163,35 @@ namespace v2rayN.Handler
|
|||||||
return url;
|
return url;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static string ShareHysteria2(ProfileItem item)
|
||||||
|
{
|
||||||
|
string url = string.Empty;
|
||||||
|
string remark = string.Empty;
|
||||||
|
if (!Utils.IsNullOrEmpty(item.remarks))
|
||||||
|
{
|
||||||
|
remark = "#" + Utils.UrlEncode(item.remarks);
|
||||||
|
}
|
||||||
|
var dicQuery = new Dictionary<string, string>();
|
||||||
|
if (!Utils.IsNullOrEmpty(item.sni))
|
||||||
|
{
|
||||||
|
dicQuery.Add("sni", item.sni);
|
||||||
|
}
|
||||||
|
if (!Utils.IsNullOrEmpty(item.alpn))
|
||||||
|
{
|
||||||
|
dicQuery.Add("alpn", Utils.UrlEncode(item.alpn));
|
||||||
|
}
|
||||||
|
dicQuery.Add("insecure", item.allowInsecure.ToLower() == "true" ? "1" : "0");
|
||||||
|
|
||||||
|
string query = "?" + string.Join("&", dicQuery.Select(x => x.Key + "=" + x.Value).ToArray());
|
||||||
|
|
||||||
|
url = string.Format("{0}@{1}:{2}",
|
||||||
|
item.id,
|
||||||
|
GetIpv6(item.address),
|
||||||
|
item.port);
|
||||||
|
url = $"{Global.hysteria2Protocol}{url}{query}{remark}";
|
||||||
|
return url;
|
||||||
|
}
|
||||||
|
|
||||||
private static string GetIpv6(string address)
|
private static string GetIpv6(string address)
|
||||||
{
|
{
|
||||||
return Utils.IsIpv6(address) ? $"[{address}]" : address;
|
return Utils.IsIpv6(address) ? $"[{address}]" : address;
|
||||||
@@ -353,6 +383,12 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
profileItem = ResolveStdVLESS(result);
|
profileItem = ResolveStdVLESS(result);
|
||||||
}
|
}
|
||||||
|
else if (result.StartsWith(Global.hysteria2Protocol) || result.StartsWith(Global.hysteria2Protocol2))
|
||||||
|
{
|
||||||
|
msg = ResUI.ConfigurationFormatIncorrect;
|
||||||
|
|
||||||
|
profileItem = ResolveHysteria2(result);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
msg = ResUI.NonvmessOrssProtocol;
|
msg = ResUI.NonvmessOrssProtocol;
|
||||||
@@ -758,6 +794,27 @@ namespace v2rayN.Handler
|
|||||||
return item;
|
return item;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static ProfileItem ResolveHysteria2(string result)
|
||||||
|
{
|
||||||
|
ProfileItem item = new()
|
||||||
|
{
|
||||||
|
configType = EConfigType.Hysteria2
|
||||||
|
};
|
||||||
|
|
||||||
|
Uri url = new(result);
|
||||||
|
|
||||||
|
item.address = url.IdnHost;
|
||||||
|
item.port = url.Port;
|
||||||
|
item.remarks = url.GetComponents(UriComponents.Fragment, UriFormat.Unescaped);
|
||||||
|
item.id = url.UserInfo;
|
||||||
|
|
||||||
|
var query = HttpUtility.ParseQueryString(url.Query);
|
||||||
|
ResolveStdTransport(query, ref item);
|
||||||
|
item.allowInsecure = (query["insecure"] ?? "") == "1" ? "true" : "false";
|
||||||
|
|
||||||
|
return item;
|
||||||
|
}
|
||||||
|
|
||||||
private static int ResolveStdTransport(NameValueCollection query, ref ProfileItem item)
|
private static int ResolveStdTransport(NameValueCollection query, ref ProfileItem item)
|
||||||
{
|
{
|
||||||
item.flow = query["flow"] ?? "";
|
item.flow = query["flow"] ?? "";
|
||||||
|
|||||||
@@ -30,7 +30,7 @@ namespace v2rayN.Handler
|
|||||||
_selecteds = new List<ServerTestItem>();
|
_selecteds = new List<ServerTestItem>();
|
||||||
foreach (var it in selecteds)
|
foreach (var it in selecteds)
|
||||||
{
|
{
|
||||||
if (it.configType == EConfigType.Custom)
|
if (it.configType == EConfigType.Custom || it.configType == EConfigType.Hysteria2)
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,5 @@
|
|||||||
using PacLib;
|
using PacLib;
|
||||||
using System.Diagnostics;
|
|
||||||
using System.IO;
|
|
||||||
using System.Text;
|
|
||||||
using v2rayN.Mode;
|
using v2rayN.Mode;
|
||||||
using v2rayN.Properties;
|
|
||||||
using v2rayN.Tool;
|
|
||||||
|
|
||||||
namespace v2rayN.Handler
|
namespace v2rayN.Handler
|
||||||
{
|
{
|
||||||
@@ -20,7 +15,6 @@ namespace v2rayN.Handler
|
|||||||
// <proxy-server><CR-LF>
|
// <proxy-server><CR-LF>
|
||||||
// <bypass-list><CR-LF>
|
// <bypass-list><CR-LF>
|
||||||
// <pac-url>
|
// <pac-url>
|
||||||
private static SysproxyConfig? _userSettings = null;
|
|
||||||
|
|
||||||
private enum RET_ERRORS : int
|
private enum RET_ERRORS : int
|
||||||
{
|
{
|
||||||
@@ -34,15 +28,6 @@ namespace v2rayN.Handler
|
|||||||
|
|
||||||
static SysProxyHandle()
|
static SysProxyHandle()
|
||||||
{
|
{
|
||||||
try
|
|
||||||
{
|
|
||||||
FileManager.UncompressFile(Utils.GetTempPath("sysproxy.exe"),
|
|
||||||
Environment.Is64BitOperatingSystem ? Resources.sysproxy64_exe : Resources.sysproxy_exe);
|
|
||||||
}
|
|
||||||
catch (IOException ex)
|
|
||||||
{
|
|
||||||
Utils.SaveLog(ex.Message, ex);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static bool UpdateSysProxy(Config config, bool forceDisable)
|
public static bool UpdateSysProxy(Config config, bool forceDisable)
|
||||||
@@ -79,13 +64,11 @@ namespace v2rayN.Handler
|
|||||||
.Replace("{http_port}", port.ToString())
|
.Replace("{http_port}", port.ToString())
|
||||||
.Replace("{socks_port}", portSocks.ToString());
|
.Replace("{socks_port}", portSocks.ToString());
|
||||||
}
|
}
|
||||||
ProxySetting.SetProxy(strProxy, strExceptions, 2);
|
ProxySetting.SetProxy(strProxy, strExceptions, 2); // set a named proxy
|
||||||
SetIEProxy(true, strProxy, strExceptions);
|
|
||||||
}
|
}
|
||||||
else if (type == ESysProxyType.ForcedClear)
|
else if (type == ESysProxyType.ForcedClear)
|
||||||
{
|
{
|
||||||
ProxySetting.UnsetProxy();
|
ProxySetting.UnsetProxy(); // set to no proxy
|
||||||
ResetIEProxy();
|
|
||||||
}
|
}
|
||||||
else if (type == ESysProxyType.Unchanged)
|
else if (type == ESysProxyType.Unchanged)
|
||||||
{
|
{
|
||||||
@@ -94,8 +77,7 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
PacHandler.Start(Utils.GetConfigPath(), port, portPac);
|
PacHandler.Start(Utils.GetConfigPath(), port, portPac);
|
||||||
var strProxy = $"{Global.httpProtocol}{Global.Loopback}:{portPac}/pac?t={DateTime.Now.Ticks}";
|
var strProxy = $"{Global.httpProtocol}{Global.Loopback}:{portPac}/pac?t={DateTime.Now.Ticks}";
|
||||||
ProxySetting.SetProxy(strProxy, "", 4);
|
ProxySetting.SetProxy(strProxy, "", 4); // use pac script url for auto-config proxy
|
||||||
SetIEProxy(false, strProxy, "");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (type != ESysProxyType.Pac)
|
if (type != ESysProxyType.Pac)
|
||||||
@@ -121,102 +103,5 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void SetIEProxy(bool global, string strProxy, string strExceptions)
|
|
||||||
{
|
|
||||||
string arguments = global
|
|
||||||
? $"global {strProxy} {strExceptions}"
|
|
||||||
: $"pac {strProxy}";
|
|
||||||
|
|
||||||
ExecSysproxy(arguments);
|
|
||||||
}
|
|
||||||
|
|
||||||
// set system proxy to 1 (null) (null) (null)
|
|
||||||
public static void ResetIEProxy()
|
|
||||||
{
|
|
||||||
ExecSysproxy("set 1 - - -");
|
|
||||||
}
|
|
||||||
|
|
||||||
private static void ExecSysproxy(string arguments)
|
|
||||||
{
|
|
||||||
// using event to avoid hanging when redirect standard output/error
|
|
||||||
// ref: https://stackoverflow.com/questions/139593/processstartinfo-hanging-on-waitforexit-why
|
|
||||||
// and http://blog.csdn.net/zhangweixing0/article/details/7356841
|
|
||||||
using AutoResetEvent outputWaitHandle = new(false);
|
|
||||||
using AutoResetEvent errorWaitHandle = new(false);
|
|
||||||
using Process process = new();
|
|
||||||
|
|
||||||
// Configure the process using the StartInfo properties.
|
|
||||||
process.StartInfo.FileName = Utils.GetTempPath("sysproxy.exe");
|
|
||||||
process.StartInfo.Arguments = arguments;
|
|
||||||
process.StartInfo.WorkingDirectory = Utils.GetTempPath();
|
|
||||||
process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
|
|
||||||
process.StartInfo.UseShellExecute = false;
|
|
||||||
process.StartInfo.RedirectStandardError = true;
|
|
||||||
process.StartInfo.RedirectStandardOutput = true;
|
|
||||||
|
|
||||||
// Need to provide encoding info, or output/error strings we got will be wrong.
|
|
||||||
process.StartInfo.StandardOutputEncoding = Encoding.Unicode;
|
|
||||||
process.StartInfo.StandardErrorEncoding = Encoding.Unicode;
|
|
||||||
|
|
||||||
process.StartInfo.CreateNoWindow = true;
|
|
||||||
|
|
||||||
StringBuilder output = new(1024);
|
|
||||||
StringBuilder error = new(1024);
|
|
||||||
|
|
||||||
process.OutputDataReceived += (sender, e) =>
|
|
||||||
{
|
|
||||||
if (e.Data == null)
|
|
||||||
{
|
|
||||||
outputWaitHandle.Set();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
output.AppendLine(e.Data);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
process.ErrorDataReceived += (sender, e) =>
|
|
||||||
{
|
|
||||||
if (e.Data == null)
|
|
||||||
{
|
|
||||||
errorWaitHandle.Set();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
error.AppendLine(e.Data);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
try
|
|
||||||
{
|
|
||||||
process.Start();
|
|
||||||
|
|
||||||
process.BeginErrorReadLine();
|
|
||||||
process.BeginOutputReadLine();
|
|
||||||
|
|
||||||
process.WaitForExit();
|
|
||||||
}
|
|
||||||
catch (System.ComponentModel.Win32Exception e)
|
|
||||||
{
|
|
||||||
// log the arguments
|
|
||||||
throw new Exception(process.StartInfo.Arguments);
|
|
||||||
}
|
|
||||||
string stderr = error.ToString();
|
|
||||||
string stdout = output.ToString();
|
|
||||||
|
|
||||||
int exitCode = process.ExitCode;
|
|
||||||
if (exitCode != (int)RET_ERRORS.RET_NO_ERROR)
|
|
||||||
{
|
|
||||||
throw new Exception(stderr);
|
|
||||||
}
|
|
||||||
|
|
||||||
//if (arguments == "query")
|
|
||||||
//{
|
|
||||||
// if (stdout.IsNullOrWhiteSpace() || stdout.IsNullOrEmpty())
|
|
||||||
// {
|
|
||||||
// throw new Exception("failed to query wininet settings");
|
|
||||||
// }
|
|
||||||
// _queryStr = stdout;
|
|
||||||
//}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -24,11 +24,13 @@ namespace v2rayN.Handler
|
|||||||
{
|
{
|
||||||
public bool Success;
|
public bool Success;
|
||||||
public string Msg;
|
public string Msg;
|
||||||
|
public string Url;
|
||||||
|
|
||||||
public ResultEventArgs(bool success, string msg)
|
public ResultEventArgs(bool success, string msg, string url = "")
|
||||||
{
|
{
|
||||||
Success = success;
|
Success = success;
|
||||||
Msg = msg;
|
Msg = msg;
|
||||||
|
Url = url;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -83,8 +85,9 @@ namespace v2rayN.Handler
|
|||||||
if (args.Success)
|
if (args.Success)
|
||||||
{
|
{
|
||||||
_updateFunc(false, string.Format(ResUI.MsgParsingSuccessfully, "v2rayN"));
|
_updateFunc(false, string.Format(ResUI.MsgParsingSuccessfully, "v2rayN"));
|
||||||
|
_updateFunc(false, args.Msg);
|
||||||
|
|
||||||
url = args.Msg;
|
url = args.Url;
|
||||||
_ = askToDownload(downloadHandle, url, true);
|
_ = askToDownload(downloadHandle, url, true);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -135,7 +138,9 @@ namespace v2rayN.Handler
|
|||||||
if (args.Success)
|
if (args.Success)
|
||||||
{
|
{
|
||||||
_updateFunc(false, string.Format(ResUI.MsgParsingSuccessfully, "Core"));
|
_updateFunc(false, string.Format(ResUI.MsgParsingSuccessfully, "Core"));
|
||||||
url = args.Msg;
|
_updateFunc(false, args.Msg);
|
||||||
|
|
||||||
|
url = args.Url;
|
||||||
_ = askToDownload(downloadHandle, url, true);
|
_ = askToDownload(downloadHandle, url, true);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@@ -405,15 +410,10 @@ namespace v2rayN.Handler
|
|||||||
try
|
try
|
||||||
{
|
{
|
||||||
var gitHubReleases = Utils.FromJson<List<GitHubRelease>>(gitHubReleaseApi);
|
var gitHubReleases = Utils.FromJson<List<GitHubRelease>>(gitHubReleaseApi);
|
||||||
SemanticVersion version;
|
var gitHubRelease = preRelease ? gitHubReleases!.First() : gitHubReleases!.First(r => r.Prerelease == false);
|
||||||
if (preRelease)
|
var version = new SemanticVersion(gitHubRelease!.TagName);
|
||||||
{
|
var body = gitHubRelease!.Body;
|
||||||
version = new SemanticVersion(gitHubReleases!.First().TagName);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
version = new SemanticVersion(gitHubReleases!.First(r => r.Prerelease == false).TagName);
|
|
||||||
}
|
|
||||||
var coreInfo = LazyConfig.Instance.GetCoreInfo(type);
|
var coreInfo = LazyConfig.Instance.GetCoreInfo(type);
|
||||||
|
|
||||||
SemanticVersion curVersion;
|
SemanticVersion curVersion;
|
||||||
@@ -520,7 +520,7 @@ namespace v2rayN.Handler
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
AbsoluteCompleted?.Invoke(this, new ResultEventArgs(true, url));
|
AbsoluteCompleted?.Invoke(this, new ResultEventArgs(true, body, url));
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
@@ -603,7 +603,7 @@ namespace v2rayN.Handler
|
|||||||
var url = string.Format(Global.singboxGeoUrl, geoName);
|
var url = string.Format(Global.singboxGeoUrl, geoName);
|
||||||
|
|
||||||
DownloadHandle downloadHandle = new();
|
DownloadHandle downloadHandle = new();
|
||||||
downloadHandle.UpdateCompleted += (sender2, args) =>
|
downloadHandle.UpdateCompleted += async (sender2, args) =>
|
||||||
{
|
{
|
||||||
if (args.Success)
|
if (args.Success)
|
||||||
{
|
{
|
||||||
@@ -612,8 +612,11 @@ namespace v2rayN.Handler
|
|||||||
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
if (needStop) coreHandler?.CoreStop();
|
if (needStop)
|
||||||
Task.Delay(1000);
|
{
|
||||||
|
coreHandler?.CoreStop();
|
||||||
|
await Task.Delay(3000);
|
||||||
|
}
|
||||||
string fileName = Utils.GetTempPath(Utils.GetDownloadFileName(url));
|
string fileName = Utils.GetTempPath(Utils.GetDownloadFileName(url));
|
||||||
if (File.Exists(fileName))
|
if (File.Exists(fileName))
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -27,7 +27,8 @@
|
|||||||
public UIItem uiItem { get; set; }
|
public UIItem uiItem { get; set; }
|
||||||
public ConstItem constItem { get; set; }
|
public ConstItem constItem { get; set; }
|
||||||
public SpeedTestItem speedTestItem { get; set; }
|
public SpeedTestItem speedTestItem { get; set; }
|
||||||
public Mux4Sbox mux4Sbox { get; set; }
|
public Mux4SboxItem mux4SboxItem { get; set; }
|
||||||
|
public HysteriaItem hysteriaItem { get; set; }
|
||||||
public List<InItem> inbound { get; set; }
|
public List<InItem> inbound { get; set; }
|
||||||
public List<KeyEventItem> globalHotkeys { get; set; }
|
public List<KeyEventItem> globalHotkeys { get; set; }
|
||||||
public List<CoreTypeItem> coreTypeItem { get; set; }
|
public List<CoreTypeItem> coreTypeItem { get; set; }
|
||||||
|
|||||||
@@ -198,7 +198,7 @@ namespace v2rayN.Mode
|
|||||||
}
|
}
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class Mux4Sbox
|
public class Mux4SboxItem
|
||||||
{
|
{
|
||||||
public string protocol { get; set; }
|
public string protocol { get; set; }
|
||||||
public int max_connections { get; set; }
|
public int max_connections { get; set; }
|
||||||
@@ -206,4 +206,11 @@ namespace v2rayN.Mode
|
|||||||
public int max_streams { get; set; }
|
public int max_streams { get; set; }
|
||||||
public bool padding { get; set; }
|
public bool padding { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Serializable]
|
||||||
|
public class HysteriaItem
|
||||||
|
{
|
||||||
|
public int up_mbps { get; set; }
|
||||||
|
public int down_mbps { get; set; }
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -11,6 +11,7 @@ namespace v2rayN.Mode
|
|||||||
public string remarks { get; set; }
|
public string remarks { get; set; }
|
||||||
public bool enabled { get; set; } = true;
|
public bool enabled { get; set; } = true;
|
||||||
public ECoreType coreType { get; set; }
|
public ECoreType coreType { get; set; }
|
||||||
|
public bool useSystemHosts { get; set; }
|
||||||
public string? normalDNS { get; set; }
|
public string? normalDNS { get; set; }
|
||||||
public string? tunDNS { get; set; }
|
public string? tunDNS { get; set; }
|
||||||
public string? domainStrategy4Freedom { get; set; }
|
public string? domainStrategy4Freedom { get; set; }
|
||||||
|
|||||||
@@ -7,6 +7,7 @@
|
|||||||
Shadowsocks = 3,
|
Shadowsocks = 3,
|
||||||
Socks = 4,
|
Socks = 4,
|
||||||
VLESS = 5,
|
VLESS = 5,
|
||||||
Trojan = 6
|
Trojan = 6,
|
||||||
|
Hysteria2 = 7
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -53,6 +53,7 @@ namespace v2rayN.Mode
|
|||||||
case EConfigType.Socks:
|
case EConfigType.Socks:
|
||||||
case EConfigType.VLESS:
|
case EConfigType.VLESS:
|
||||||
case EConfigType.Trojan:
|
case EConfigType.Trojan:
|
||||||
|
case EConfigType.Hysteria2:
|
||||||
summary += string.Format("{0}({1}:{2})", remarks, addr, port);
|
summary += string.Format("{0}({1}:{2})", remarks, addr, port);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|||||||
20
v2rayN/v2rayN/Properties/Resources.Designer.cs
generated
20
v2rayN/v2rayN/Properties/Resources.Designer.cs
generated
@@ -219,25 +219,5 @@ namespace v2rayN.Properties {
|
|||||||
return ((System.Drawing.Bitmap)(obj));
|
return ((System.Drawing.Bitmap)(obj));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// 查找 System.Byte[] 类型的本地化资源。
|
|
||||||
/// </summary>
|
|
||||||
internal static byte[] sysproxy_exe {
|
|
||||||
get {
|
|
||||||
object obj = ResourceManager.GetObject("sysproxy_exe", resourceCulture);
|
|
||||||
return ((byte[])(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// 查找 System.Byte[] 类型的本地化资源。
|
|
||||||
/// </summary>
|
|
||||||
internal static byte[] sysproxy64_exe {
|
|
||||||
get {
|
|
||||||
object obj = ResourceManager.GetObject("sysproxy64_exe", resourceCulture);
|
|
||||||
return ((byte[])(obj));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -118,12 +118,6 @@
|
|||||||
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
||||||
</resheader>
|
</resheader>
|
||||||
<assembly alias="System.Windows.Forms" name="System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
|
<assembly alias="System.Windows.Forms" name="System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" />
|
||||||
<data name="sysproxy_exe" type="System.Resources.ResXFileRef, System.Windows.Forms">
|
|
||||||
<value>..\resources\sysproxy.exe.gz;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
|
||||||
</data>
|
|
||||||
<data name="sysproxy64_exe" type="System.Resources.ResXFileRef, System.Windows.Forms">
|
|
||||||
<value>..\resources\sysproxy64.exe.gz;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
|
|
||||||
</data>
|
|
||||||
<data name="NotifyIcon1" type="System.Resources.ResXFileRef, System.Windows.Forms">
|
<data name="NotifyIcon1" type="System.Resources.ResXFileRef, System.Windows.Forms">
|
||||||
<value>..\Resources\NotifyIcon1.ico;System.Drawing.Icon, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
|
<value>..\Resources\NotifyIcon1.ico;System.Drawing.Icon, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
|
||||||
</data>
|
</data>
|
||||||
|
|||||||
Binary file not shown.
Binary file not shown.
35
v2rayN/v2rayN/Resx/ResUI.Designer.cs
generated
35
v2rayN/v2rayN/Resx/ResUI.Designer.cs
generated
@@ -321,7 +321,7 @@ namespace v2rayN.Resx {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to {0} already up to date..
|
/// Looks up a localized string similar to {0} {1} already up to date..
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static string IsLatestCore {
|
public static string IsLatestCore {
|
||||||
get {
|
get {
|
||||||
@@ -330,7 +330,7 @@ namespace v2rayN.Resx {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to {0} already up to date..
|
/// Looks up a localized string similar to {0} {1} already up to date..
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static string IsLatestN {
|
public static string IsLatestN {
|
||||||
get {
|
get {
|
||||||
@@ -590,6 +590,15 @@ namespace v2rayN.Resx {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Add [Trojan] server.
|
||||||
|
/// </summary>
|
||||||
|
public static string menuAddHysteria2Server {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("menuAddHysteria2Server", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to Import bulk URL from clipboard (Ctrl+V).
|
/// Looks up a localized string similar to Import bulk URL from clipboard (Ctrl+V).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@@ -2295,9 +2304,9 @@ namespace v2rayN.Resx {
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to Click to import default DNS config.
|
/// Looks up a localized string similar to Click to import default DNS config.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public static string TBSettingDnsImportDefConfig {
|
public static string TbSettingDnsImportDefConfig {
|
||||||
get {
|
get {
|
||||||
return ResourceManager.GetString("TBSettingDnsImportDefConfig", resourceCulture);
|
return ResourceManager.GetString("TbSettingDnsImportDefConfig", resourceCulture);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2553,6 +2562,15 @@ namespace v2rayN.Resx {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Hysteria Max bandwidth (Up/Dw).
|
||||||
|
/// </summary>
|
||||||
|
public static string TbSettingsHysteriaBandwidth {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("TbSettingsHysteriaBandwidth", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to Ignore Geo files when updating core.
|
/// Looks up a localized string similar to Ignore Geo files when updating core.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@@ -2886,6 +2904,15 @@ namespace v2rayN.Resx {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Looks up a localized string similar to Use System Hosts.
|
||||||
|
/// </summary>
|
||||||
|
public static string TbSettingsUseSystemHosts {
|
||||||
|
get {
|
||||||
|
return ResourceManager.GetString("TbSettingsUseSystemHosts", resourceCulture);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Looks up a localized string similar to ShortId.
|
/// Looks up a localized string similar to ShortId.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|||||||
@@ -1120,7 +1120,7 @@
|
|||||||
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
||||||
<value>Please fill in DNS Structure, Click to view the document</value>
|
<value>Please fill in DNS Structure, Click to view the document</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TBSettingDnsImportDefConfig" xml:space="preserve">
|
<data name="TbSettingDnsImportDefConfig" xml:space="preserve">
|
||||||
<value>Click to import default DNS config</value>
|
<value>Click to import default DNS config</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
||||||
@@ -1138,4 +1138,13 @@
|
|||||||
<data name="TbRoutingRuleDomain" xml:space="preserve">
|
<data name="TbRoutingRuleDomain" xml:space="preserve">
|
||||||
<value>Domain</value>
|
<value>Domain</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="menuAddHysteria2Server" xml:space="preserve">
|
||||||
|
<value>Add [Trojan] server</value>
|
||||||
|
</data>
|
||||||
|
<data name="TbSettingsHysteriaBandwidth" xml:space="preserve">
|
||||||
|
<value>Hysteria Max bandwidth (Up/Dw)</value>
|
||||||
|
</data>
|
||||||
|
<data name="TbSettingsUseSystemHosts" xml:space="preserve">
|
||||||
|
<value>Use System Hosts</value>
|
||||||
|
</data>
|
||||||
</root>
|
</root>
|
||||||
@@ -1117,7 +1117,7 @@
|
|||||||
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
||||||
<value>请填写 DNS JSON 结构,点击查看文档</value>
|
<value>请填写 DNS JSON 结构,点击查看文档</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TBSettingDnsImportDefConfig" xml:space="preserve">
|
<data name="TbSettingDnsImportDefConfig" xml:space="preserve">
|
||||||
<value>点击导入默认DNS配置</value>
|
<value>点击导入默认DNS配置</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
||||||
@@ -1135,4 +1135,13 @@
|
|||||||
<data name="TbRoutingRuleIP" xml:space="preserve">
|
<data name="TbRoutingRuleIP" xml:space="preserve">
|
||||||
<value>IP 或 IP CIDR</value>
|
<value>IP 或 IP CIDR</value>
|
||||||
</data>
|
</data>
|
||||||
|
<data name="menuAddHysteria2Server" xml:space="preserve">
|
||||||
|
<value>添加[Hysteria2]服务器</value>
|
||||||
|
</data>
|
||||||
|
<data name="TbSettingsHysteriaBandwidth" xml:space="preserve">
|
||||||
|
<value>Hysteria 最大带宽(Up/Dw)</value>
|
||||||
|
</data>
|
||||||
|
<data name="TbSettingsUseSystemHosts" xml:space="preserve">
|
||||||
|
<value>使用系统hosts</value>
|
||||||
|
</data>
|
||||||
</root>
|
</root>
|
||||||
@@ -1117,7 +1117,7 @@
|
|||||||
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
<data name="TbDnsSingboxObjectDoc" xml:space="preserve">
|
||||||
<value>請填寫 DNS JSON 結構,點擊查看文件</value>
|
<value>請填寫 DNS JSON 結構,點擊查看文件</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TBSettingDnsImportDefConfig" xml:space="preserve">
|
<data name="TbSettingDnsImportDefConfig" xml:space="preserve">
|
||||||
<value>點擊匯入預設DNS配置</value>
|
<value>點擊匯入預設DNS配置</value>
|
||||||
</data>
|
</data>
|
||||||
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
<data name="TbdomainStrategy4Singbox" xml:space="preserve">
|
||||||
|
|||||||
@@ -145,6 +145,10 @@ namespace v2rayN.ViewModels
|
|||||||
case EConfigType.Trojan:
|
case EConfigType.Trojan:
|
||||||
ret = ConfigHandler.AddTrojanServer(ref _config, item);
|
ret = ConfigHandler.AddTrojanServer(ref _config, item);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case EConfigType.Hysteria2:
|
||||||
|
ret = ConfigHandler.AddHysteria2Server(ref _config, item);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ret == 0)
|
if (ret == 0)
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ namespace v2rayN.ViewModels
|
|||||||
private NoticeHandler? _noticeHandler;
|
private NoticeHandler? _noticeHandler;
|
||||||
private Window _view;
|
private Window _view;
|
||||||
|
|
||||||
|
[Reactive] public bool useSystemHosts { get; set; }
|
||||||
[Reactive] public string domainStrategy4Freedom { get; set; }
|
[Reactive] public string domainStrategy4Freedom { get; set; }
|
||||||
[Reactive] public string normalDNS { get; set; }
|
[Reactive] public string normalDNS { get; set; }
|
||||||
[Reactive] public string normalDNS2 { get; set; }
|
[Reactive] public string normalDNS2 { get; set; }
|
||||||
@@ -31,6 +32,7 @@ namespace v2rayN.ViewModels
|
|||||||
_view = view;
|
_view = view;
|
||||||
|
|
||||||
var item = LazyConfig.Instance.GetDNSItem(ECoreType.Xray);
|
var item = LazyConfig.Instance.GetDNSItem(ECoreType.Xray);
|
||||||
|
useSystemHosts = item.useSystemHosts;
|
||||||
domainStrategy4Freedom = item?.domainStrategy4Freedom!;
|
domainStrategy4Freedom = item?.domainStrategy4Freedom!;
|
||||||
normalDNS = item?.normalDNS!;
|
normalDNS = item?.normalDNS!;
|
||||||
|
|
||||||
@@ -95,6 +97,7 @@ namespace v2rayN.ViewModels
|
|||||||
|
|
||||||
var item = LazyConfig.Instance.GetDNSItem(ECoreType.Xray);
|
var item = LazyConfig.Instance.GetDNSItem(ECoreType.Xray);
|
||||||
item.domainStrategy4Freedom = domainStrategy4Freedom;
|
item.domainStrategy4Freedom = domainStrategy4Freedom;
|
||||||
|
item.useSystemHosts = useSystemHosts;
|
||||||
item.normalDNS = normalDNS;
|
item.normalDNS = normalDNS;
|
||||||
ConfigHandler.SaveDNSItems(_config, item);
|
ConfigHandler.SaveDNSItems(_config, item);
|
||||||
|
|
||||||
|
|||||||
@@ -89,6 +89,7 @@ namespace v2rayN.ViewModels
|
|||||||
public ReactiveCommand<Unit, Unit> AddShadowsocksServerCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddShadowsocksServerCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> AddSocksServerCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddSocksServerCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> AddTrojanServerCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddTrojanServerCmd { get; }
|
||||||
|
public ReactiveCommand<Unit, Unit> AddHysteria2ServerCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> AddCustomServerCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddCustomServerCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> AddServerViaClipboardCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddServerViaClipboardCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> AddServerViaScanCmd { get; }
|
public ReactiveCommand<Unit, Unit> AddServerViaScanCmd { get; }
|
||||||
@@ -147,11 +148,14 @@ namespace v2rayN.ViewModels
|
|||||||
public ReactiveCommand<Unit, Unit> CheckUpdateNCmd { get; }
|
public ReactiveCommand<Unit, Unit> CheckUpdateNCmd { get; }
|
||||||
|
|
||||||
public ReactiveCommand<Unit, Unit> CheckUpdateV2flyCoreCmd { get; }
|
public ReactiveCommand<Unit, Unit> CheckUpdateV2flyCoreCmd { get; }
|
||||||
|
|
||||||
//public ReactiveCommand<Unit, Unit> CheckUpdateSagerNetCoreCmd { get; }
|
//public ReactiveCommand<Unit, Unit> CheckUpdateSagerNetCoreCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> CheckUpdateXrayCoreCmd { get; }
|
public ReactiveCommand<Unit, Unit> CheckUpdateXrayCoreCmd { get; }
|
||||||
|
|
||||||
//public ReactiveCommand<Unit, Unit> CheckUpdateClashCoreCmd { get; }
|
//public ReactiveCommand<Unit, Unit> CheckUpdateClashCoreCmd { get; }
|
||||||
//public ReactiveCommand<Unit, Unit> CheckUpdateClashMetaCoreCmd { get; }
|
//public ReactiveCommand<Unit, Unit> CheckUpdateClashMetaCoreCmd { get; }
|
||||||
public ReactiveCommand<Unit, Unit> CheckUpdateSingBoxCoreCmd { get; }
|
public ReactiveCommand<Unit, Unit> CheckUpdateSingBoxCoreCmd { get; }
|
||||||
|
|
||||||
public ReactiveCommand<Unit, Unit> CheckUpdateGeoCmd { get; }
|
public ReactiveCommand<Unit, Unit> CheckUpdateGeoCmd { get; }
|
||||||
|
|
||||||
public ReactiveCommand<Unit, Unit> ReloadCmd { get; }
|
public ReactiveCommand<Unit, Unit> ReloadCmd { get; }
|
||||||
@@ -337,6 +341,10 @@ namespace v2rayN.ViewModels
|
|||||||
{
|
{
|
||||||
EditServer(true, EConfigType.Trojan);
|
EditServer(true, EConfigType.Trojan);
|
||||||
});
|
});
|
||||||
|
AddHysteria2ServerCmd = ReactiveCommand.Create(() =>
|
||||||
|
{
|
||||||
|
EditServer(true, EConfigType.Hysteria2);
|
||||||
|
});
|
||||||
AddCustomServerCmd = ReactiveCommand.Create(() =>
|
AddCustomServerCmd = ReactiveCommand.Create(() =>
|
||||||
{
|
{
|
||||||
EditServer(true, EConfigType.Custom);
|
EditServer(true, EConfigType.Custom);
|
||||||
|
|||||||
@@ -32,6 +32,8 @@ namespace v2rayN.ViewModels
|
|||||||
[Reactive] public string defFingerprint { get; set; }
|
[Reactive] public string defFingerprint { get; set; }
|
||||||
[Reactive] public string defUserAgent { get; set; }
|
[Reactive] public string defUserAgent { get; set; }
|
||||||
[Reactive] public string mux4SboxProtocol { get; set; }
|
[Reactive] public string mux4SboxProtocol { get; set; }
|
||||||
|
[Reactive] public int hyUpMbps { get; set; }
|
||||||
|
[Reactive] public int hyDownMbps { get; set; }
|
||||||
|
|
||||||
#endregion Core
|
#endregion Core
|
||||||
|
|
||||||
@@ -120,7 +122,9 @@ namespace v2rayN.ViewModels
|
|||||||
defAllowInsecure = _config.coreBasicItem.defAllowInsecure;
|
defAllowInsecure = _config.coreBasicItem.defAllowInsecure;
|
||||||
defFingerprint = _config.coreBasicItem.defFingerprint;
|
defFingerprint = _config.coreBasicItem.defFingerprint;
|
||||||
defUserAgent = _config.coreBasicItem.defUserAgent;
|
defUserAgent = _config.coreBasicItem.defUserAgent;
|
||||||
mux4SboxProtocol = _config.mux4Sbox.protocol;
|
mux4SboxProtocol = _config.mux4SboxItem.protocol;
|
||||||
|
hyUpMbps = _config.hysteriaItem.up_mbps;
|
||||||
|
hyDownMbps = _config.hysteriaItem.down_mbps;
|
||||||
|
|
||||||
#endregion Core
|
#endregion Core
|
||||||
|
|
||||||
@@ -274,7 +278,9 @@ namespace v2rayN.ViewModels
|
|||||||
_config.coreBasicItem.defAllowInsecure = defAllowInsecure;
|
_config.coreBasicItem.defAllowInsecure = defAllowInsecure;
|
||||||
_config.coreBasicItem.defFingerprint = defFingerprint;
|
_config.coreBasicItem.defFingerprint = defFingerprint;
|
||||||
_config.coreBasicItem.defUserAgent = defUserAgent;
|
_config.coreBasicItem.defUserAgent = defUserAgent;
|
||||||
_config.mux4Sbox.protocol = mux4SboxProtocol;
|
_config.mux4SboxItem.protocol = mux4SboxProtocol;
|
||||||
|
_config.hysteriaItem.up_mbps = hyUpMbps;
|
||||||
|
_config.hysteriaItem.down_mbps = hyDownMbps;
|
||||||
|
|
||||||
//Kcp
|
//Kcp
|
||||||
//_config.kcpItem.mtu = Kcpmtu;
|
//_config.kcpItem.mtu = Kcpmtu;
|
||||||
@@ -359,6 +365,9 @@ namespace v2rayN.ViewModels
|
|||||||
case 6:
|
case 6:
|
||||||
type = CoreType6;
|
type = CoreType6;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 7:
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
item.coreType = (ECoreType)Enum.Parse(typeof(ECoreType), type);
|
item.coreType = (ECoreType)Enum.Parse(typeof(ECoreType), type);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
<reactiveui:ReactiveWindow
|
<reactiveui:ReactiveWindow
|
||||||
x:Class="v2rayN.Views.AddServerWindow"
|
x:Class="v2rayN.Views.AddServerWindow"
|
||||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
|
||||||
xmlns:conv="clr-namespace:v2rayN.Converters"
|
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
|
||||||
xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes"
|
xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes"
|
||||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
|
||||||
xmlns:reactiveui="http://reactiveui.net"
|
xmlns:reactiveui="http://reactiveui.net"
|
||||||
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||||
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
|
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||||
|
xmlns:conv="clr-namespace:v2rayN.Converters"
|
||||||
xmlns:resx="clr-namespace:v2rayN.Resx"
|
xmlns:resx="clr-namespace:v2rayN.Resx"
|
||||||
xmlns:vms="clr-namespace:v2rayN.ViewModels"
|
xmlns:vms="clr-namespace:v2rayN.ViewModels"
|
||||||
Title="{x:Static resx:ResUI.menuServers}"
|
Title="{x:Static resx:ResUI.menuServers}"
|
||||||
@@ -399,13 +399,43 @@
|
|||||||
Margin="{StaticResource ServerItemMargin}"
|
Margin="{StaticResource ServerItemMargin}"
|
||||||
Style="{StaticResource DefComboBox}" />
|
Style="{StaticResource DefComboBox}" />
|
||||||
</Grid>
|
</Grid>
|
||||||
|
<Grid
|
||||||
|
x:Name="gridHysteria2"
|
||||||
|
Grid.Row="2"
|
||||||
|
Visibility="Hidden">
|
||||||
|
<Grid.RowDefinitions>
|
||||||
|
<RowDefinition Height="Auto" />
|
||||||
|
<RowDefinition Height="Auto" />
|
||||||
|
<RowDefinition Height="Auto" />
|
||||||
|
</Grid.RowDefinitions>
|
||||||
|
<Grid.ColumnDefinitions>
|
||||||
|
<ColumnDefinition Width="180" />
|
||||||
|
<ColumnDefinition Width="Auto" />
|
||||||
|
</Grid.ColumnDefinitions>
|
||||||
|
|
||||||
|
<TextBlock
|
||||||
|
Grid.Row="1"
|
||||||
|
Grid.Column="0"
|
||||||
|
Margin="{StaticResource ServerItemMargin}"
|
||||||
|
VerticalAlignment="Center"
|
||||||
|
Style="{StaticResource ToolbarTextBlock}"
|
||||||
|
Text="{x:Static resx:ResUI.TbId3}" />
|
||||||
|
<TextBox
|
||||||
|
x:Name="txtId7"
|
||||||
|
Grid.Row="1"
|
||||||
|
Grid.Column="1"
|
||||||
|
Width="400"
|
||||||
|
Margin="{StaticResource ServerItemMargin}"
|
||||||
|
Style="{StaticResource DefTextBox}" />
|
||||||
|
</Grid>
|
||||||
|
|
||||||
<Separator
|
<Separator
|
||||||
|
x:Name="sepa2"
|
||||||
Grid.Row="3"
|
Grid.Row="3"
|
||||||
Margin="0,2"
|
Margin="0,2"
|
||||||
Style="{DynamicResource MaterialDesignSeparator}" />
|
Style="{DynamicResource MaterialDesignSeparator}" />
|
||||||
|
|
||||||
<Grid Grid.Row="4">
|
<Grid x:Name="gridTransport" Grid.Row="4">
|
||||||
<Grid.RowDefinitions>
|
<Grid.RowDefinitions>
|
||||||
<RowDefinition Height="Auto" />
|
<RowDefinition Height="Auto" />
|
||||||
<RowDefinition Height="Auto" />
|
<RowDefinition Height="Auto" />
|
||||||
|
|||||||
@@ -117,6 +117,15 @@ namespace v2rayN.Views
|
|||||||
cmbFlow6.Items.Add(it);
|
cmbFlow6.Items.Add(it);
|
||||||
});
|
});
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case EConfigType.Hysteria2:
|
||||||
|
gridHysteria2.Visibility = Visibility.Visible;
|
||||||
|
sepa2.Visibility = Visibility.Collapsed;
|
||||||
|
gridTransport.Visibility = Visibility.Collapsed;
|
||||||
|
cmbCoreType.IsEnabled = false;
|
||||||
|
cmbFingerprint.IsEnabled = false;
|
||||||
|
cmbFingerprint.Text = string.Empty;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
gridTlsMore.Visibility = Visibility.Hidden;
|
gridTlsMore.Visibility = Visibility.Hidden;
|
||||||
@@ -156,6 +165,10 @@ namespace v2rayN.Views
|
|||||||
this.Bind(ViewModel, vm => vm.SelectedSource.id, v => v.txtId6.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.SelectedSource.id, v => v.txtId6.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.SelectedSource.flow, v => v.cmbFlow6.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.SelectedSource.flow, v => v.cmbFlow6.Text).DisposeWith(disposables);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case EConfigType.Hysteria2:
|
||||||
|
this.Bind(ViewModel, vm => vm.SelectedSource.id, v => v.txtId7.Text).DisposeWith(disposables);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
this.Bind(ViewModel, vm => vm.SelectedSource.network, v => v.cmbNetwork.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.SelectedSource.network, v => v.cmbNetwork.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.SelectedSource.headerType, v => v.cmbHeaderType.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.SelectedSource.headerType, v => v.cmbHeaderType.Text).DisposeWith(disposables);
|
||||||
|
|||||||
@@ -64,6 +64,20 @@
|
|||||||
Style="{StaticResource DefComboBox}" />
|
Style="{StaticResource DefComboBox}" />
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
|
||||||
|
<StackPanel DockPanel.Dock="Bottom" Orientation="Horizontal">
|
||||||
|
<TextBlock
|
||||||
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
|
VerticalAlignment="Center"
|
||||||
|
Style="{StaticResource ToolbarTextBlock}"
|
||||||
|
Text="{x:Static resx:ResUI.TbSettingsUseSystemHosts}" />
|
||||||
|
<ToggleButton
|
||||||
|
x:Name="togUseSystemHosts"
|
||||||
|
Grid.Row="5"
|
||||||
|
Grid.Column="1"
|
||||||
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
|
HorizontalAlignment="Left" />
|
||||||
|
</StackPanel>
|
||||||
|
|
||||||
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal">
|
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal">
|
||||||
<TextBlock
|
<TextBlock
|
||||||
Margin="{StaticResource SettingItemMargin}"
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
@@ -81,7 +95,7 @@
|
|||||||
<Button
|
<Button
|
||||||
x:Name="btnImportDefConfig4V2ray"
|
x:Name="btnImportDefConfig4V2ray"
|
||||||
Margin="8,0,0,0"
|
Margin="8,0,0,0"
|
||||||
Content="{x:Static resx:ResUI.TBSettingDnsImportDefConfig}"
|
Content="{x:Static resx:ResUI.TbSettingDnsImportDefConfig}"
|
||||||
Cursor="Hand"
|
Cursor="Hand"
|
||||||
Style="{StaticResource DefButton}" />
|
Style="{StaticResource DefButton}" />
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
@@ -113,7 +127,7 @@
|
|||||||
<Button
|
<Button
|
||||||
x:Name="btnImportDefConfig4Singbox"
|
x:Name="btnImportDefConfig4Singbox"
|
||||||
Margin="8,0,0,0"
|
Margin="8,0,0,0"
|
||||||
Content="{x:Static resx:ResUI.TBSettingDnsImportDefConfig}"
|
Content="{x:Static resx:ResUI.TbSettingDnsImportDefConfig}"
|
||||||
Cursor="Hand"
|
Cursor="Hand"
|
||||||
Style="{StaticResource DefButton}" />
|
Style="{StaticResource DefButton}" />
|
||||||
</StackPanel>
|
</StackPanel>
|
||||||
|
|||||||
@@ -37,6 +37,7 @@ namespace v2rayN.Views
|
|||||||
|
|
||||||
this.WhenActivated(disposables =>
|
this.WhenActivated(disposables =>
|
||||||
{
|
{
|
||||||
|
this.Bind(ViewModel, vm=>vm.useSystemHosts, v=>v.togUseSystemHosts.IsChecked).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.domainStrategy4Freedom, v => v.cmbdomainStrategy4Freedom.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.domainStrategy4Freedom, v => v.cmbdomainStrategy4Freedom.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.normalDNS, v => v.txtnormalDNS.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.normalDNS, v => v.txtnormalDNS.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.normalDNS2, v => v.txtnormalDNS2.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.normalDNS2, v => v.txtnormalDNS2.Text).DisposeWith(disposables);
|
||||||
|
|||||||
@@ -83,6 +83,10 @@
|
|||||||
x:Name="menuAddTrojanServer"
|
x:Name="menuAddTrojanServer"
|
||||||
Height="{StaticResource MenuItemHeight}"
|
Height="{StaticResource MenuItemHeight}"
|
||||||
Header="{x:Static resx:ResUI.menuAddTrojanServer}" />
|
Header="{x:Static resx:ResUI.menuAddTrojanServer}" />
|
||||||
|
<MenuItem
|
||||||
|
x:Name="menuAddHysteria2Server"
|
||||||
|
Height="{StaticResource MenuItemHeight}"
|
||||||
|
Header="{x:Static resx:ResUI.menuAddHysteria2Server}" />
|
||||||
<Separator Margin="-40,5" />
|
<Separator Margin="-40,5" />
|
||||||
<MenuItem
|
<MenuItem
|
||||||
x:Name="menuAddServerViaClipboard"
|
x:Name="menuAddServerViaClipboard"
|
||||||
|
|||||||
@@ -86,6 +86,7 @@ namespace v2rayN.Views
|
|||||||
this.BindCommand(ViewModel, vm => vm.AddShadowsocksServerCmd, v => v.menuAddShadowsocksServer).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddShadowsocksServerCmd, v => v.menuAddShadowsocksServer).DisposeWith(disposables);
|
||||||
this.BindCommand(ViewModel, vm => vm.AddSocksServerCmd, v => v.menuAddSocksServer).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddSocksServerCmd, v => v.menuAddSocksServer).DisposeWith(disposables);
|
||||||
this.BindCommand(ViewModel, vm => vm.AddTrojanServerCmd, v => v.menuAddTrojanServer).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddTrojanServerCmd, v => v.menuAddTrojanServer).DisposeWith(disposables);
|
||||||
|
this.BindCommand(ViewModel, vm => vm.AddHysteria2ServerCmd, v => v.menuAddHysteria2Server).DisposeWith(disposables);
|
||||||
this.BindCommand(ViewModel, vm => vm.AddCustomServerCmd, v => v.menuAddCustomServer).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddCustomServerCmd, v => v.menuAddCustomServer).DisposeWith(disposables);
|
||||||
this.BindCommand(ViewModel, vm => vm.AddServerViaClipboardCmd, v => v.menuAddServerViaClipboard).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddServerViaClipboardCmd, v => v.menuAddServerViaClipboard).DisposeWith(disposables);
|
||||||
this.BindCommand(ViewModel, vm => vm.AddServerViaScanCmd, v => v.menuAddServerViaScan).DisposeWith(disposables);
|
this.BindCommand(ViewModel, vm => vm.AddServerViaScanCmd, v => v.menuAddServerViaScan).DisposeWith(disposables);
|
||||||
@@ -327,21 +328,27 @@ namespace v2rayN.Views
|
|||||||
case Key.V:
|
case Key.V:
|
||||||
ViewModel?.AddServerViaClipboard();
|
ViewModel?.AddServerViaClipboard();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.P:
|
case Key.P:
|
||||||
ViewModel?.ServerSpeedtest(ESpeedActionType.Ping);
|
ViewModel?.ServerSpeedtest(ESpeedActionType.Ping);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.O:
|
case Key.O:
|
||||||
ViewModel?.ServerSpeedtest(ESpeedActionType.Tcping);
|
ViewModel?.ServerSpeedtest(ESpeedActionType.Tcping);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.R:
|
case Key.R:
|
||||||
ViewModel?.ServerSpeedtest(ESpeedActionType.Realping);
|
ViewModel?.ServerSpeedtest(ESpeedActionType.Realping);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.S:
|
case Key.S:
|
||||||
_ = ViewModel?.ScanScreenTaskAsync();
|
_ = ViewModel?.ScanScreenTaskAsync();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.T:
|
case Key.T:
|
||||||
ViewModel?.ServerSpeedtest(ESpeedActionType.Speedtest);
|
ViewModel?.ServerSpeedtest(ESpeedActionType.Speedtest);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Key.E:
|
case Key.E:
|
||||||
ViewModel?.ServerSpeedtest(ESpeedActionType.Mixedtest);
|
ViewModel?.ServerSpeedtest(ESpeedActionType.Mixedtest);
|
||||||
break;
|
break;
|
||||||
@@ -494,11 +501,18 @@ namespace v2rayN.Views
|
|||||||
|
|
||||||
if (!_config.guiItem.enableStatistics)
|
if (!_config.guiItem.enableStatistics)
|
||||||
{
|
{
|
||||||
colTodayUp.Visibility = Visibility.Hidden;
|
colTodayUp.Visibility =
|
||||||
colTodayDown.Visibility = Visibility.Hidden;
|
colTodayDown.Visibility =
|
||||||
colTotalUp.Visibility = Visibility.Hidden;
|
colTotalUp.Visibility =
|
||||||
colTotalDown.Visibility = Visibility.Hidden;
|
colTotalDown.Visibility = Visibility.Hidden;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
colTodayUp.Visibility =
|
||||||
|
colTodayDown.Visibility =
|
||||||
|
colTotalUp.Visibility =
|
||||||
|
colTotalDown.Visibility = Visibility.Visible;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void StorageUI()
|
private void StorageUI()
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
<reactiveui:ReactiveWindow
|
<reactiveui:ReactiveWindow
|
||||||
x:Class="v2rayN.Views.OptionSettingWindow"
|
x:Class="v2rayN.Views.OptionSettingWindow"
|
||||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||||
xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes"
|
|
||||||
xmlns:reactiveui="http://reactiveui.net"
|
|
||||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
|
||||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
|
||||||
xmlns:conv="clr-namespace:v2rayN.Converters"
|
xmlns:conv="clr-namespace:v2rayN.Converters"
|
||||||
|
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||||
|
xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes"
|
||||||
|
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||||
|
xmlns:reactiveui="http://reactiveui.net"
|
||||||
xmlns:resx="clr-namespace:v2rayN.Resx"
|
xmlns:resx="clr-namespace:v2rayN.Resx"
|
||||||
xmlns:vms="clr-namespace:v2rayN.ViewModels"
|
xmlns:vms="clr-namespace:v2rayN.ViewModels"
|
||||||
Title="{x:Static resx:ResUI.menuSetting}"
|
Title="{x:Static resx:ResUI.menuSetting}"
|
||||||
@@ -68,6 +68,7 @@
|
|||||||
<RowDefinition Height="Auto" />
|
<RowDefinition Height="Auto" />
|
||||||
<RowDefinition Height="Auto" />
|
<RowDefinition Height="Auto" />
|
||||||
<RowDefinition Height="Auto" />
|
<RowDefinition Height="Auto" />
|
||||||
|
<RowDefinition Height="Auto" />
|
||||||
</Grid.RowDefinitions>
|
</Grid.RowDefinitions>
|
||||||
<Grid.ColumnDefinitions>
|
<Grid.ColumnDefinitions>
|
||||||
<ColumnDefinition Width="Auto" />
|
<ColumnDefinition Width="Auto" />
|
||||||
@@ -307,6 +308,33 @@
|
|||||||
Width="200"
|
Width="200"
|
||||||
Margin="{StaticResource SettingItemMargin}"
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
Style="{StaticResource DefComboBox}" />
|
Style="{StaticResource DefComboBox}" />
|
||||||
|
|
||||||
|
<TextBlock
|
||||||
|
Grid.Row="15"
|
||||||
|
Grid.Column="0"
|
||||||
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
|
VerticalAlignment="Center"
|
||||||
|
Style="{StaticResource ToolbarTextBlock}"
|
||||||
|
Text="{x:Static resx:ResUI.TbSettingsHysteriaBandwidth}" />
|
||||||
|
|
||||||
|
<StackPanel
|
||||||
|
Grid.Row="15"
|
||||||
|
Grid.Column="1"
|
||||||
|
Orientation="Horizontal">
|
||||||
|
|
||||||
|
<TextBox
|
||||||
|
x:Name="txtUpMbps"
|
||||||
|
Width="90"
|
||||||
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
|
materialDesign:HintAssist.Hint="Up"
|
||||||
|
Style="{StaticResource DefTextBox}" />
|
||||||
|
<TextBox
|
||||||
|
x:Name="txtDownMbps"
|
||||||
|
Width="90"
|
||||||
|
Margin="{StaticResource SettingItemMargin}"
|
||||||
|
materialDesign:HintAssist.Hint="Down"
|
||||||
|
Style="{StaticResource DefTextBox}" />
|
||||||
|
</StackPanel>
|
||||||
</Grid>
|
</Grid>
|
||||||
</ScrollViewer>
|
</ScrollViewer>
|
||||||
</TabItem>
|
</TabItem>
|
||||||
|
|||||||
@@ -151,6 +151,8 @@ namespace v2rayN.Views
|
|||||||
this.Bind(ViewModel, vm => vm.defFingerprint, v => v.cmbdefFingerprint.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.defFingerprint, v => v.cmbdefFingerprint.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.defUserAgent, v => v.cmbdefUserAgent.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.defUserAgent, v => v.cmbdefUserAgent.Text).DisposeWith(disposables);
|
||||||
this.Bind(ViewModel, vm => vm.mux4SboxProtocol, v => v.cmbmux4SboxProtocol.Text).DisposeWith(disposables);
|
this.Bind(ViewModel, vm => vm.mux4SboxProtocol, v => v.cmbmux4SboxProtocol.Text).DisposeWith(disposables);
|
||||||
|
this.Bind(ViewModel, vm => vm.hyUpMbps, v => v.txtUpMbps.Text).DisposeWith(disposables);
|
||||||
|
this.Bind(ViewModel, vm => vm.hyDownMbps, v => v.txtDownMbps.Text).DisposeWith(disposables);
|
||||||
|
|
||||||
//this.Bind(ViewModel, vm => vm.Kcpmtu, v => v.txtKcpmtu.Text).DisposeWith(disposables);
|
//this.Bind(ViewModel, vm => vm.Kcpmtu, v => v.txtKcpmtu.Text).DisposeWith(disposables);
|
||||||
//this.Bind(ViewModel, vm => vm.Kcptti, v => v.txtKcptti.Text).DisposeWith(disposables);
|
//this.Bind(ViewModel, vm => vm.Kcptti, v => v.txtKcptti.Text).DisposeWith(disposables);
|
||||||
|
|||||||
@@ -10,7 +10,7 @@
|
|||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
<ApplicationIcon>v2rayN.ico</ApplicationIcon>
|
<ApplicationIcon>v2rayN.ico</ApplicationIcon>
|
||||||
<Copyright>Copyright © 2017-2023 (GPLv3)</Copyright>
|
<Copyright>Copyright © 2017-2023 (GPLv3)</Copyright>
|
||||||
<FileVersion>6.30</FileVersion>
|
<FileVersion>6.31</FileVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -13,6 +13,7 @@ namespace v2rayUpgrade
|
|||||||
{
|
{
|
||||||
Application.EnableVisualStyles();
|
Application.EnableVisualStyles();
|
||||||
Application.SetHighDpiMode(HighDpiMode.SystemAware);
|
Application.SetHighDpiMode(HighDpiMode.SystemAware);
|
||||||
|
Application.SetHighDpiMode(HighDpiMode.PerMonitorV2);
|
||||||
Application.SetCompatibleTextRenderingDefault(false);
|
Application.SetCompatibleTextRenderingDefault(false);
|
||||||
Application.Run(new MainForm(args));
|
Application.Run(new MainForm(args));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,8 +2,6 @@
|
|||||||
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0" xmlns:asmv3="urn:schemas-microsoft-com:asm.v3">
|
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0" xmlns:asmv3="urn:schemas-microsoft-com:asm.v3">
|
||||||
<asmv3:application>
|
<asmv3:application>
|
||||||
<asmv3:windowsSettings>
|
<asmv3:windowsSettings>
|
||||||
<dpiAware xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">true</dpiAware>
|
|
||||||
<dpiAwareness xmlns="http://schemas.microsoft.com/SMI/2016/WindowsSettings">PerMonitorV2</dpiAwareness>
|
|
||||||
</asmv3:windowsSettings>
|
</asmv3:windowsSettings>
|
||||||
</asmv3:application>
|
</asmv3:application>
|
||||||
</assembly>
|
</assembly>
|
||||||
Reference in New Issue
Block a user