@@ -91,37 +91,8 @@ RetryCacheCheck:
9191 End Try
9292 DirectoryUtils.Create(PathTemp & "Cache\" )
9393 DirectoryUtils.Create(PathAppdata)
94-
95- # If DEBUG Then
96- Dim FileLockPath = Path.Combine(PathAppdata.TrimEnd( "\" ), "PCL.dev.Lock" )
97- # Else
98- Dim FileLockPath = Path.Combine(PathAppdata.TrimEnd( "\" ), "PCL.Lock" )
99- # End If
100-
10194 '要求单例
102- If BuildType <> BuildTypes.Debug Then
103- If Not GetProgramLock(FileLockPath) Then
104- Dim IsLocked = False
105- Dim ShouldWaitForExit As Boolean = e.Args.Length > 0 AndAlso e.Args( 0 ) = "--wait" '要求等待已有的 PCL 退出
106- If Not ShouldWaitForExit Then
107- DropToTopByLock(FileLockPath)
108- Beep()
109- Environment.Exit(ProcessReturnValues.Cancel)
110- End If
111- For i = 0 To 10
112- If GetProgramLock(FileLockPath) Then
113- IsLocked = True
114- Exit For
115- End If
116- Thread.Sleep( 500 )
117- Next
118- If Not IsLocked Then
119- DropToTopByLock(FileLockPath)
120- Beep()
121- Environment.Exit(ProcessReturnValues.Cancel)
122- End If
123- End If
124- End If
95+ WaitingMutex(e)
12596 '设置 ToolTipService 默认值
12697 ToolTipService.InitialShowDelayProperty.OverrideMetadata( GetType (DependencyObject), New FrameworkPropertyMetadata( 300 ))
12798 ToolTipService.BetweenShowDelayProperty.OverrideMetadata( GetType (DependencyObject), New FrameworkPropertyMetadata( 400 ))
@@ -173,38 +144,37 @@ RetryCacheCheck:
173144 FormMain.EndProgramForce(ProcessReturnValues.Exception)
174145 End Try
175146 End Sub
176-
177- Private Shared KernelLock As Mutex
178-
179147 ''' <summary>
180- ''' 尝试获取单例锁
148+ ''' 要求程序以单例运行。
149+ ''' 如果已在运行,则将其窗口拖出来并播放提示音,然后结束当前进程。
181150 ''' </summary>
182- ''' <param name="LockPath">文件锁位置</param>
183- ''' <returns>一个值用于指示是否获得文件锁</returns>
184- Private Function GetProgramLock(LockPath As String ) As Boolean
151+ Private Shared Sub WaitingMutex(e As StartupEventArgs)
152+ If BuildType = BuildTypes.Debug Then Return
185153 Try
186- Dim IsLocked = False
187- KernelLock = New Mutex( True , "Local\Plain Craft Launcher" , IsLocked)
188- If Not IsLocked Then Return False
189- Logger.Info( "获取单例锁成功" )
190- File.WriteAllText(LockPath, Process.GetCurrentProcess().Id.ToString())
191- Return IsLocked
154+ Dim MutexCreatedNew As Boolean
155+ PclMutex = New Mutex( True , "PCL_SingletonMutex" , MutexCreatedNew)
156+ If MutexCreatedNew Then Return
157+ Logger.Warn( "已有一个 PCL 实例正在运行" )
158+ '等待已有的 PCL 退出
159+ If e.Args.Length > 0 AndAlso e.Args( 0 ) = "--wait" Then
160+ Try
161+ If PclMutex.WaitOne( 10000 ) Then Return '等待至多 10 秒
162+ Catch Ignored As AbandonedMutexException
163+ Return '已有实例异常退出,继续启动
164+ End Try
165+ End If
166+ '将已有的 PCL 窗口拖出来
167+ Dim WindowHwnd As IntPtr = FindWindow( Nothing , "Plain Craft Launcher " )
168+ If WindowHwnd = IntPtr.Zero Then WindowHwnd = FindWindow( Nothing , "Plain Craft Launcher 2 " )
169+ If WindowHwnd <> IntPtr.Zero Then ShowWindowToTop(WindowHwnd)
170+ '播放提示音并退出
171+ Beep()
172+ Environment.[Exit](ProcessReturnValues.Cancel)
192173 Catch ex As Exception
193-
174+ Logger.Warn(ex, "单例检查失败" )
194175 End Try
195-
196- Return False
197- End Function
198-
199- ''' <summary>
200- ''' 从文件锁中尝试拖出进程
201- ''' </summary>
202- Public Sub DropToTopByLock(LockPath As String )
203- Dim Pid As Integer
204- If Not Integer .TryParse(File.ReadAllText(LockPath), Pid) Then Return
205- Dim Handle = Process.GetProcessById(Pid)?.MainWindowHandle
206- If Handle <> Intptr.Zero Then ShowWindowToTop(Handle)
207176 End Sub
177+ Private Shared PclMutex As Mutex
208178
209179 '结束
210180 Private Sub Application_SessionEnding(sender As Object , e As SessionEndingCancelEventArgs) Handles Me .SessionEnding
0 commit comments