Compare commits

...

72 Commits
1.3.7 ... 1.4.0

Author SHA1 Message Date
Amazing_DM
bd05f875f2 Version 1.4.0 2020-03-11 09:59:01 +08:00
Amazing_DM
ea3fb188e4 :bug:修复NTT规则重复添加 2020-03-11 09:57:34 +08:00
Amazing_DM
ee3ac561b5 Update submodule 2020-03-10 21:43:19 +08:00
Amazing_DM
4fb090d7a4 Revert ":art:所有tap模式绕Lan IP"
This reverts commit 6dd50f1510.
2020-03-10 21:33:40 +08:00
Amazing_DM
9302900b5d Catch一模式列表筛选异常 2020-03-10 21:08:45 +08:00
Amazing_DM
6dd50f1510 :art:所有tap模式绕Lan IP
Signed-off-by: Amazing_DM <amazingdmdd@gmail.com>
2020-03-10 16:01:01 +08:00
Amazing_DM
91f73b936d Update submodule
Signed-off-by: Amazing_DM <amazingdmdd@gmail.com>
2020-03-10 14:57:59 +08:00
Amazing_DM
9ddcc3ae3c :zap:更新内核
Signed-off-by: Amazing_DM <amazingdmdd@gmail.com>
2020-03-10 14:45:50 +08:00
Amazing_DM
9d637a3c67 Merge pull request #249 from henning724/master
处理遍历适配器时的异常,解决一部分tun/tap启动问题
2020-03-10 00:04:43 +08:00
henning
8ff8582dd7 处理遍历适配器时的异常 2020-03-09 23:36:39 +08:00
Amazing_DM
b76a22da33 🎨 tap模式内置dns改为dns2tcp处理 2020-03-09 20:46:53 +08:00
Amazing_DM
ee61c5dbd3 :art:优化启动速度 2020-03-06 14:13:00 +08:00
Amazing_DM
658ed3245f Update version 2020-03-06 13:17:27 +08:00
Amazing_DM
d443c6d311 :sparkles:启动时显示详细信息 2020-03-06 13:03:37 +08:00
Amazing_DM
caa6b8fa94 :ambulance:恢复本地DNS服务 2020-03-06 12:37:14 +08:00
Amazing_DM
26af839d01 Update submodule 2020-03-06 12:15:56 +08:00
Amazing_DM
08db39f72b Update submodule 2020-03-05 21:32:43 +08:00
Amazing_DM
5e1f25a27e 添加NAT检测功能,特别感谢@HMBSbige大佬的轮子 2020-03-05 16:02:51 +08:00
Amazing_DM
5985f6cf57 Merge pull request #248 from henning724/master
修复程序启动崩溃,增加tun/tap相关的log
2020-02-28 11:43:58 +08:00
henning
2ae4f454ff 修复:当logging文件夹存在时,程序启动崩溃 2020-02-27 15:45:39 +08:00
henning
48ab9a8995 增加寻找适配器的logging 2020-02-27 15:33:09 +08:00
henning
6f817ee245 增加更多tun/tap错误反馈信息到application.log 2020-02-27 15:24:10 +08:00
Connection Refused
b091424d19 Merge pull request #247 from henning724/master
An attempt to fix forever "Starting" problem while using TUN/TAP
2020-02-27 00:26:13 +08:00
henning
d612ab76de An attempt to fix forever "Starting" problem while using TUN/TAP 2020-02-26 15:30:15 +08:00
Connection Refused
61838ac8bc Remove built-in UDP DNS to TCP query 2020-02-19 18:29:44 +08:00
Connection Refused
6d66733644 Update submodule 2020-02-19 18:23:39 +08:00
Amazing_DM
bf7a766574 Merge pull request #246 from LovelyWei/dev
添加开机自启选项
2020-02-18 20:17:14 +08:00
LovelyWei
11afbc91ab Merge branch 'master' into dev 2020-02-18 18:22:35 +08:00
LovelyWei
c39ae5f12f fix a bug 2020-02-18 18:21:15 +08:00
LovelyWei
0d511b0325 添加开机自启选项 2020-02-18 15:22:32 +08:00
BingLingGroup
9f46d7afaa Merge pull request #245 from LovelyWei/master 2020-02-18 15:21:03 +08:00
BingLingGroup
df706037f0 Refactor hiding codes 2020-02-18 15:16:58 +08:00
LovelyWei
81510e0036 添加启动后隐藏选项 2020-02-18 13:14:24 +08:00
Connection Refused
9b7f0b1469 Delete across-gfw.jpg 2020-02-13 21:24:43 +08:00
Connection Refused
6632ea4fd8 Update README.zh-CN.md 2020-02-13 21:23:58 +08:00
Connection Refused
580aa6bd05 Update README.md 2020-02-13 21:23:35 +08:00
Amazing_DM
b39e5d2dbe 添加复制服务器分享链接按钮
 添加模式删除按钮
 添加自定义配置数量(在设置里修改后需重启软件)
:speech_balloon:添加快捷配置翻译
2020-02-13 19:22:44 +08:00
Amazing_DM
282e000beb 添加快捷删除模式按钮 2020-02-13 17:13:22 +08:00
Connection Refused
7fe227bb49 Revert "Remove V2Ray support"
This reverts commit c235713c1b.
2020-02-10 02:57:47 +08:00
Connection Refused
c235713c1b Remove V2Ray support 2020-02-09 22:23:55 +08:00
Amazing_DM
3db75738dc Update submodule 2020-02-07 21:20:06 +08:00
Amazing_DM
61666a180d 🐛 修复了一个允许创建空文件名模式的bug
🎨 现在只允许修改进程加速的模式
💬 更新部分中文翻译
2020-02-06 22:50:18 +08:00
Amazing_DM
b4199abc4a fix a bug 2020-02-06 13:41:56 +08:00
Amazing_DM
5958e353c2 Update submodule
Signed-off-by: Amazing_DM <amazingdmdd@gmail.com>
2020-02-06 13:22:07 +08:00
Amazing_DM
f5c6632a92 添加Tap-Driver
Signed-off-by: Amazing_DM <amazingdmdd@gmail.com>
2020-02-06 13:14:52 +08:00
Amazing_DM
1d38ea1746 Update submodule 2020-02-06 11:16:24 +08:00
Amazing_DM
3a048c76e1 Merge branch 'master' of https://github.com/NetchX/Netch 2020-02-05 21:58:49 +08:00
Amazing_DM
0b6b66461d fix a little bug 2020-02-05 21:33:29 +08:00
Connection Refused
bc7681bd0b Update README.zh-CN.md 2020-02-05 20:58:03 +08:00
Connection Refused
ee347b62bc Update README.md 2020-02-05 20:57:43 +08:00
Amazing_DM
1a5572ae2d 添加模式修改功能
订阅列表右键现在可以复制链接啦~
2020-02-05 20:17:49 +08:00
Amazing_DM
6b4368153c Merge pull request #244 from NormanBB/master
新增新手入门教程
2020-02-05 04:10:04 -06:00
NormanBB
4ec5cf2e23 Update Basic-usage.md 2020-02-05 16:26:53 +08:00
NormanBB
244b1fba29 Update README.zh-CN.md 2020-02-05 16:22:25 +08:00
NormanBB
079d390933 Update README.zh-CN.md 2020-02-05 16:03:59 +08:00
NormanBB
d2af068325 Update README.zh-CN.md 2020-02-05 16:00:10 +08:00
NormanBB
6445bf633e Update README.zh-CN.md 2020-02-05 15:39:19 +08:00
NormanBB
282957f8bd Update Basic-usage.md 2020-02-05 15:31:27 +08:00
NormanBB
5bb320a08c Add files via upload 2020-02-05 14:31:32 +08:00
NormanBB
4178d363a9 Update Basic-usage.md 2020-02-05 12:23:57 +08:00
NormanBB
20f232b086 Update README.zh-CN.md 2020-02-05 12:17:00 +08:00
NormanBB
bb365279d6 Create Basic-usage.md 2020-02-05 12:10:43 +08:00
NormanBB
e5126e728e Update README.zh-CN.md 2020-02-05 12:07:22 +08:00
Connection Refused
5c5318cd25 Update README.zh-CN.md 2020-02-04 12:49:21 +08:00
Connection Refused
3cef06a786 Update README.zh-CN.md 2020-02-04 12:48:52 +08:00
Connection Refused
15e5e4f735 Update README.md 2020-02-04 12:48:27 +08:00
Andy1999
6697d4454d 图太大了重新调整一下大小 2020-02-04 00:57:57 +08:00
Andy1999
9a047014cf 新增 NyanCAT 赞助商
豪华赞助
2020-02-04 00:56:34 +08:00
Connection Refused
af7b618551 Update README.zh-CN.md 2020-02-03 21:31:11 +08:00
Connection Refused
e01436c434 Update README.md 2020-02-03 21:30:59 +08:00
Tindy X
b312534d06 Fix a bug
Clean up codes.
2020-01-30 17:06:11 +08:00
Tindy X
54ab6618bd Update submodule 2020-01-30 17:01:05 +08:00
37 changed files with 1668 additions and 961 deletions

View File

@@ -1,14 +1,89 @@
using System;
using Netch.Forms;
using System;
using System.Diagnostics;
using System.IO;
using System.Net;
using System.Threading;
namespace Netch.Controllers
{
public class DNSController
{
public static DNS.Server.DnsServer Server = new DNS.Server.DnsServer(new Resolver());
/// <summary>
/// 进程实例
/// </summary>
public Process Instance;
/// <summary>
/// 启动NatTypeTester
/// </summary>
/// <returns></returns>
public bool Start()
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Starting dns2tcp Service")}");
try
{
if (!File.Exists("bin\\dns2tcp.exe"))
{
return false;
}
Instance = MainController.GetProcess();
Instance.StartInfo.FileName = "bin\\dns2tcp.exe";
Instance.StartInfo.Arguments = " -L 127.0.0.1:53 -R 1.1.1.1:53";
Instance.OutputDataReceived += OnOutputDataReceived;
Instance.ErrorDataReceived += OnOutputDataReceived;
Instance.Start();
Instance.BeginOutputReadLine();
Instance.BeginErrorReadLine();
return true;
}
catch (Exception)
{
Utils.Logging.Info("dns2tcp 进程出错");
Stop();
return false;
}
}
/// <summary>
/// 停止
/// </summary>
public void Stop()
{
try
{
if (Instance != null && !Instance.HasExited)
{
Instance.Kill();
}
}
catch (Exception e)
{
Utils.Logging.Info(e.ToString());
}
}
public void OnOutputDataReceived(object sender, DataReceivedEventArgs e)
{
if (!string.IsNullOrWhiteSpace(e.Data))
{
if (File.Exists("logging\\dns2tcp.log"))
{
File.Delete("logging\\dns2tcp.log");
}
File.AppendAllText("logging\\dns2tcp.log", $"{e.Data}\r\n");
}
}
/* public static DNS.Server.DnsServer Server = new DNS.Server.DnsServer(new Resolver());
public bool Start()
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting LocalDns service")}");
try
{
_ = Server.Listen(new IPEndPoint(IPAddress.IPv6Any, 53));
@@ -32,6 +107,6 @@ namespace Netch.Controllers
{
Utils.Logging.Info(e.ToString());
}
}
}*/
}
}

View File

@@ -1,6 +1,7 @@
using System;
using System.Diagnostics;
using System.IO;
using System.Threading.Tasks;
namespace Netch.Controllers
{
@@ -51,6 +52,11 @@ namespace Netch.Controllers
/// </summary>
public TUNTAPController pTUNTAPController;
/// <summary>
/// NTT 控制器
/// </summary>
public NTTController pNTTController;
/// <summary>
/// 启动
/// </summary>
@@ -106,8 +112,18 @@ namespace Netch.Controllers
{
pNFController = new NFController();
}
if (pNTTController == null)
{
pNTTController = new NTTController();
}
// 进程代理模式,启动 NF 控制器
result = pNFController.Start(server, mode);
Task.Run(() =>
{
pNTTController.Start();
});
}
else if (mode.Type == 1)
{
@@ -115,8 +131,17 @@ namespace Netch.Controllers
{
pTUNTAPController = new TUNTAPController();
}
if (pNTTController == null)
{
pNTTController = new NTTController();
}
// TUN/TAP 黑名单代理模式,启动 TUN/TAP 控制器
result = pTUNTAPController.Start(server, mode);
Task.Run(() =>
{
pNTTController.Start();
});
}
else if (mode.Type == 2)
{
@@ -124,8 +149,17 @@ namespace Netch.Controllers
{
pTUNTAPController = new TUNTAPController();
}
if (pNTTController == null)
{
pNTTController = new NTTController();
}
// TUN/TAP 白名单代理模式,启动 TUN/TAP 控制器
result = pTUNTAPController.Start(server, mode);
Task.Run(() =>
{
pNTTController.Start();
});
}
else if (mode.Type == 3 || mode.Type == 5)
{
@@ -171,7 +205,7 @@ namespace Netch.Controllers
{
pVMessController.Stop();
}
if (pNFController != null)
{
pNFController.Stop();
@@ -184,10 +218,15 @@ namespace Netch.Controllers
{
pHTTPController.Stop();
}
if (pNTTController != null)
{
pNTTController.Stop();
}
}
public void KillProcess(string name) {
public void KillProcess(string name)
{
var processes = Process.GetProcessesByName(name);
foreach (var p in processes)
{
@@ -198,7 +237,7 @@ namespace Netch.Controllers
}
}
private static bool IsChildProcess(Process process,string name)
private static bool IsChildProcess(Process process, string name)
{
bool result;
try

View File

@@ -1,4 +1,5 @@
using System;
using Netch.Forms;
using System;
using System.Diagnostics;
using System.IO;
using System.ServiceProcess;
@@ -39,6 +40,7 @@ namespace Netch.Controllers
/// <returns>是否成功</returns>
public bool Start(Models.Server server, Models.Mode mode)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting Redirector")}");
if (!File.Exists("bin\\Redirector.exe"))
{
return false;
@@ -98,6 +100,7 @@ namespace Netch.Controllers
var service = new ServiceController("netfilter2");
if (service.Status == ServiceControllerStatus.Stopped)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting netfilter2 Service")}");
service.Start();
}
}
@@ -113,7 +116,8 @@ namespace Netch.Controllers
}
}
var processes = "";
var processes = "NTT.exe,";
foreach (var proc in mode.Rule)
{
processes += proc;
@@ -147,7 +151,7 @@ namespace Netch.Controllers
}
}
Instance.StartInfo.Arguments = fallback + $" -t {Global.Settings.RedirectorTCPPort}";
Instance.StartInfo.Arguments = fallback;
Instance.OutputDataReceived += OnOutputDataReceived;
Instance.ErrorDataReceived += OnOutputDataReceived;
State = Models.State.Starting;
@@ -155,7 +159,6 @@ namespace Netch.Controllers
Instance.BeginOutputReadLine();
Instance.BeginErrorReadLine();
var IsFallback = false;
for (var i = 0; i < 1000; i++)
{
Thread.Sleep(10);
@@ -164,33 +167,6 @@ namespace Netch.Controllers
{
return true;
}
if (State == Models.State.Stopped)
{
if (!IsFallback)
{
IsFallback = true;
Stop();
Utils.Logging.Info($"尝试去除 \"-t {Global.Settings.RedirectorTCPPort}\" 参数后启动 \"bin\\Redirector.exe\"");
Instance.StartInfo.Arguments = fallback;
Utils.Logging.Info($"当前 \"bin\\Redirector.exe\" 启动参数为 \"{Instance.StartInfo.Arguments}\"");
Global.Settings.RedirectorTCPPort = 2800;
Instance.CancelOutputRead();
Instance.CancelErrorRead();
Instance.OutputDataReceived += OnOutputDataReceived;
Instance.ErrorDataReceived += OnOutputDataReceived;
State = Models.State.Starting;
Instance.Start();
Instance.BeginOutputReadLine();
Instance.BeginErrorReadLine();
}
else
{
Utils.Logging.Info("NF 进程启动失败");
Stop();
return false;
}
}
}
Utils.Logging.Info("NF 进程启动超时");
@@ -229,7 +205,7 @@ namespace Netch.Controllers
{
State = Models.State.Stopped;
}
else if (e.Data.Contains("Started"))
else if (e.Data.Contains("Redirect to"))
{
State = Models.State.Started;
}

View File

@@ -0,0 +1,95 @@
using Netch.Forms;
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
namespace Netch.Controllers
{
public class NTTController
{
/// <summary>
/// 进程实例
/// </summary>
public Process Instance;
/// <summary>
/// 当前状态
/// </summary>
public Models.State State = Models.State.Waiting;
/// <summary>
/// 启动NatTypeTester
/// </summary>
/// <returns></returns>
public (bool, string, string, string) Start()
{
MainForm.Instance.NatTypeStatusText($"{Utils.i18N.Translate("Starting NatTester")}");
try
{
if (!File.Exists("bin\\NTT.exe"))
{
return (false, null, null, null);
}
Instance = MainController.GetProcess();
Instance.StartInfo.FileName = "bin\\NTT.exe";
Instance.StartInfo.Arguments = $" {Global.Settings.STUN_Server} {Global.Settings.STUN_Server_Port}";
Instance.OutputDataReceived += OnOutputDataReceived;
Instance.ErrorDataReceived += OnOutputDataReceived;
State = Models.State.Starting;
Instance.Start();
Instance.BeginOutputReadLine();
Instance.BeginErrorReadLine();
Instance.WaitForExit();
string[] result = File.ReadAllText("logging\\NTT.log").ToString().Split('#');
var natType = result[0];
var localEnd = result[1];
var publicEnd = result[2];
MainForm.Instance.NatTypeStatusText(natType);
return (true, natType, localEnd, publicEnd);
}
catch (Exception)
{
Utils.Logging.Info("NTT 进程出错");
Stop();
return (false, null, null, null);
}
}
/// <summary>
/// 停止
/// </summary>
public void Stop()
{
try
{
if (Instance != null && !Instance.HasExited)
{
Instance.Kill();
}
}
catch (Exception e)
{
Utils.Logging.Info(e.ToString());
}
}
public void OnOutputDataReceived(object sender, DataReceivedEventArgs e)
{
if (!string.IsNullOrWhiteSpace(e.Data))
{
if (File.Exists("logging\\NTT.log"))
{
File.Delete("logging\\NTT.log");
}
File.AppendAllText("logging\\NTT.log", $"{e.Data}\r\n");
}
}
}
}

View File

@@ -1,4 +1,5 @@
using System;
using Netch.Forms;
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
@@ -25,6 +26,7 @@ namespace Netch.Controllers
/// <returns>是否启动成功</returns>
public bool Start(Models.Server server, Models.Mode mode)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting Shadowsocks")}");
if (!File.Exists("bin\\Shadowsocks.exe"))
{
return false;

View File

@@ -1,4 +1,5 @@
using System;
using Netch.Forms;
using System;
using System.Diagnostics;
using System.IO;
using System.Threading;
@@ -25,6 +26,7 @@ namespace Netch.Controllers
/// <returns>是否启动成功</returns>
public bool Start(Models.Server server, Models.Mode mode)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting ShadowsocksR")}");
if (!File.Exists("bin\\ShadowsocksR.exe"))
{
return false;

View File

@@ -4,6 +4,8 @@ using System.IO;
using System.Net;
using System.Text;
using System.Threading;
using Netch.Forms;
using Netch.Utils;
namespace Netch.Controllers
{
@@ -31,7 +33,7 @@ namespace Netch.Controllers
public Models.Mode SavedMode = new Models.Mode();
/// <summary>
/// 本地 DNS 服务控制器
/// 本地 DNS 服务控制器
/// </summary>
public DNSController pDNSController = new DNSController();
@@ -61,6 +63,7 @@ namespace Netch.Controllers
/// </summary>
public bool SetupBypass()
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("SetupBypass")}");
// 让服务器 IP 走直连
foreach (var address in ServerAddresses)
{
@@ -240,6 +243,7 @@ namespace Netch.Controllers
/// <returns>是否成功</returns>
public bool Start(Models.Server server, Models.Mode mode)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting Tap")}");
foreach (var proc in Process.GetProcessesByName("tun2socks"))
{
try
@@ -269,12 +273,16 @@ namespace Netch.Controllers
{
return false;
}
Logging.Info("设置绕行规则");
SetupBypass();
Logging.Info("设置绕行规则完毕");
Instance = new Process();
Instance.StartInfo.WorkingDirectory = string.Format("{0}\\bin", Directory.GetCurrentDirectory());
Instance.StartInfo.FileName = string.Format("{0}\\bin\\tun2socks.exe", Directory.GetCurrentDirectory());
var adapterName = TUNTAP.GetName(Global.TUNTAP.ComponentID);
Logging.Info($"tun2sock使用适配器{adapterName}");
string dns;
if (Global.Settings.TUNTAP.UseCustomDNS)
@@ -293,16 +301,17 @@ namespace Netch.Controllers
{
pDNSController.Start();
dns = "127.0.0.1";
//dns = "1.1.1.1,1.0.0.1";
}
if (server.Type == "Socks5")
{
Instance.StartInfo.Arguments = string.Format("-proxyServer {0}:{1} -tunAddr {2} -tunMask {3} -tunGw {4} -tunDns {5} -tunName \"{6}\"", server.Hostname, server.Port, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, Global.TUNTAP.Adapter.Name);
Instance.StartInfo.Arguments = string.Format("-proxyServer {0}:{1} -tunAddr {2} -tunMask {3} -tunGw {4} -tunDns {5} -tunName \"{6}\"", server.Hostname, server.Port, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, adapterName);
}
else
{
Instance.StartInfo.Arguments = string.Format("-proxyServer 127.0.0.1:{0} -tunAddr {1} -tunMask {2} -tunGw {3} -tunDns {4} -tunName \"{5}\"", Global.Settings.Socks5LocalPort, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, Global.TUNTAP.Adapter.Name);
}
Instance.StartInfo.Arguments = string.Format("-proxyServer 127.0.0.1:{0} -tunAddr {1} -tunMask {2} -tunGw {3} -tunDns {4} -tunName \"{5}\"", Global.Settings.Socks5LocalPort, Global.Settings.TUNTAP.Address, Global.Settings.TUNTAP.Netmask, Global.Settings.TUNTAP.Gateway, dns, adapterName);
}
Instance.StartInfo.CreateNoWindow = true;
Instance.StartInfo.RedirectStandardError = true;
@@ -353,6 +362,7 @@ namespace Netch.Controllers
//pDNSController.Stop();
//修复点击停止按钮后再启动DNS服务没监听的BUG
ClearBypass();
pDNSController.Stop();
}
catch (Exception e)
{

View File

@@ -26,7 +26,7 @@ namespace Netch.Controllers
public const string Name = @"Netch";
public const string Copyright = @"Copyright © 2019 - 2020";
public const string Version = @"1.3.7";
public const string Version = @"1.4.0";
public async void Check(bool notifyNoFound, bool isPreRelease)
{

View File

@@ -1,4 +1,5 @@
using System;
using Netch.Forms;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
@@ -26,6 +27,7 @@ namespace Netch.Controllers
/// <returns>是否启动成功</returns>
public bool Start(Models.Server server, Models.Mode mode)
{
MainForm.Instance.StatusText($"{Utils.i18N.Translate("Status")}{Utils.i18N.Translate(": ")}{Utils.i18N.Translate("Starting V2ray")}");
if (!File.Exists("bin\\v2ray.exe") || !File.Exists("bin\\v2ctl.exe"))
{
return false;

File diff suppressed because it is too large Load Diff

View File

@@ -1,4 +1,4 @@
using Netch.Controllers;
using Netch.Controllers;
using System;
using System.Collections.Generic;
using System.Diagnostics;
@@ -41,6 +41,11 @@ namespace Netch.Forms
public List<Button> ProfileButtons = new List<Button>();
/// <summary>
/// 主窗体的静态实例
/// </summary>
public static MainForm Instance = null;
public MainForm()
{
InitializeComponent();
@@ -48,6 +53,7 @@ namespace Netch.Forms
CheckForIllegalCrossThreadCalls = false;
// MenuStrip.Renderer = new Override.ToolStripProfessionalRender();
Instance = this;
}
private void CheckUpdate()
@@ -204,6 +210,17 @@ namespace Netch.Forms
SelectLastMode();
}
public void UpdateMode(Models.Mode NewMode, Models.Mode OldMode)
{
ModeComboBox.Items.Clear();
Global.ModeFiles.Remove(OldMode);
Global.ModeFiles.Add(NewMode);
var array = Global.ModeFiles.ToArray();
Array.Sort(array, (a, b) => string.Compare(a.Remark, b.Remark, StringComparison.Ordinal));
ModeComboBox.Items.AddRange(array);
SelectLastMode();
}
private void SaveConfigs()
{
@@ -221,60 +238,66 @@ namespace Netch.Forms
private void ComboBox_DrawItem(object sender, DrawItemEventArgs e)
{
var cbx = sender as ComboBox;
// 绘制背景颜色
e.Graphics.FillRectangle(new SolidBrush(Color.White), e.Bounds);
if (e.Index >= 0)
try
{
// 绘制 备注/名称 字符串
e.Graphics.DrawString(cbx.Items[e.Index].ToString(), cbx.Font, new SolidBrush(Color.Black), e.Bounds);
if (cbx.Items[e.Index] is Models.Server)
var cbx = sender as ComboBox;
// 绘制背景颜色
e.Graphics.FillRectangle(new SolidBrush(Color.White), e.Bounds);
if (e.Index >= 0)
{
var item = cbx.Items[e.Index] as Models.Server;
// 绘制 备注/名称 字符串
e.Graphics.DrawString(cbx.Items[e.Index].ToString(), cbx.Font, new SolidBrush(Color.Black), e.Bounds);
// 计算延迟底色
SolidBrush brush;
if (item.Delay > 200)
if (cbx.Items[e.Index] is Models.Server)
{
// 红色
brush = new SolidBrush(Color.Red);
var item = cbx.Items[e.Index] as Models.Server;
// 计算延迟底色
SolidBrush brush;
if (item.Delay > 200)
{
// 红色
brush = new SolidBrush(Color.Red);
}
else if (item.Delay > 80)
{
// 黄色
brush = new SolidBrush(Color.Yellow);
}
else if (item.Delay >= 0)
{
// 绿色
brush = new SolidBrush(Color.FromArgb(50, 255, 56));
}
else
{
// 灰色
brush = new SolidBrush(Color.Gray);
}
// 绘制延迟底色
e.Graphics.FillRectangle(brush, ServerComboBox.Size.Width - 60, e.Bounds.Y, 60, e.Bounds.Height);
// 绘制延迟字符串
e.Graphics.DrawString(item.Delay.ToString(), cbx.Font, new SolidBrush(Color.Black), ServerComboBox.Size.Width - 58, e.Bounds.Y);
}
else if (item.Delay > 80)
else if (cbx.Items[e.Index] is Models.Mode)
{
// 黄色
brush = new SolidBrush(Color.Yellow);
var item = cbx.Items[e.Index] as Models.Mode;
// 绘制延迟底色
e.Graphics.FillRectangle(new SolidBrush(Color.Gray), ServerComboBox.Size.Width - 60, e.Bounds.Y, 60, e.Bounds.Height);
// 绘制延迟字符串
e.Graphics.DrawString(item.Rule.Count.ToString(), cbx.Font, new SolidBrush(Color.Black), ServerComboBox.Size.Width - 58, e.Bounds.Y);
}
else if (item.Delay >= 0)
{
// 绿色
brush = new SolidBrush(Color.FromArgb(50, 255, 56));
}
else
{
// 灰色
brush = new SolidBrush(Color.Gray);
}
// 绘制延迟底色
e.Graphics.FillRectangle(brush, ServerComboBox.Size.Width - 60, e.Bounds.Y, 60, e.Bounds.Height);
// 绘制延迟字符串
e.Graphics.DrawString(item.Delay.ToString(), cbx.Font, new SolidBrush(Color.Black), ServerComboBox.Size.Width - 58, e.Bounds.Y);
}
else if (cbx.Items[e.Index] is Models.Mode)
{
var item = cbx.Items[e.Index] as Models.Mode;
// 绘制延迟底色
e.Graphics.FillRectangle(new SolidBrush(Color.Gray), ServerComboBox.Size.Width - 60, e.Bounds.Y, 60, e.Bounds.Height);
// 绘制延迟字符串
e.Graphics.DrawString(item.Rule.Count.ToString(), cbx.Font, new SolidBrush(Color.Black), ServerComboBox.Size.Width - 58, e.Bounds.Y);
}
}
catch (Exception)
{ }
}
private void MainForm_Load(object sender, EventArgs e)
@@ -545,6 +568,7 @@ namespace Netch.Forms
MenuStrip.Enabled = ConfigurationGroupBox.Enabled = ControlButton.Enabled = SettingsButton.Enabled = true;
ControlButton.Text = Utils.i18N.Translate("Start");
MainController.Stop();
NatTypeStatusLabel.Text = "";
}
Utils.Configuration.Save();
}).ContinueWith(task =>
@@ -748,6 +772,7 @@ namespace Netch.Forms
private void ControlButton_Click(object sender, EventArgs e)
{
SaveConfigs();
if (State == Models.State.Waiting || State == Models.State.Stopped)
{
// 当前 ServerComboBox 中至少有一项
@@ -775,11 +800,34 @@ namespace Netch.Forms
var mode = ModeComboBox.SelectedItem as Models.Mode;
MainController = new MainController();
if (MainController.Start(server, mode))
var startResult = MainController.Start(server, mode);
if (startResult)
{
// UsedBandwidthLabel.Visible = UploadSpeedLabel.Visible = DownloadSpeedLabel.Visible = true;
// MainController.pNFController.OnBandwidthUpdated += OnBandwidthUpdated;
// 如果勾选启动后最小化
if (Global.Settings.MinimizeWhenStarted)
{
WindowState = FormWindowState.Minimized;
NotifyIcon.Visible = true;
if (IsFirstOpened)
{
// 显示提示语
NotifyIcon.ShowBalloonTip(5,
UpdateChecker.Name,
Utils.i18N.Translate("Netch is now minimized to the notification bar, double click this icon to restore."),
ToolTipIcon.Info);
IsFirstOpened = false;
}
Hide();
}
ControlButton.Enabled = true;
ControlButton.Text = Utils.i18N.Translate("Stop");
@@ -852,6 +900,7 @@ namespace Netch.Forms
var mode = ModeComboBox.SelectedItem as Models.Mode;
MainController.Stop();
NatTypeStatusLabel.Text = "";
// LastUploadBandwidth = 0;
// LastDownloadBandwidth = 0;
@@ -1019,7 +1068,7 @@ namespace Netch.Forms
public void InitProfile()
{
var num_profile = 4;
var num_profile = Global.Settings.ProfileCount;
ProfileTable.ColumnCount = num_profile;
while (Global.Settings.profiles.Count < num_profile)
@@ -1108,5 +1157,75 @@ namespace Netch.Forms
Global.Settings.profiles[index] = new Models.Profile(selectedServer, selectedMode, name);
}
private void EditModePictureBox_Click(object sender, EventArgs e)
{
// 当前ModeComboBox中至少有一项
if (ModeComboBox.Items.Count > 0 && ModeComboBox.SelectedIndex != -1)
{
SaveConfigs();
var selectedMode = (Models.Mode)ModeComboBox.SelectedItem;
// 只允许修改进程加速的模式
if (selectedMode.Type == 0)
{
//Process.Start(Environment.CurrentDirectory + "\\mode\\" + selectedMode.FileName + ".txt");
Mode.Process process = new Mode.Process(selectedMode);
process.Text = "Edit Process Mode";
process.Show();
Hide();
}
}
else
{
MessageBox.Show(Utils.i18N.Translate("Please select an mode first"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
private void DeleteModePictureBox_Click(object sender, EventArgs e)
{
// 当前ModeComboBox中至少有一项
if (ModeComboBox.Items.Count > 0 && ModeComboBox.SelectedIndex != -1)
{
var selectedMode = (Models.Mode)ModeComboBox.SelectedItem;
//删除模式文件
selectedMode.DeleteFile("mode");
ModeComboBox.Items.Clear();
Global.ModeFiles.Remove(selectedMode);
var array = Global.ModeFiles.ToArray();
Array.Sort(array, (a, b) => string.Compare(a.Remark, b.Remark, StringComparison.Ordinal));
ModeComboBox.Items.AddRange(array);
SelectLastMode();
Utils.Configuration.Save();
}
else
{
MessageBox.Show(Utils.i18N.Translate("Please select an mode first"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
private void CopyLinkPictureBox_Click(object sender, EventArgs e)
{
// 当前ServerComboBox中至少有一项
if (ServerComboBox.SelectedIndex != -1)
{
var selectedMode = (Models.Server)ServerComboBox.SelectedItem;
Clipboard.SetText(Utils.ShareLink.GetShareLink(selectedMode));
}
else
{
MessageBox.Show(Utils.i18N.Translate("Please select a server first"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
public void StatusText(string text)
{
StatusLabel.Text = text;
}
public void NatTypeStatusText(string text)
{
NatTypeStatusLabel.Text = "NatType:" + text;
}
}
}

View File

@@ -160,6 +160,7 @@
this.RuleListBox.Name = "RuleListBox";
this.RuleListBox.Size = new System.Drawing.Size(328, 123);
this.RuleListBox.TabIndex = 2;
this.RuleListBox.MouseUp += new System.Windows.Forms.MouseEventHandler(this.RuleListBox_MouseUp);
//
// RemarkTextBox
//

View File

@@ -7,11 +7,45 @@ namespace Netch.Forms.Mode
{
public partial class Process : Form
{
//用于判断当前窗口是否为编辑模式
private Boolean EditMode = false;
//被编辑模式坐标
private Models.Mode EditMode_Old = null;
/// <summary>
/// 编辑模式
/// </summary>
/// <param name="mode">模式</param>
public Process(Models.Mode mode)
{
InitializeComponent();
CheckForIllegalCrossThreadCalls = false;
EditMode_Old = mode;
this.Text = "Edit Process Mode";
//循环填充已有规则
mode.Rule.ForEach(i => RuleListBox.Items.Add(i));
EditMode = true;
StaySameButton.Enabled = false;
TimeDataButton.Enabled = false;
FilenameTextBox.Enabled = false;
FilenameLabel.Enabled = false;
UseCustomFilenameBox.Enabled = false;
FilenameTextBox.Text = mode.FileName;
RemarkTextBox.Text = mode.Remark;
}
public Process()
{
InitializeComponent();
CheckForIllegalCrossThreadCalls = false;
EditMode = false;
EditMode_Old = null;
}
/// <summary>
@@ -91,6 +125,27 @@ namespace Netch.Forms.Mode
Global.MainForm.Show();
}
/// <summary>
/// listBox右键菜单
/// </summary>
private void RuleListBox_MouseUp(object sender, MouseEventArgs e)
{
ContextMenuStrip strip = new ContextMenuStrip();
strip.Items.Add(Utils.i18N.Translate("Delete"));
if (e.Button == MouseButtons.Right)
{
strip.Show(this.RuleListBox, e.Location);//鼠标右键按下弹出菜单
strip.MouseClick += new MouseEventHandler(deleteRule_Click);
}
}
void deleteRule_Click(object sender, EventArgs e)
{
if (RuleListBox.SelectedIndex != -1)
{
RuleListBox.Items.RemoveAt(RuleListBox.SelectedIndex);
}
}
private void AddButton_Click(object sender, EventArgs e)
{
if (!string.IsNullOrWhiteSpace(ProcessNameTextBox.Text))
@@ -134,43 +189,16 @@ namespace Netch.Forms.Mode
private void ControlButton_Click(object sender, EventArgs e)
{
// 自定义文件名
if (UseCustomFilenameBox.Checked)
if (EditMode)
{
Global.Settings.ModeFileNameType = 0;
}
// 使用和备注一致的文件名
else if (StaySameButton.Checked)
{
Global.Settings.ModeFileNameType = 1;
FilenameTextBox.Text = RemarkTextBox.Text;
}
// 使用时间数据作为文件名
else
{
Global.Settings.ModeFileNameType = 2;
FilenameTextBox.Text = ((long)(DateTime.UtcNow - new DateTime(1970, 1, 1)).TotalMilliseconds).ToString();
}
Utils.Configuration.Save();
if (!string.IsNullOrWhiteSpace(RemarkTextBox.Text))
{
var ModeFilename = Path.Combine("mode", FilenameTextBox.Text);
// 如果文件已存在,返回
if (File.Exists(ModeFilename + ".txt"))
{
MessageBox.Show(Utils.i18N.Translate("File already exists.\n Please Change the filename"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
// 编辑模式
if (RuleListBox.Items.Count != 0)
{
var mode = new Models.Mode
{
BypassChina = false,
FileName = ModeFilename,
FileName = FilenameTextBox.Text,
Type = 0,
Remark = RemarkTextBox.Text
};
@@ -190,11 +218,11 @@ namespace Netch.Forms.Mode
Directory.CreateDirectory("mode");
}
File.WriteAllText(ModeFilename + ".txt", text);
File.WriteAllText(Path.Combine("mode", FilenameTextBox.Text) + ".txt", text);
MessageBox.Show(Utils.i18N.Translate("Mode added successfully"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
MessageBox.Show(Utils.i18N.Translate("Mode updated successfully"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
Global.MainForm.AddMode(mode);
Global.MainForm.UpdateMode(mode, EditMode_Old);
Close();
}
else
@@ -204,9 +232,84 @@ namespace Netch.Forms.Mode
}
else
{
MessageBox.Show(Utils.i18N.Translate("Please enter a mode remark"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
// 自定义文件名
if (UseCustomFilenameBox.Checked)
{
Global.Settings.ModeFileNameType = 0;
}
// 使用和备注一致的文件名
else if (StaySameButton.Checked)
{
Global.Settings.ModeFileNameType = 1;
FilenameTextBox.Text = RemarkTextBox.Text;
}
// 使用时间数据作为文件名
else
{
Global.Settings.ModeFileNameType = 2;
FilenameTextBox.Text = ((long)(DateTime.UtcNow - new DateTime(1970, 1, 1)).TotalMilliseconds).ToString();
}
Utils.Configuration.Save();
if (!string.IsNullOrWhiteSpace(RemarkTextBox.Text))
{
if (Global.Settings.ModeFileNameType == 0 && string.IsNullOrWhiteSpace(FilenameTextBox.Text))
{
MessageBox.Show(Utils.i18N.Translate("Please enter a mode filename"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
var ModeFilename = Path.Combine("mode", FilenameTextBox.Text);
// 如果文件已存在,返回
if (File.Exists(ModeFilename + ".txt"))
{
MessageBox.Show(Utils.i18N.Translate("File already exists.\n Please Change the filename"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
if (RuleListBox.Items.Count != 0)
{
var mode = new Models.Mode
{
BypassChina = false,
FileName = ModeFilename,
Type = 0,
Remark = RemarkTextBox.Text
};
var text = $"# {RemarkTextBox.Text}, 0\r\n";
foreach (var item in RuleListBox.Items)
{
var process = item as string;
mode.Rule.Add(process);
text += process + "\r\n";
}
text = text.Substring(0, text.Length - 2);
if (!Directory.Exists("mode"))
{
Directory.CreateDirectory("mode");
}
File.WriteAllText(ModeFilename + ".txt", text);
MessageBox.Show(Utils.i18N.Translate("Mode added successfully"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
Global.MainForm.AddMode(mode);
Close();
}
else
{
MessageBox.Show(Utils.i18N.Translate("Unable to add empty rule"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
else
{
MessageBox.Show(Utils.i18N.Translate("Please enter a mode remark"), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
}
}
}
private void UseCustomFileNameBox_CheckedChanged(object sender, EventArgs e)

View File

@@ -30,8 +30,6 @@
{
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(SettingForm));
this.PortGroupBox = new System.Windows.Forms.GroupBox();
this.RedirectorLabel = new System.Windows.Forms.Label();
this.RedirectorTextBox = new System.Windows.Forms.TextBox();
this.AllowDevicesCheckBox = new System.Windows.Forms.CheckBox();
this.HTTPPortLabel = new System.Windows.Forms.Label();
this.HTTPPortTextBox = new System.Windows.Forms.TextBox();
@@ -50,6 +48,14 @@
this.ControlButton = new System.Windows.Forms.Button();
this.GlobalBypassIPsButton = new System.Windows.Forms.Button();
this.BehaviorGroupBox = new System.Windows.Forms.GroupBox();
this.STUN_ServerPortTextBox = new System.Windows.Forms.TextBox();
this.label2 = new System.Windows.Forms.Label();
this.label1 = new System.Windows.Forms.Label();
this.RunAtStartup = new System.Windows.Forms.CheckBox();
this.STUN_ServerTextBox = new System.Windows.Forms.TextBox();
this.MinimizeWhenStartedCheckBox = new System.Windows.Forms.CheckBox();
this.ProfileCount_Label = new System.Windows.Forms.Label();
this.ProfileCount_TextBox = new System.Windows.Forms.TextBox();
this.CheckUpdateWhenOpenedCheckBox = new System.Windows.Forms.CheckBox();
this.StartWhenOpenedCheckBox = new System.Windows.Forms.CheckBox();
this.StopWhenExitedCheckBox = new System.Windows.Forms.CheckBox();
@@ -61,48 +67,24 @@
//
// PortGroupBox
//
this.PortGroupBox.Controls.Add(this.RedirectorLabel);
this.PortGroupBox.Controls.Add(this.RedirectorTextBox);
this.PortGroupBox.Controls.Add(this.AllowDevicesCheckBox);
this.PortGroupBox.Controls.Add(this.HTTPPortLabel);
this.PortGroupBox.Controls.Add(this.HTTPPortTextBox);
this.PortGroupBox.Controls.Add(this.Socks5PortLabel);
this.PortGroupBox.Controls.Add(this.Socks5PortTextBox);
this.PortGroupBox.Location = new System.Drawing.Point(15, 15);
this.PortGroupBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.PortGroupBox.Location = new System.Drawing.Point(12, 12);
this.PortGroupBox.Name = "PortGroupBox";
this.PortGroupBox.Padding = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.PortGroupBox.Size = new System.Drawing.Size(525, 175);
this.PortGroupBox.Size = new System.Drawing.Size(420, 140);
this.PortGroupBox.TabIndex = 0;
this.PortGroupBox.TabStop = false;
this.PortGroupBox.Text = "Local Port";
//
// RedirectorLabel
//
this.RedirectorLabel.AutoSize = true;
this.RedirectorLabel.Location = new System.Drawing.Point(11, 138);
this.RedirectorLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.RedirectorLabel.Name = "RedirectorLabel";
this.RedirectorLabel.Size = new System.Drawing.Size(119, 20);
this.RedirectorLabel.TabIndex = 6;
this.RedirectorLabel.Text = "Redirector TCP";
//
// RedirectorTextBox
//
this.RedirectorTextBox.Location = new System.Drawing.Point(150, 134);
this.RedirectorTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.RedirectorTextBox.Name = "RedirectorTextBox";
this.RedirectorTextBox.Size = new System.Drawing.Size(366, 27);
this.RedirectorTextBox.TabIndex = 7;
this.RedirectorTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// AllowDevicesCheckBox
//
this.AllowDevicesCheckBox.AutoSize = true;
this.AllowDevicesCheckBox.Location = new System.Drawing.Point(150, 100);
this.AllowDevicesCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.AllowDevicesCheckBox.Location = new System.Drawing.Point(120, 80);
this.AllowDevicesCheckBox.Name = "AllowDevicesCheckBox";
this.AllowDevicesCheckBox.Size = new System.Drawing.Size(259, 24);
this.AllowDevicesCheckBox.Size = new System.Drawing.Size(206, 21);
this.AllowDevicesCheckBox.TabIndex = 5;
this.AllowDevicesCheckBox.Text = "Allow other Devices to connect";
this.AllowDevicesCheckBox.TextAlign = System.Drawing.ContentAlignment.MiddleRight;
@@ -111,38 +93,34 @@
// HTTPPortLabel
//
this.HTTPPortLabel.AutoSize = true;
this.HTTPPortLabel.Location = new System.Drawing.Point(11, 68);
this.HTTPPortLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.HTTPPortLabel.Location = new System.Drawing.Point(9, 54);
this.HTTPPortLabel.Name = "HTTPPortLabel";
this.HTTPPortLabel.Size = new System.Drawing.Size(48, 20);
this.HTTPPortLabel.Size = new System.Drawing.Size(38, 17);
this.HTTPPortLabel.TabIndex = 3;
this.HTTPPortLabel.Text = "HTTP";
//
// HTTPPortTextBox
//
this.HTTPPortTextBox.Location = new System.Drawing.Point(150, 64);
this.HTTPPortTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.HTTPPortTextBox.Location = new System.Drawing.Point(120, 51);
this.HTTPPortTextBox.Name = "HTTPPortTextBox";
this.HTTPPortTextBox.Size = new System.Drawing.Size(366, 27);
this.HTTPPortTextBox.Size = new System.Drawing.Size(294, 23);
this.HTTPPortTextBox.TabIndex = 4;
this.HTTPPortTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// Socks5PortLabel
//
this.Socks5PortLabel.AutoSize = true;
this.Socks5PortLabel.Location = new System.Drawing.Point(11, 31);
this.Socks5PortLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.Socks5PortLabel.Location = new System.Drawing.Point(9, 25);
this.Socks5PortLabel.Name = "Socks5PortLabel";
this.Socks5PortLabel.Size = new System.Drawing.Size(60, 20);
this.Socks5PortLabel.Size = new System.Drawing.Size(49, 17);
this.Socks5PortLabel.TabIndex = 0;
this.Socks5PortLabel.Text = "Socks5";
//
// Socks5PortTextBox
//
this.Socks5PortTextBox.Location = new System.Drawing.Point(150, 28);
this.Socks5PortTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.Socks5PortTextBox.Location = new System.Drawing.Point(120, 22);
this.Socks5PortTextBox.Name = "Socks5PortTextBox";
this.Socks5PortTextBox.Size = new System.Drawing.Size(366, 27);
this.Socks5PortTextBox.Size = new System.Drawing.Size(294, 23);
this.Socks5PortTextBox.TabIndex = 1;
this.Socks5PortTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
@@ -157,11 +135,9 @@
this.TUNTAPGroupBox.Controls.Add(this.TUNTAPNetmaskTextBox);
this.TUNTAPGroupBox.Controls.Add(this.TUNTAPAddressLabel);
this.TUNTAPGroupBox.Controls.Add(this.TUNTAPAddressTextBox);
this.TUNTAPGroupBox.Location = new System.Drawing.Point(15, 198);
this.TUNTAPGroupBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPGroupBox.Location = new System.Drawing.Point(12, 158);
this.TUNTAPGroupBox.Name = "TUNTAPGroupBox";
this.TUNTAPGroupBox.Padding = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPGroupBox.Size = new System.Drawing.Size(525, 205);
this.TUNTAPGroupBox.Size = new System.Drawing.Size(420, 164);
this.TUNTAPGroupBox.TabIndex = 3;
this.TUNTAPGroupBox.TabStop = false;
this.TUNTAPGroupBox.Text = "TUN/TAP";
@@ -169,10 +145,9 @@
// TUNTAPUseCustomDNSCheckBox
//
this.TUNTAPUseCustomDNSCheckBox.AutoSize = true;
this.TUNTAPUseCustomDNSCheckBox.Location = new System.Drawing.Point(150, 172);
this.TUNTAPUseCustomDNSCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPUseCustomDNSCheckBox.Location = new System.Drawing.Point(120, 138);
this.TUNTAPUseCustomDNSCheckBox.Name = "TUNTAPUseCustomDNSCheckBox";
this.TUNTAPUseCustomDNSCheckBox.Size = new System.Drawing.Size(154, 24);
this.TUNTAPUseCustomDNSCheckBox.Size = new System.Drawing.Size(127, 21);
this.TUNTAPUseCustomDNSCheckBox.TabIndex = 9;
this.TUNTAPUseCustomDNSCheckBox.Text = "Use Custom DNS";
this.TUNTAPUseCustomDNSCheckBox.UseVisualStyleBackColor = true;
@@ -181,86 +156,77 @@
// TUNTAPDNSLabel
//
this.TUNTAPDNSLabel.AutoSize = true;
this.TUNTAPDNSLabel.Location = new System.Drawing.Point(11, 140);
this.TUNTAPDNSLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.TUNTAPDNSLabel.Location = new System.Drawing.Point(9, 112);
this.TUNTAPDNSLabel.Name = "TUNTAPDNSLabel";
this.TUNTAPDNSLabel.Size = new System.Drawing.Size(41, 20);
this.TUNTAPDNSLabel.Size = new System.Drawing.Size(34, 17);
this.TUNTAPDNSLabel.TabIndex = 7;
this.TUNTAPDNSLabel.Text = "DNS";
//
// TUNTAPDNSTextBox
//
this.TUNTAPDNSTextBox.Location = new System.Drawing.Point(150, 136);
this.TUNTAPDNSTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPDNSTextBox.Location = new System.Drawing.Point(120, 110);
this.TUNTAPDNSTextBox.Name = "TUNTAPDNSTextBox";
this.TUNTAPDNSTextBox.Size = new System.Drawing.Size(366, 27);
this.TUNTAPDNSTextBox.Size = new System.Drawing.Size(294, 23);
this.TUNTAPDNSTextBox.TabIndex = 8;
this.TUNTAPDNSTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// TUNTAPGatewayLabel
//
this.TUNTAPGatewayLabel.AutoSize = true;
this.TUNTAPGatewayLabel.Location = new System.Drawing.Point(11, 104);
this.TUNTAPGatewayLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.TUNTAPGatewayLabel.Location = new System.Drawing.Point(9, 83);
this.TUNTAPGatewayLabel.Name = "TUNTAPGatewayLabel";
this.TUNTAPGatewayLabel.Size = new System.Drawing.Size(71, 20);
this.TUNTAPGatewayLabel.Size = new System.Drawing.Size(57, 17);
this.TUNTAPGatewayLabel.TabIndex = 5;
this.TUNTAPGatewayLabel.Text = "Gateway";
//
// TUNTAPGatewayTextBox
//
this.TUNTAPGatewayTextBox.Location = new System.Drawing.Point(150, 100);
this.TUNTAPGatewayTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPGatewayTextBox.Location = new System.Drawing.Point(120, 80);
this.TUNTAPGatewayTextBox.Name = "TUNTAPGatewayTextBox";
this.TUNTAPGatewayTextBox.Size = new System.Drawing.Size(366, 27);
this.TUNTAPGatewayTextBox.Size = new System.Drawing.Size(294, 23);
this.TUNTAPGatewayTextBox.TabIndex = 6;
this.TUNTAPGatewayTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// TUNTAPNetmaskLabel
//
this.TUNTAPNetmaskLabel.AutoSize = true;
this.TUNTAPNetmaskLabel.Location = new System.Drawing.Point(11, 68);
this.TUNTAPNetmaskLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.TUNTAPNetmaskLabel.Location = new System.Drawing.Point(9, 54);
this.TUNTAPNetmaskLabel.Name = "TUNTAPNetmaskLabel";
this.TUNTAPNetmaskLabel.Size = new System.Drawing.Size(73, 20);
this.TUNTAPNetmaskLabel.Size = new System.Drawing.Size(60, 17);
this.TUNTAPNetmaskLabel.TabIndex = 3;
this.TUNTAPNetmaskLabel.Text = "Netmask";
//
// TUNTAPNetmaskTextBox
//
this.TUNTAPNetmaskTextBox.Location = new System.Drawing.Point(150, 64);
this.TUNTAPNetmaskTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPNetmaskTextBox.Location = new System.Drawing.Point(120, 51);
this.TUNTAPNetmaskTextBox.Name = "TUNTAPNetmaskTextBox";
this.TUNTAPNetmaskTextBox.Size = new System.Drawing.Size(366, 27);
this.TUNTAPNetmaskTextBox.Size = new System.Drawing.Size(294, 23);
this.TUNTAPNetmaskTextBox.TabIndex = 4;
this.TUNTAPNetmaskTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// TUNTAPAddressLabel
//
this.TUNTAPAddressLabel.AutoSize = true;
this.TUNTAPAddressLabel.Location = new System.Drawing.Point(11, 31);
this.TUNTAPAddressLabel.Margin = new System.Windows.Forms.Padding(4, 0, 4, 0);
this.TUNTAPAddressLabel.Location = new System.Drawing.Point(9, 25);
this.TUNTAPAddressLabel.Name = "TUNTAPAddressLabel";
this.TUNTAPAddressLabel.Size = new System.Drawing.Size(69, 20);
this.TUNTAPAddressLabel.Size = new System.Drawing.Size(56, 17);
this.TUNTAPAddressLabel.TabIndex = 1;
this.TUNTAPAddressLabel.Text = "Address";
//
// TUNTAPAddressTextBox
//
this.TUNTAPAddressTextBox.Location = new System.Drawing.Point(150, 28);
this.TUNTAPAddressTextBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.TUNTAPAddressTextBox.Location = new System.Drawing.Point(120, 22);
this.TUNTAPAddressTextBox.Name = "TUNTAPAddressTextBox";
this.TUNTAPAddressTextBox.Size = new System.Drawing.Size(366, 27);
this.TUNTAPAddressTextBox.Size = new System.Drawing.Size(294, 23);
this.TUNTAPAddressTextBox.TabIndex = 2;
this.TUNTAPAddressTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// ControlButton
//
this.ControlButton.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Right)));
this.ControlButton.Location = new System.Drawing.Point(446, 588);
this.ControlButton.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.ControlButton.Location = new System.Drawing.Point(357, 648);
this.ControlButton.Name = "ControlButton";
this.ControlButton.Size = new System.Drawing.Size(94, 29);
this.ControlButton.Size = new System.Drawing.Size(75, 23);
this.ControlButton.TabIndex = 11;
this.ControlButton.Text = "Save";
this.ControlButton.UseVisualStyleBackColor = true;
@@ -269,10 +235,9 @@
// GlobalBypassIPsButton
//
this.GlobalBypassIPsButton.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
this.GlobalBypassIPsButton.Location = new System.Drawing.Point(15, 588);
this.GlobalBypassIPsButton.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.GlobalBypassIPsButton.Location = new System.Drawing.Point(12, 648);
this.GlobalBypassIPsButton.Name = "GlobalBypassIPsButton";
this.GlobalBypassIPsButton.Size = new System.Drawing.Size(160, 29);
this.GlobalBypassIPsButton.Size = new System.Drawing.Size(128, 23);
this.GlobalBypassIPsButton.TabIndex = 10;
this.GlobalBypassIPsButton.Text = "Global Bypass IPs";
this.GlobalBypassIPsButton.UseVisualStyleBackColor = true;
@@ -280,26 +245,102 @@
//
// BehaviorGroupBox
//
this.BehaviorGroupBox.Controls.Add(this.STUN_ServerPortTextBox);
this.BehaviorGroupBox.Controls.Add(this.label2);
this.BehaviorGroupBox.Controls.Add(this.label1);
this.BehaviorGroupBox.Controls.Add(this.RunAtStartup);
this.BehaviorGroupBox.Controls.Add(this.STUN_ServerTextBox);
this.BehaviorGroupBox.Controls.Add(this.MinimizeWhenStartedCheckBox);
this.BehaviorGroupBox.Controls.Add(this.ProfileCount_Label);
this.BehaviorGroupBox.Controls.Add(this.ProfileCount_TextBox);
this.BehaviorGroupBox.Controls.Add(this.CheckUpdateWhenOpenedCheckBox);
this.BehaviorGroupBox.Controls.Add(this.StartWhenOpenedCheckBox);
this.BehaviorGroupBox.Controls.Add(this.StopWhenExitedCheckBox);
this.BehaviorGroupBox.Controls.Add(this.ExitWhenClosedCheckBox);
this.BehaviorGroupBox.Location = new System.Drawing.Point(15, 412);
this.BehaviorGroupBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.BehaviorGroupBox.Location = new System.Drawing.Point(12, 330);
this.BehaviorGroupBox.Name = "BehaviorGroupBox";
this.BehaviorGroupBox.Padding = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.BehaviorGroupBox.Size = new System.Drawing.Size(525, 165);
this.BehaviorGroupBox.Size = new System.Drawing.Size(420, 312);
this.BehaviorGroupBox.TabIndex = 8;
this.BehaviorGroupBox.TabStop = false;
this.BehaviorGroupBox.Text = "Behavior";
//
// STUN_ServerPortTextBox
//
this.STUN_ServerPortTextBox.Location = new System.Drawing.Point(120, 237);
this.STUN_ServerPortTextBox.Name = "STUN_ServerPortTextBox";
this.STUN_ServerPortTextBox.Size = new System.Drawing.Size(294, 23);
this.STUN_ServerPortTextBox.TabIndex = 8;
this.STUN_ServerPortTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// label2
//
this.label2.AutoSize = true;
this.label2.Location = new System.Drawing.Point(9, 243);
this.label2.Name = "label2";
this.label2.Size = new System.Drawing.Size(110, 17);
this.label2.TabIndex = 12;
this.label2.Text = "STUN Server Port";
//
// label1
//
this.label1.AutoSize = true;
this.label1.Location = new System.Drawing.Point(9, 214);
this.label1.Name = "label1";
this.label1.Size = new System.Drawing.Size(82, 17);
this.label1.TabIndex = 10;
this.label1.Text = "STUN Server";
//
// RunAtStartup
//
this.RunAtStartup.AutoSize = true;
this.RunAtStartup.Location = new System.Drawing.Point(120, 130);
this.RunAtStartup.Name = "RunAtStartup";
this.RunAtStartup.Size = new System.Drawing.Size(109, 21);
this.RunAtStartup.TabIndex = 11;
this.RunAtStartup.Text = "Run at startup";
this.RunAtStartup.UseVisualStyleBackColor = true;
//
// STUN_ServerTextBox
//
this.STUN_ServerTextBox.Location = new System.Drawing.Point(120, 211);
this.STUN_ServerTextBox.Name = "STUN_ServerTextBox";
this.STUN_ServerTextBox.Size = new System.Drawing.Size(294, 23);
this.STUN_ServerTextBox.TabIndex = 11;
this.STUN_ServerTextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// MinimizeWhenStartedCheckBox
//
this.MinimizeWhenStartedCheckBox.AutoSize = true;
this.MinimizeWhenStartedCheckBox.Location = new System.Drawing.Point(120, 103);
this.MinimizeWhenStartedCheckBox.Name = "MinimizeWhenStartedCheckBox";
this.MinimizeWhenStartedCheckBox.Size = new System.Drawing.Size(158, 21);
this.MinimizeWhenStartedCheckBox.TabIndex = 10;
this.MinimizeWhenStartedCheckBox.Text = "Minimize when started";
this.MinimizeWhenStartedCheckBox.UseVisualStyleBackColor = true;
//
// ProfileCount_Label
//
this.ProfileCount_Label.AutoSize = true;
this.ProfileCount_Label.Location = new System.Drawing.Point(9, 185);
this.ProfileCount_Label.Name = "ProfileCount_Label";
this.ProfileCount_Label.Size = new System.Drawing.Size(79, 17);
this.ProfileCount_Label.TabIndex = 8;
this.ProfileCount_Label.Text = "ProfileCount";
//
// ProfileCount_TextBox
//
this.ProfileCount_TextBox.Location = new System.Drawing.Point(222, 182);
this.ProfileCount_TextBox.Name = "ProfileCount_TextBox";
this.ProfileCount_TextBox.Size = new System.Drawing.Size(192, 23);
this.ProfileCount_TextBox.TabIndex = 9;
this.ProfileCount_TextBox.TextAlign = System.Windows.Forms.HorizontalAlignment.Center;
//
// CheckUpdateWhenOpenedCheckBox
//
this.CheckUpdateWhenOpenedCheckBox.AutoSize = true;
this.CheckUpdateWhenOpenedCheckBox.Location = new System.Drawing.Point(150, 129);
this.CheckUpdateWhenOpenedCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.CheckUpdateWhenOpenedCheckBox.Location = new System.Drawing.Point(120, 157);
this.CheckUpdateWhenOpenedCheckBox.Name = "CheckUpdateWhenOpenedCheckBox";
this.CheckUpdateWhenOpenedCheckBox.Size = new System.Drawing.Size(235, 24);
this.CheckUpdateWhenOpenedCheckBox.Size = new System.Drawing.Size(190, 21);
this.CheckUpdateWhenOpenedCheckBox.TabIndex = 8;
this.CheckUpdateWhenOpenedCheckBox.Text = "Check update when opened";
this.CheckUpdateWhenOpenedCheckBox.TextAlign = System.Drawing.ContentAlignment.MiddleRight;
@@ -308,10 +349,9 @@
// StartWhenOpenedCheckBox
//
this.StartWhenOpenedCheckBox.AutoSize = true;
this.StartWhenOpenedCheckBox.Location = new System.Drawing.Point(150, 95);
this.StartWhenOpenedCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.StartWhenOpenedCheckBox.Location = new System.Drawing.Point(120, 76);
this.StartWhenOpenedCheckBox.Name = "StartWhenOpenedCheckBox";
this.StartWhenOpenedCheckBox.Size = new System.Drawing.Size(170, 24);
this.StartWhenOpenedCheckBox.Size = new System.Drawing.Size(137, 21);
this.StartWhenOpenedCheckBox.TabIndex = 7;
this.StartWhenOpenedCheckBox.Text = "Start when opened";
this.StartWhenOpenedCheckBox.TextAlign = System.Drawing.ContentAlignment.MiddleRight;
@@ -320,10 +360,9 @@
// StopWhenExitedCheckBox
//
this.StopWhenExitedCheckBox.AutoSize = true;
this.StopWhenExitedCheckBox.Location = new System.Drawing.Point(150, 61);
this.StopWhenExitedCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.StopWhenExitedCheckBox.Location = new System.Drawing.Point(120, 49);
this.StopWhenExitedCheckBox.Name = "StopWhenExitedCheckBox";
this.StopWhenExitedCheckBox.Size = new System.Drawing.Size(159, 24);
this.StopWhenExitedCheckBox.Size = new System.Drawing.Size(127, 21);
this.StopWhenExitedCheckBox.TabIndex = 6;
this.StopWhenExitedCheckBox.Text = "Stop when exited";
this.StopWhenExitedCheckBox.TextAlign = System.Drawing.ContentAlignment.MiddleRight;
@@ -332,10 +371,9 @@
// ExitWhenClosedCheckBox
//
this.ExitWhenClosedCheckBox.AutoSize = true;
this.ExitWhenClosedCheckBox.Location = new System.Drawing.Point(150, 28);
this.ExitWhenClosedCheckBox.Margin = new System.Windows.Forms.Padding(4, 4, 4, 4);
this.ExitWhenClosedCheckBox.Location = new System.Drawing.Point(120, 22);
this.ExitWhenClosedCheckBox.Name = "ExitWhenClosedCheckBox";
this.ExitWhenClosedCheckBox.Size = new System.Drawing.Size(152, 24);
this.ExitWhenClosedCheckBox.Size = new System.Drawing.Size(123, 21);
this.ExitWhenClosedCheckBox.TabIndex = 5;
this.ExitWhenClosedCheckBox.Text = "Exit when closed";
this.ExitWhenClosedCheckBox.TextAlign = System.Drawing.ContentAlignment.MiddleRight;
@@ -343,9 +381,9 @@
//
// SettingForm
//
this.AutoScaleDimensions = new System.Drawing.SizeF(120F, 120F);
this.AutoScaleDimensions = new System.Drawing.SizeF(96F, 96F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Dpi;
this.ClientSize = new System.Drawing.Size(555, 630);
this.ClientSize = new System.Drawing.Size(444, 682);
this.Controls.Add(this.BehaviorGroupBox);
this.Controls.Add(this.PortGroupBox);
this.Controls.Add(this.GlobalBypassIPsButton);
@@ -354,7 +392,7 @@
this.Font = new System.Drawing.Font("微软雅黑", 9F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(134)));
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
this.Margin = new System.Windows.Forms.Padding(4, 5, 4, 5);
this.Margin = new System.Windows.Forms.Padding(3, 4, 3, 4);
this.MaximizeBox = false;
this.Name = "SettingForm";
this.StartPosition = System.Windows.Forms.FormStartPosition.CenterScreen;
@@ -391,12 +429,18 @@
private System.Windows.Forms.Button GlobalBypassIPsButton;
private System.Windows.Forms.CheckBox TUNTAPUseCustomDNSCheckBox;
private System.Windows.Forms.CheckBox AllowDevicesCheckBox;
private System.Windows.Forms.TextBox RedirectorTextBox;
private System.Windows.Forms.Label RedirectorLabel;
private System.Windows.Forms.GroupBox BehaviorGroupBox;
private System.Windows.Forms.CheckBox ExitWhenClosedCheckBox;
private System.Windows.Forms.CheckBox StopWhenExitedCheckBox;
private System.Windows.Forms.CheckBox StartWhenOpenedCheckBox;
private System.Windows.Forms.CheckBox CheckUpdateWhenOpenedCheckBox;
private System.Windows.Forms.Label ProfileCount_Label;
private System.Windows.Forms.TextBox ProfileCount_TextBox;
private System.Windows.Forms.CheckBox MinimizeWhenStartedCheckBox;
private System.Windows.Forms.CheckBox RunAtStartup;
private System.Windows.Forms.Label label2;
private System.Windows.Forms.Label label1;
private System.Windows.Forms.TextBox STUN_ServerTextBox;
private System.Windows.Forms.TextBox STUN_ServerPortTextBox;
}
}

View File

@@ -1,6 +1,8 @@
using System;
using System.Collections;
using System.Net;
using System.Windows.Forms;
using TaskScheduler;
namespace Netch.Forms
{
@@ -57,10 +59,11 @@ namespace Netch.Forms
StopWhenExitedCheckBox.Checked = Global.Settings.StopWhenExited;
StartWhenOpenedCheckBox.Checked = Global.Settings.StartWhenOpened;
CheckUpdateWhenOpenedCheckBox.Checked = Global.Settings.CheckUpdateWhenOpened;
MinimizeWhenStartedCheckBox.Checked = Global.Settings.MinimizeWhenStarted;
RunAtStartup.Checked = Global.Settings.RunAtStartup;
Socks5PortTextBox.Text = Global.Settings.Socks5LocalPort.ToString();
HTTPPortTextBox.Text = Global.Settings.HTTPLocalPort.ToString();
RedirectorTextBox.Text = Global.Settings.RedirectorTCPPort.ToString();
TUNTAPAddressTextBox.Text = Global.Settings.TUNTAP.Address;
TUNTAPNetmaskTextBox.Text = Global.Settings.TUNTAP.Netmask;
@@ -72,7 +75,14 @@ namespace Netch.Forms
ExitWhenClosedCheckBox.Text = Utils.i18N.Translate(ExitWhenClosedCheckBox.Text);
StopWhenExitedCheckBox.Text = Utils.i18N.Translate(StopWhenExitedCheckBox.Text);
StartWhenOpenedCheckBox.Text = Utils.i18N.Translate(StartWhenOpenedCheckBox.Text);
MinimizeWhenStartedCheckBox.Text = Utils.i18N.Translate(MinimizeWhenStartedCheckBox.Text);
RunAtStartup.Text = Utils.i18N.Translate(RunAtStartup.Text);
CheckUpdateWhenOpenedCheckBox.Text = Utils.i18N.Translate(CheckUpdateWhenOpenedCheckBox.Text);
ProfileCount_Label.Text = Utils.i18N.Translate(ProfileCount_Label.Text);
ProfileCount_TextBox.Text = Global.Settings.ProfileCount.ToString();
STUN_ServerTextBox.Text = Global.Settings.STUN_Server.ToString();
STUN_ServerPortTextBox.Text = Global.Settings.STUN_Server_Port.ToString();
if (Global.Settings.TUNTAP.DNS.Count > 0)
{
@@ -130,6 +140,47 @@ namespace Netch.Forms
Global.Settings.StopWhenExited = StopWhenExitedCheckBox.Checked;
Global.Settings.StartWhenOpened = StartWhenOpenedCheckBox.Checked;
Global.Settings.CheckUpdateWhenOpened = CheckUpdateWhenOpenedCheckBox.Checked;
Global.Settings.MinimizeWhenStarted = MinimizeWhenStartedCheckBox.Checked;
Global.Settings.RunAtStartup = RunAtStartup.Checked;
// 开机自启判断
TaskSchedulerClass scheduler = new TaskSchedulerClass();
scheduler.Connect(null, null, null, null);
ITaskFolder folder = scheduler.GetFolder("\\");
bool taskIsExists = false;
try
{
folder.GetTask("Netch Startup");
taskIsExists = true;
}
catch (Exception) { }
if (RunAtStartup.Checked)
{
if (taskIsExists)
folder.DeleteTask("Netch Startup", 0);
ITaskDefinition task = scheduler.NewTask(0);
task.RegistrationInfo.Author = "Netch";
task.RegistrationInfo.Description = "Netch run at startup.";
task.Principal.RunLevel = _TASK_RUNLEVEL.TASK_RUNLEVEL_HIGHEST;
task.Triggers.Create(_TASK_TRIGGER_TYPE2.TASK_TRIGGER_LOGON);
IExecAction action = (IExecAction)task.Actions.Create(_TASK_ACTION_TYPE.TASK_ACTION_EXEC);
action.Path = System.Windows.Forms.Application.ExecutablePath;
task.Settings.ExecutionTimeLimit = "PT0S";
task.Settings.DisallowStartIfOnBatteries = false;
task.Settings.RunOnlyIfIdle = false;
folder.RegisterTaskDefinition("Netch Startup", task, (int)_TASK_CREATION.TASK_CREATE, null, null, _TASK_LOGON_TYPE.TASK_LOGON_INTERACTIVE_TOKEN, "");
}
else
{
if (taskIsExists)
folder.DeleteTask("Netch Startup", 0);
}
try
{
@@ -173,27 +224,6 @@ namespace Netch.Forms
return;
}
try
{
var RedirectorPort = int.Parse(RedirectorTextBox.Text);
if (RedirectorPort > 0 && RedirectorPort < 65536)
{
Global.Settings.RedirectorTCPPort = RedirectorPort;
}
else
{
throw new FormatException();
}
}
catch (FormatException)
{
RedirectorTextBox.Text = Global.Settings.RedirectorTCPPort.ToString();
MessageBox.Show(Utils.i18N.Translate("Port value illegal. Try again."), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
if (AllowDevicesCheckBox.Checked)
{
Global.Settings.LocalAddress = "0.0.0.0";
@@ -235,6 +265,49 @@ namespace Netch.Forms
return;
}
try
{
var ProfileCount = int.Parse(ProfileCount_TextBox.Text);
if (ProfileCount > 0)
{
Global.Settings.ProfileCount = ProfileCount;
}
else
{
throw new FormatException();
}
}
catch (FormatException)
{
ProfileCount_TextBox.Text = Global.Settings.ProfileCount.ToString();
MessageBox.Show(Utils.i18N.Translate("ProfileCount value illegal. Try again."), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
try
{
var STUN_Server = STUN_ServerTextBox.Text;
Global.Settings.STUN_Server = STUN_Server;
var STUN_ServerPort = int.Parse(STUN_ServerPortTextBox.Text);
if (STUN_ServerPort > 0)
{
Global.Settings.STUN_Server_Port = STUN_ServerPort;
}
else
{
throw new FormatException();
}
}
catch (FormatException)
{
ProfileCount_TextBox.Text = Global.Settings.ProfileCount.ToString();
MessageBox.Show(Utils.i18N.Translate("STUN_ServerPort value illegal. Try again."), Utils.i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return;
}
Global.Settings.TUNTAP.Address = TUNTAPAddressTextBox.Text;
Global.Settings.TUNTAP.Netmask = TUNTAPNetmaskTextBox.Text;

View File

@@ -45,6 +45,7 @@
this.UserAgentHeader = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader()));
this.pContextMenuStrip = new System.Windows.Forms.ContextMenuStrip(this.components);
this.DeleteToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
this.CopyLinkToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
this.UseSelectedServerCheckBox = new System.Windows.Forms.CheckBox();
this.AddSubscriptionBox.SuspendLayout();
this.pContextMenuStrip.SuspendLayout();
@@ -169,6 +170,8 @@
//
this.pContextMenuStrip.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
this.DeleteToolStripMenuItem});
this.pContextMenuStrip.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
this.CopyLinkToolStripMenuItem});
this.pContextMenuStrip.Name = "pContextMenuStrip";
this.pContextMenuStrip.Size = new System.Drawing.Size(114, 26);
//
@@ -179,6 +182,13 @@
this.DeleteToolStripMenuItem.Text = "Delete";
this.DeleteToolStripMenuItem.Click += new System.EventHandler(this.DeleteToolStripMenuItem_Click);
//
// CopyLinkToolStripMenuItem
//
this.CopyLinkToolStripMenuItem.Name = "CopyLinkToolStripMenuItem";
this.CopyLinkToolStripMenuItem.Size = new System.Drawing.Size(113, 22);
this.CopyLinkToolStripMenuItem.Text = "CopyLink";
this.CopyLinkToolStripMenuItem.Click += new System.EventHandler(this.CopyLinkToolStripMenuItem_Click);
//
// UseSelectedServerCheckBox
//
this.UseSelectedServerCheckBox.AutoSize = true;
@@ -229,6 +239,7 @@
private System.Windows.Forms.ColumnHeader LinkColumnHeader;
private System.Windows.Forms.ContextMenuStrip pContextMenuStrip;
private System.Windows.Forms.ToolStripMenuItem DeleteToolStripMenuItem;
private System.Windows.Forms.ToolStripMenuItem CopyLinkToolStripMenuItem;
private System.Windows.Forms.Label UserAgentLabel;
private System.Windows.Forms.TextBox UserAgentTextBox;
private System.Windows.Forms.ColumnHeader UserAgentHeader;

View File

@@ -1,4 +1,5 @@
using System;
using Netch.Models;
using System;
using System.Collections.Generic;
using System.Windows.Forms;
@@ -41,6 +42,7 @@ namespace Netch.Forms
LinkColumnHeader.Text = Utils.i18N.Translate(LinkColumnHeader.Text);
UseSelectedServerCheckBox.Text = Utils.i18N.Translate(UseSelectedServerCheckBox.Text);
DeleteToolStripMenuItem.Text = Utils.i18N.Translate(DeleteToolStripMenuItem.Text);
CopyLinkToolStripMenuItem.Text = Utils.i18N.Translate(CopyLinkToolStripMenuItem.Text);
RemarkLabel.Text = Utils.i18N.Translate(RemarkLabel.Text);
LinkLabel.Text = Utils.i18N.Translate(LinkLabel.Text);
AddButton.Text = Utils.i18N.Translate(AddButton.Text);
@@ -56,7 +58,18 @@ namespace Netch.Forms
{
Global.MainForm.Show();
}
private void CopyLinkToolStripMenuItem_Click(object sender, EventArgs e)
{
if (SubscribeLinkListView.SelectedItems.Count > 0)
{
for (var i = SubscribeLinkListView.SelectedItems.Count - 1; i >= 0; i--)
{
var item = SubscribeLinkListView.SelectedItems[i];
var link = Global.Settings.SubscribeLink[item.Index];
Clipboard.SetText(link.Link);
}
}
}
private void DeleteToolStripMenuItem_Click(object sender, EventArgs e)
{
if (MessageBox.Show(Utils.i18N.Translate("Delete or not ? Will clean up the corresponding group of items in the server list"), Utils.i18N.Translate("Information"), MessageBoxButtons.OKCancel, MessageBoxIcon.Information) == DialogResult.OK)

View File

@@ -115,5 +115,20 @@ namespace Netch.Models
// 写入到模式文件里
System.IO.File.WriteAllText(NewPath, ToFileString());
}
/// <summary>
/// 删除模式文件
/// </summary>
public void DeleteFile(string Dir)
{
if (System.IO.Directory.Exists(Dir))
{
var NewPath = System.IO.Path.Combine(Dir, FileName);
if (System.IO.File.Exists(NewPath + ".txt"))
{
System.IO.File.Delete(NewPath + ".txt");
}
}
}
}
}

View File

@@ -63,6 +63,16 @@ namespace Netch.Models
/// </summary>
public bool StartWhenOpened = false;
/// <summary>
/// 是否启动后自动最小化
/// </summary>
public bool MinimizeWhenStarted = false;
/// <summary>
/// 是否开机启动软件
/// </summary>
public bool RunAtStartup = false;
/// <summary>
/// 是否打开软件时检查更新
/// </summary>
@@ -87,7 +97,7 @@ namespace Netch.Models
/// <summary>
/// Redirector TCP 占用端口
/// </summary>
public int RedirectorTCPPort = 2800;
//public int RedirectorTCPPort = 2800;
/// <summary>
/// HTTP 和 Socks5 本地代理地址
@@ -117,12 +127,26 @@ namespace Netch.Models
/// <summary>
/// 全局绕过 IP 列表
/// </summary>
public List<string> BypassIPs = new List<string>();
public List<string> BypassIPs = new List<string>() { "10.0.0.0/8", "172.16.0.0/16", "192.168.0.0/24" };
/// <summary>
/// Saved profiles
/// 已保存的快捷配置
/// </summary>
public List<Profile> profiles = new List<Profile>();
/// <summary>
/// 快捷配置数量
/// </summary>
public int ProfileCount = 4;
/// <summary>
/// STUN测试服务器
/// </summary>
public string STUN_Server = "stun.stunprotocol.org";
/// <summary>
/// STUN测试服务器
/// </summary>
public int STUN_Server_Port = 3478;
}
}

View File

@@ -24,7 +24,17 @@ namespace Netch
// 清理上一次的日志文件,防止淤积占用磁盘空间
if (Directory.Exists("logging"))
{
Directory.Delete("logging", true);
DirectoryInfo directory = new DirectoryInfo("logging");
foreach (FileInfo file in directory.GetFiles())
{
file.Delete();
}
foreach (DirectoryInfo dir in directory.GetDirectories())
{
dir.Delete(true);
}
}
// 预创建目录

View File

@@ -52,6 +52,18 @@
<None Remove=".gitignore" />
</ItemGroup>
<ItemGroup>
<COMReference Include="TaskScheduler.dll">
<Guid>e34cb9f1-c7f7-424c-be29-027dcc09363a</Guid>
<VersionMajor>1</VersionMajor>
<VersionMinor>0</VersionMinor>
<WrapperTool>tlbimp</WrapperTool>
<Lcid>0</Lcid>
<Isolated>false</Isolated>
<EmbedInteropTypes>false</EmbedInteropTypes>
</COMReference>
</ItemGroup>
<ItemGroup>
<PackageReference Include="DNS" Version="5.0.0" />
<PackageReference Include="DnsClient" Version="1.2.0" />
@@ -67,8 +79,23 @@
<Reference Include="System.Web" />
</ItemGroup>
<ItemGroup>
<Compile Update="Properties\Resources.Designer.cs">
<DesignTime>True</DesignTime>
<AutoGen>True</AutoGen>
<DependentUpon>Resources.resx</DependentUpon>
</Compile>
</ItemGroup>
<ItemGroup>
<EmbeddedResource Update="Properties\Resources.resx">
<Generator>ResXFileCodeGenerator</Generator>
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
</EmbeddedResource>
</ItemGroup>
<Target Name="PostBuild" AfterTargets="PostBuildEvent">
<Exec Command="@ECHO OFF&#xD;&#xA;RD /S /Q $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;RD /S /Q $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;RD /S /Q $(TargetDir)mode &gt; NUL 2&gt;&amp;1&#xD;&#xA;&#xD;&#xA;MKDIR $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;MKDIR $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;MKDIR $(TargetDir)mode &gt; NUL 2&gt;&amp;1&#xD;&#xA;&#xD;&#xA;COPY /Y $(SolutionDir)binaries\$(PlatformName)\* $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)binaries\* $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;MOVE /Y $(TargetDir)bin\nfapinet.dll $(TargetDir)nfapinet.dll &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)translations\i18n\* $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)modes\mode\*.txt $(TargetDir)mode &gt; NUL 2&gt;&amp;1" />
<Exec Command="@ECHO OFF&#xD;&#xA;RD /S /Q $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;RD /S /Q $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;RD /S /Q $(TargetDir)mode &gt; NUL 2&gt;&amp;1&#xD;&#xA;&#xD;&#xA;MKDIR $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;MKDIR $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;MKDIR $(TargetDir)mode &gt; NUL 2&gt;&amp;1&#xD;&#xA;&#xD;&#xA;COPY /Y $(SolutionDir)binaries\$(PlatformName)\* $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)binaries\* $(TargetDir)bin &gt; NUL 2&gt;&amp;1&#xD;&#xA;MOVE /Y $(TargetDir)bin\nfapinet.dll $(TargetDir)nfapinet.dll &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)translations\i18n\* $(TargetDir)i18n &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)modes\mode\*.txt $(TargetDir)mode &gt; NUL 2&gt;&amp;1&#xD;&#xA;MKDIR $(TargetDir)bin\tap-driver &gt; NUL 2&gt;&amp;1&#xD;&#xA;COPY /Y $(SolutionDir)binaries\$(PlatformName)\tap-driver\* $(TargetDir)bin\tap-driver &gt; NUL 2&gt;&amp;1" />
</Target>
</Project>

View File

@@ -70,6 +70,16 @@ namespace Netch.Properties {
}
}
/// <summary>
/// 查找 System.Drawing.Bitmap 类型的本地化资源。
/// </summary>
internal static System.Drawing.Bitmap CopyLink {
get {
object obj = ResourceManager.GetObject("CopyLink", resourceCulture);
return ((System.Drawing.Bitmap)(obj));
}
}
/// <summary>
/// 查找 System.Byte[] 类型的本地化资源。
/// </summary>

View File

@@ -121,12 +121,12 @@
<data name="defaultTUNTAP" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\defaultTUNTAP;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</data>
<data name="Netch" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\Netch.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="zh_CN" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\zh-CN;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</data>
<data name="speed" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\speed.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="delete" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\delete.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
@@ -136,10 +136,13 @@
<data name="CNIP" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\CNIP;System.Byte[], mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</data>
<data name="speed" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\speed.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
<data name="Netch" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\Netch.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="N3RO" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\N3RO.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
<data name="CopyLink" type="System.Resources.ResXFileRef, System.Windows.Forms">
<value>..\Resources\CopyLink.png;System.Drawing.Bitmap, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a</value>
</data>
</root>

Binary file not shown.

After

Width:  |  Height:  |  Size: 715 B

View File

@@ -16,6 +16,16 @@
"Started": "已启动",
"Stopping": "正在停止中",
"Stopped": "已停止",
"Starting Shadowsocks": "正在启动Shadowsocks",
"Starting ShadowsocksR": "正在启动ShadowsocksR",
"Starting V2ray": "正在启动V2ray",
"Starting Tap": "正在启动Tap",
"Starting NatTester": "正在启动Nat测试",
"Starting LocalDns service": "正在启动本地DNS服务",
"Starting Redirector": "正在启动Redirector",
"Starting netfilter2 Service": "正在启动netfilter2服务",
"Starting dns2tcp Service": "正在启动dns2tcp服务",
"SetupBypass": "设置绕行规则",
"Server": "服务器",
"Import Servers From Clipboard": "从剪贴板导入服务器",
@@ -30,6 +40,7 @@
"Mode": "模式",
"Create Process Mode": "创建进程模式",
"Manage Process Mode": "管理进程模式",
"Edit Process Mode": "修改进程模式",
"Address": "地址",
"Username": "用户名",
@@ -100,12 +111,16 @@
"Please enter an process name (xxx.exe)": "请输入一个进程名xxx.exe",
"Scan completed": "扫描完成",
"Mode added successfully": "模式添加成功",
"Mode updated successfully": "模式修改成功",
"Unable to add empty rule": "无法添加空规则",
"Please enter a mode remark": "请输入模式的备注",
"File already exists.\n Please Change the filename": "文件名已存在,请修改文件名",
"Please enter a mode filename": "请输入模式的文件名",
"Link": "链接",
"Use Selected Server To Update Subscription": "使用选中的服务器更新订阅",
"Delete": "删除",
"CopyLink": "复制链接",
"Delete or not ? Will clean up the corresponding group of items in the server list": "是否删除?将会清理服务器列表中对应组的项目",
"Remark can not be empty": "备注不可为空",
"Link can not be empty": "链接不可为空",
@@ -114,6 +129,8 @@
"Settings": "设置",
"Start when opened": "打开软件时启动加速",
"Minimize when started": "启动加速后隐藏",
"Run at startup": "开机自动启动",
"Local Port": "本地端口",
"Allow other Devices to connect": "允许其他设备连入",
"Netmask": "子网掩码",
@@ -125,6 +142,10 @@
"Global Bypass IPs": "全局直连 IP",
"Port value illegal. Try again.": "端口值非法。请重试。",
"Check update when opened": "打开软件时检查更新",
"ProfileCount": "快捷配置数量(重启软件生效)",
"ProfileCount value illegal. Try again.": "快捷配置数值非法。请重试。",
"STUN_ServerPort value illegal. Try again.": "STUN端口数值非法。请重试。",
"TUN/TAP driver is not detected. Is it installed now?": "未检测到TUN/TAP驱动是否现在安装",
"Profile": "配置名",
"Profiles": "配置",

View File

@@ -1,4 +1,5 @@
using System;
using System.Diagnostics;
using System.IO;
using System.Net;
using System.Net.NetworkInformation;
@@ -104,63 +105,95 @@ namespace Netch.Utils
return false;
}
Logging.Info($"搜索适配器index{Global.Adapter.Index}");
var AddressGot = false;
foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces())
{
var adapterProperties = adapter.GetIPProperties();
var p = adapterProperties.GetIPv4Properties();
// 通过索引查找对应适配器的 IPv4 地址
if (p.Index == Global.Adapter.Index)
try
{
var AddressGot = false;
var AdapterIPs = "";
var adapterProperties = adapter.GetIPProperties();
var p = adapterProperties.GetIPv4Properties();
Logging.Info($"检测适配器:{adapter.Name} {adapter.Id} {adapter.Description}, index: {p.Index}");
foreach (var ip in adapterProperties.UnicastAddresses)
// 通过索引查找对应适配器的 IPv4 地址
if (p.Index == Global.Adapter.Index)
{
if (ip.Address.AddressFamily == AddressFamily.InterNetwork)
var AdapterIPs = "";
foreach (var ip in adapterProperties.UnicastAddresses)
{
AddressGot = true;
Global.Adapter.Address = ip.Address;
Logging.Info($"当前出口 IPv4 地址:{Global.Adapter.Address}");
break;
if (ip.Address.AddressFamily == AddressFamily.InterNetwork)
{
AddressGot = true;
Global.Adapter.Address = ip.Address;
Logging.Info($"当前出口 IPv4 地址:{Global.Adapter.Address}");
break;
}
AdapterIPs = $"{ip.Address} | ";
}
AdapterIPs = $"{ip.Address} | ";
if (!AddressGot)
{
if (AdapterIPs.Length > 3)
{
AdapterIPs = AdapterIPs.Substring(0, AdapterIPs.Length - 3);
Logging.Info($"所有出口地址:{AdapterIPs}");
}
Logging.Info("出口无 IPv4 地址,当前只支持 IPv4 地址");
return false;
}
break;
}
if (!AddressGot)
{
if (AdapterIPs.Length > 3)
{
AdapterIPs = AdapterIPs.Substring(0, AdapterIPs.Length - 3);
Logging.Info($"所有出口地址:{AdapterIPs}");
}
Logging.Info("出口无 IPv4 地址,当前只支持 IPv4 地址");
return false;
}
break;
}
catch (Exception)
{ }
}
if (!AddressGot)
{
Logging.Info("无法找到当前使用适配器");
return false;
}
// 搜索 TUN/TAP 适配器的索引
Global.TUNTAP.ComponentID = TUNTAP.GetComponentID();
if (string.IsNullOrEmpty(Global.TUNTAP.ComponentID))
{
MessageBox.Show(i18N.Translate("Please install TAP-Windows and create an TUN/TAP adapter manually"), i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
return false;
if (MessageBox.Show(i18N.Translate("TUN/TAP driver is not detected. Is it installed now?"), i18N.Translate("Information"), MessageBoxButtons.OKCancel, MessageBoxIcon.Information) == DialogResult.OK)
{
//安装Tap Driver
Process installProcess = new Process();
installProcess.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
installProcess.StartInfo.FileName = Path.Combine("bin/tap-driver", "install.bat");
installProcess.Start();
installProcess.WaitForExit();
installProcess.Close();
Global.TUNTAP.ComponentID = TUNTAP.GetComponentID();
}
else {
return false;
}
//MessageBox.Show(i18N.Translate("Please install TAP-Windows and create an TUN/TAP adapter manually"), i18N.Translate("Information"), MessageBoxButtons.OK, MessageBoxIcon.Information);
// return false;
}
var name = TUNTAP.GetName(Global.TUNTAP.ComponentID);
foreach (var adapter in NetworkInterface.GetAllNetworkInterfaces())
{
if (adapter.Name == name)
if (adapter.Id == Global.TUNTAP.ComponentID)
{
Global.TUNTAP.Adapter = adapter;
Global.TUNTAP.Index = adapter.GetIPProperties().GetIPv4Properties().Index;
break;
Logging.Info($"找到适配器:{adapter.Id}");
return true;
}
}
return true;
Logging.Info("无法找到出口");
return false;
}
}
}

View File

@@ -21,6 +21,66 @@ namespace Netch.Utils
{
return Encoding.UTF8.GetString(Convert.FromBase64String(text.Replace("-", "+").Replace("_", "/").PadRight(text.Length + (4 - text.Length % 4) % 4, '=')));
}
/// <summary>
/// URL 传输安全的 Base64 加密
/// </summary>
/// <param name="text">需要加密的字符串</param>
/// <returns>加密后的字符串</returns>
public static string URLSafeBase64Encode(string text)
{
return Convert.ToBase64String(Encoding.UTF8.GetBytes(text)).Replace("-", "+").Replace("_", "/").PadRight(text.Length + (4 - text.Length % 4) % 4, '=');
}
/// <summary>
/// 根据服务器生成分享链接
/// </summary>
/// <param name="server">需要获取分享链接的服务器</param>
/// <returns>解码后的字符串</returns>
public static string GetShareLink(Models.Server server)
{
string retLinkStr = "";
switch (server.Type)
{
case "Socks5":
// https://t.me/socks?server=1.1.1.1&port=443
retLinkStr = string.Format("https://t.me/socks?server={0}&port={1}", server.Hostname, server.Port);
break;
case "SS":
// ss://method:password@server:port#Remark
retLinkStr = "ss://" + URLSafeBase64Encode(string.Format("{0}:{1}@{2}:{3}", server.EncryptMethod, server.Password, server.Hostname, server.Port)) + "#" + HttpUtility.UrlEncode(server.Remark);
break;
case "SSR":
// https://github.com/shadowsocksr-backup/shadowsocks-rss/wiki/SSR-QRcode-scheme
// ssr://base64(host:port:protocol:method:obfs:base64pass/?obfsparam=base64param&protoparam=base64param&remarks=base64remarks&group=base64group&udpport=0&uot=0)
string paraStr = string.Format("/?obfsparam={0}&protoparam={1}&remarks={2}", URLSafeBase64Encode(server.OBFSParam), URLSafeBase64Encode(server.ProtocolParam), URLSafeBase64Encode(server.Remark));
retLinkStr = "ssr://" + URLSafeBase64Encode(string.Format("{0}:{1}:{2}:{3}:{4}:{5}{6}", server.Hostname, server.Port, server.Protocol, server.EncryptMethod, server.OBFS, URLSafeBase64Encode(server.Password), paraStr));
break;
case "VMess":
string vmessJson = Newtonsoft.Json.JsonConvert.SerializeObject(new
{
v = "2",
ps = server.Remark,
add = server.Hostname,
port = server.Port,
id = server.UserID,
aid = server.AlterID,
net = server.TransferProtocol,
type = server.FakeType,
host = server.Host,
path = server.Path,
tls = server.TLSSecure ? "tls" : ""
});
retLinkStr = "vmess://" + URLSafeBase64Encode(vmessJson);
break;
default:
return null;
}
return retLinkStr;
}
public static List<Server> Parse(string text)
{
@@ -47,7 +107,7 @@ namespace Netch.Utils
foreach (var line in text.GetLines())
{
var servers = ParseLine(line);
if (line != null)
if (servers != null)
{
list.AddRange(servers);
}
@@ -109,110 +169,7 @@ namespace Netch.Utils
{
var data = new Server();
data.Type = "SS";
/*
try
{
if(!text.Contains("/?"))
{
var finder = new Regex(@"ss://(?<base64>[A-Za-z0-9+-/=_]+)(?:#(?<tag>\S+))?", RegexOptions.IgnoreCase);
var parser = new Regex(@"^((?<method>.+?):(?<password>.*)@(?<hostname>.+?):(?<port>\d+?))$", RegexOptions.IgnoreCase);
var match = finder.Match(text);
if (!match.Success)
{
throw new FormatException();
}
var base64 = match.Groups["base64"].Value.TrimEnd('/');
var tag = match.Groups["tag"].Value;
if (!String.IsNullOrEmpty(tag))
{
data.Remark = HttpUtility.UrlDecode(tag);
}
match = parser.Match(URLSafeBase64Decode(base64));
if (!match.Success)
{
throw new FormatException();
}
data.Address = match.Groups["hostname"].Value;
data.Port = int.Parse(match.Groups["port"].Value);
data.Password = match.Groups["password"].Value;
data.EncryptMethod = match.Groups["method"].Value;
}
else
{
if (text.Contains("#"))
{
data.Remark = HttpUtility.UrlDecode(text.Split('#')[1]);
text = text.Split('#')[0];
}
var finder = new Regex(@"ss://(?<base64>.+?)@(?<server>.+?):(?<port>\d+?)/\?plugin=(?<plugin>.+)");
var parser = new Regex(@"^(?<method>.+?):(?<password>.+)$");
var match = finder.Match(text);
if (!match.Success)
{
throw new FormatException();
}
data.Address = match.Groups["server"].Value;
data.Port = int.Parse(match.Groups["port"].Value);
var plugins = HttpUtility.UrlDecode(match.Groups["plugin"].Value).Split(';');
if (plugins[0] == "obfs-local")
plugins[0] = "simple-obfs";
var base64 = URLSafeBase64Decode(match.Groups["base64"].Value);
match = parser.Match(base64);
if (!match.Success)
{
throw new FormatException();
}
data.EncryptMethod = match.Groups["method"].Value;
data.Password = match.Groups["password"].Value;
data.Plugin = plugins[0];
data.PluginOption = plugins[1];
}
if (!Global.EncryptMethods.SS.Contains(data.EncryptMethod))
{
Logging.Info(String.Format("不支持的 SS 加密方式:{0}", data.EncryptMethod));
return null;
}
list.Add(data);
}
catch (FormatException)
{
try
{
var uri = new Uri(text);
var userinfo = URLSafeBase64Decode(uri.UserInfo).Split(new char[] { ':' }, 2);
if (userinfo.Length != 2)
{
return null;
}
data.Remark = uri.GetComponents(UriComponents.Fragment, UriFormat.Unescaped);
data.Address = uri.IdnHost;
data.Port = uri.Port;
data.Password = userinfo[1];
data.EncryptMethod = userinfo[0];
if (!Global.EncryptMethods.SS.Contains(data.EncryptMethod))
{
Logging.Info(String.Format("不支持的 SS 加密方式:{0}", data.EncryptMethod));
return null;
}
list.Add(data);
}
catch (UriFormatException)
{
return null;
}
}
*/
text = text.Replace("/?", "?");
try
{
@@ -337,81 +294,7 @@ namespace Netch.Utils
data.Type = "SSR";
text = text.Substring(6);
/*
var shadowsocksr = URLSafeBase64Decode(text).Split(':');
if (shadowsocksr.Length > 6)
{
var buff = "";
for (int i = 0; i < shadowsocksr.Length - 5; i++)
{
buff += shadowsocksr[i];
buff += ":";
}
data.Address = buff.Substring(0, buff.Length - 1).Trim();
}
else
{
data.Address = shadowsocksr[0];
}
data.Port = int.Parse(shadowsocksr[shadowsocksr.Length - 5]);
data.Protocol = shadowsocksr[shadowsocksr.Length - 4];
if (!Global.Protocols.Contains(data.Protocol))
{
Logging.Info(String.Format("不支持的 SSR 协议:{0}", data.Protocol));
return null;
}
data.EncryptMethod = shadowsocksr[shadowsocksr.Length - 3];
if (!Global.EncryptMethods.SSR.Contains(data.EncryptMethod))
{
Logging.Info(String.Format("不支持的 SSR 加密方式:{0}", data.EncryptMethod));
return null;
}
data.OBFS = shadowsocksr[shadowsocksr.Length - 2];
if (!Global.OBFSs.Contains(data.OBFS))
{
Logging.Info(String.Format("不支持的 SSR 混淆:{0}", data.OBFS));
return null;
}
var info = shadowsocksr[shadowsocksr.Length - 1].Split('/');
data.Password = URLSafeBase64Decode(info[0]);
var dict = new Dictionary<string, string>();
if (info.Length > 1 && info[1].Length > 1)
{
foreach (var str in info[1].Substring(1).Split('&'))
{
var splited = str.Split('=');
dict.Add(splited[0], splited[1]);
}
}
if (dict.ContainsKey("remarks"))
{
data.Remark = URLSafeBase64Decode(dict["remarks"]);
}
if (dict.ContainsKey("protoparam"))
{
data.ProtocolParam = URLSafeBase64Decode(dict["protoparam"]);
}
if (dict.ContainsKey("obfsparam"))
{
data.OBFSParam = URLSafeBase64Decode(dict["obfsparam"]);
}
if (data.EncryptMethod != "none" && data.Protocol == "origin" && data.OBFS == "plain")
{
data.Type = "SS";
}
*/
var parser = new Regex(@"^(?<server>.+):(?<port>(-?\d+?)):(?<protocol>.+?):(?<method>.+?):(?<obfs>.+?):(?<password>.+?)/\?(?<info>.*)$");
var match = parser.Match(URLSafeBase64Decode(text));

View File

@@ -22,10 +22,12 @@ As well, Netch avoid the restricted NAT problem caused by SSTap. You can use an
## Sponsor
开发不易,以下为恰饭时间
[![ManSora](docs/sponsor/mansora.jpg)](https://www.mansora.net/cart.php)
[![Across-GFW](docs/sponsor/across-gfw.jpg)](https://across-gfw.com/register?aff=4739)
[![NyanCAT](docs/sponsor/nyancat.jpg)](https://nyancat.info)
这是我所选择的服务器提供商IPLC 专线翻墙、稳定、速度快、价格便宜。欢迎大家使用我的推广链接前去注册:[这里](https://across-gfw.com/register?aff=4739)
NyanCAT Network全中转高质量节点多条低倍率节点保证流量无忧节点极低延迟涵盖五大洲。Netflix 视频党,游戏党,海外回国党必备,无需年付,月付 19 元起
[Telegram 群组](https://t.me/NyanCaaaat)
[![ManSora](docs/sponsor/mansora.jpg)](https://www.mansora.net/cart.php)
## Screenshots
@@ -34,4 +36,4 @@ As well, Netch avoid the restricted NAT problem caused by SSTap. You can use an
## Requirements
- Microsoft Visual C++ Runtime
- [.NET Framework 4.8](https://dotnet.microsoft.com/download/dotnet-framework/net48)
- [.NET Framework 4.8](https://dotnet.microsoft.com/download/dotnet-framework/net48)

42
docs/Basic-usage.md Normal file
View File

@@ -0,0 +1,42 @@
# 新手入门
**Version : 1.3.7**
[下载地址](https://github.com/NetchX/Netch/releases)
## 主界面
![主界面](screenshots/main.zh-CN.png)
## 添加服务器
> Netch 目前仅支持以下代理协议ShadowsocksVMessSocks5ShadowsockR。
首先,点击`服务器`增加所需服务器
<img width="50%" height="50%" src="screenshots/Add-server.png">
可手动添加单个服务器,或者通过剪切板链接添加单个服务器。也可通过订阅链接批量添加。
点击 `订阅` ` 管理订阅链接` 进入以下界面。
<img width="50%" height="50%" src="screenshots/Add-link.jpg">
填写备注与链接,点击添加,然后保存。保存后点击 `订阅` ` 从订阅链接更新服务器`。完成服务器添加。添加完服务器后可对服务器进行修改,删除和测速。
## 选择模式
> 此处需要会一点英语,比如你应该知道`吃鸡`的英文名称是`PlayerUnknown's Battlegrounds`
1.3.7 上线了模式搜索功能,即在模式框里输入字符即可搜索,使用英文名称进行搜索,搜索到所需的模式后单击选择,启用模式。相对应的游戏即可被加速
若没有所需的模式,请选择`[3] Bypass LAN and China (TUN/TAP)`的模式。此模式需要安装 [Tap-Windows](https://github.com/OpenVPN/tap-windows) 适配器,如果 Netch 提示没有该适配器,可以直接安装 [Tap-Windows](https://build.openvpn.net/downloads/releases/latest/tap-windows-latest-stable.exe) 来获得该适配器
关于更多的模式说明,详见[进阶用法](https://github.com/NormanBB/NetchMode/blob/master/docs/README.zh-CN.md)。
选择完模式后,点击启用,游戏已被代理。这一步需在开启游戏前完成。
## 配置说明
目前netch支持自定义四个配置填入配置名选择相应的服务器和游戏模式按下`Ctrl`与鼠标左键,即可保存当前配置。下次使用时,点击配置名即可快速启用。
~~如果你还觉得不会用可以去用SStap (逃~~

View File

@@ -1,5 +1,6 @@
# Netch
[![](https://img.shields.io/badge/Telegram-频道-blue.svg)](https://t.me/Netch)
> ~~issue已关有问题可进tele群问不保证回答不保证解决咕~~
游戏加速工具
@@ -8,9 +9,11 @@
- [TOC](#toc)
- [简介](#%e7%ae%80%e4%bb%8b)
- [赞助商](#%e8%b5%9e%e5%8a%a9%e5%95%86)
- [截图](#%e6%88%aa%e5%9b%be)
- [新手入门](Basic-usage.md)
- [进阶用法](https://github.com/NormanBB/NetchMode/blob/master/docs/README.zh-CN.md)
- [依赖](#%e4%be%9d%e8%b5%96)
- [语言支持](#语言支持)
## 简介
Netch 是一款 Windows 平台的开源游戏加速工具Netch 可以实现类似 SocksCap64 那样的进程代理,也可以实现 SSTap 那样的全局 TUN/TAP 代理,和 Shadowsocks-Windows 那样的本地 Socks5HTTP 和系统代理。至于连接至远程服务器的代理协议,目前 Netch 支持以下代理协议ShadowsocksVMessSocks5ShadowsocksR
@@ -20,16 +23,26 @@ Netch 是一款 Windows 平台的开源游戏加速工具Netch 可以实现
## 赞助商
开发不易,以下为恰饭时间
[![NyanCAT](sponsor/nyancat.jpg)](https://nyancat.info)
NyanCAT Network全中转高质量节点多条低倍率节点保证流量无忧节点极低延迟涵盖五大洲。Netflix 视频党,游戏党,海外回国党必备,无需年付,月付 19 元起
[Telegram 群组](https://t.me/NyanCaaaat)
[![ManSora](sponsor/mansora.jpg)](https://www.mansora.net/cart.php)
[![Across-GFW](sponsor/across-gfw.jpg)](https://across-gfw.com/register?aff=4739)
这是我所选择的服务器提供商IPLC 专线翻墙、稳定、速度快、价格便宜。欢迎大家使用我的推广链接前去注册:[这里](https://across-gfw.com/register?aff=4739)
## 新手入门
## 截图
![主界面](screenshots/main.zh-CN.png)
[新手入门教程](Basic-usage.md)
## 进阶用法
[进阶教程](https://github.com/NormanBB/NetchMode/blob/master/docs/README.zh-CN.md)
## 依赖
- [Visual C++ 运行库合集](https://www.google.com/search?q=Visual+C%2B%2B+%E8%BF%90%E8%A1%8C%E5%BA%93%E5%90%88%E9%9B%86)
- [.NET Framework 4.8](https://dotnet.microsoft.com/download/dotnet-framework/thank-you/net48-offline-installer)
- [TAP-Windows](https://build.openvpn.net/downloads/releases/tap-windows-9.21.2.exe)
## 语言支持
Netch 支持多种语言,在启动时会根据系统语言选择自身语言。如果需要手动切换语言,可以在启动时加入命令行参数,命令行参数为目前支持的语言代码,可以去 [NetchTranslation/i18n](https://github.com/NetchX/NetchTranslation/tree/master/i18n) 文件夹下查看外部支持的语言代码文件。Netch 目前内置 en-USzh-CN外置 zh-TW。欢迎大家为 [NetchTranslation](https://github.com/NetchX/NetchTranslation) 提供其他语言的翻译
- Microsoft Visual C++ 运行库合集
- [.NET Framework 4.8](https://dotnet.microsoft.com/download/dotnet-framework/net48)

Binary file not shown.

After

Width:  |  Height:  |  Size: 85 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 72 KiB

BIN
docs/sponsor/nyancat.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

2
modes

Submodule modes updated: cff55c0541...8d6f98d43e