C# winform程式實現開機自啟動,並且識別是開機啟動還是雙擊啟動

来源:https://www.cnblogs.com/hjsstudio/archive/2018/10/29/9863857.html
-Advertisement-
Play Games

開機啟動程式,在很多場合都會用到,尤其是那種在後臺運行的程式。 效果圖: 以上兩幅圖都用到了命令行啟動程式,為了模擬開機啟動或者其他程式調用此程式。 第一幅圖:程式啟動可以根據不同參數,執行不同的操作。如果是雙擊啟動,就自動運行邏輯代碼,如果是帶特定參數啟動,就自動運行邏輯代碼。 第二幅圖:winf ...


開機啟動程式,在很多場合都會用到,尤其是那種在後臺運行的程式。

效果圖:

 

 

以上兩幅圖都用到了命令行啟動程式,為了模擬開機啟動或者其他程式調用此程式。

第一幅圖:程式啟動可以根據不同參數,執行不同的操作。如果是雙擊啟動,就自動運行邏輯代碼,如果是帶特定參數啟動,就自動運行邏輯代碼。

第二幅圖:winform 程式設置開機啟動,模擬雙擊啟動和開機啟動的不同效果。

 

開機啟動並自動運行方法:其實思路很簡單,就是將程式添加到註冊表中,這設置值的時候,加一個參數就可以了。然後程式在入口函數處判斷啟動參數,如果有啟動參數,就走自動運行邏輯代碼,如果沒有,就只是程式啟動,並不運行邏輯代碼。

 

【Main參數】

   在C/C++中,我們很明確的知道 main(int argc, char *argv[]/*, char *envp[]*/) 函數有兩(三)個參數,第三個參數一般用得少,我是還沒用到過。所以常見的都是用兩個參數。第一個是參數個數,非負數。第二個是表示從執行環境傳遞給程式的各個實參。也就是說,我們要用程式入口參數,只需要判斷argc的值,然後使用數組取argv的值就行。

  那麼到了C#就變的更簡單了。直接變成 string[] 了。那麼你只要遍歷這個字元串數組就可以了。

  我們用VS創建命令行工程的時候,如果是命令行程式那麼VS會預設使用帶參數的main函數:void Main(string [] args);如果是winform工程,VS是預設使用void Main()。其實無論預設使用哪個都無所謂,主要是自己要清楚main函數的格式,以及代表的含義。main函數不光有參數,還可以有返回值。其實我們平時寫的C#工程中main函數看似沒有返回值,其實是可以帶有int類型的返回值的。如果你不清楚這一塊,傳送門

  那如果我們用的是 void Main() 這種形式我們怎麼獲取程式入庫參數?這裡其實是只是一個錶面現象。別以為你不帶參數,我就獲取不到了 ^_^ 。微軟為我們提供了一個類:Environment。這個類比較強大。如果你還不清楚怎麼用,那去 MSDN 搜一下就會了。獲取命令行參數也就一個函數而已: string[] Environment.GetCommandLineArgs();使用這個方法需要註意就是返回值是數組類型,第一個元素包含正在執行的程式的文件名,從第二個參數開始,才是命令行參數。其實這個辦法就剛好解決了 winform 程式中獲取命令行參數的問題。

【註冊表操作】

將程式啟動寫入註冊表實現開機啟動,這個感覺沒什麼好說的。使用固定方法操作就行。不過用有一點需要註意就是在訪問註冊表的時候可能會提示沒有許可權,你這個網上百度有好多方法。但是MSDN中也給出了方法。就是在工程的中添加應用程式文件清單中修改一句就可以了。

 

核心代碼:

using System;
using Microsoft.Win32;

namespace AutoStartRun
{
    public sealed class SystemHelper
    {
        private SystemHelper() { }

        /// <summary>
        /// 設置程式開機啟動
        /// </summary>
        /// <param name="strAppPath">應用程式exe所在文件夾</param>
        /// <param name="strAppName">應用程式exe名稱</param>
        /// <param name="bIsAutoRun">自動運行狀態</param>
        public static void SetAutoRun(string strAppPath, string strAppName, bool bIsAutoRun)
        {
            try
            {
                if (string.IsNullOrWhiteSpace(strAppPath)
                    || string.IsNullOrWhiteSpace(strAppName))
                {
                    throw new Exception("應用程式路徑或名稱為空!");
                }

                RegistryKey reg = Registry.LocalMachine;
                RegistryKey run = reg.CreateSubKey(@"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Run\");

                if (bIsAutoRun)
                {
                    run.SetValue(strAppName, strAppPath);
                }
                else
                {
                    if (null != run.GetValue(strAppName))
                    {
                        run.DeleteValue(strAppName);
                    }
                }

                run.Close();
                reg.Close();
            }
            catch (Exception ex)
            {
                throw new Exception(ex.Message, ex);
            }
        }

        /// <summary>
        /// 判斷是否開機啟動
        /// </summary>
        /// <param name="strAppPath">應用程式路徑</param>
        /// <param name="strAppName">應用程式名稱</param>
        /// <returns></returns>
        public static bool IsAutoRun(string strAppPath, string strAppName)
        {
            try
            {
                RegistryKey reg = Registry.LocalMachine;
                RegistryKey software = reg.OpenSubKey(@"SOFTWARE");
                RegistryKey run = reg.OpenSubKey(@"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Run\");
                object key = run.GetValue(strAppName);
                software.Close();
                run.Close();
                if (null == key || !strAppPath.Equals(key.ToString()))
                {
                    return false;
                }
                return true;
            }
            catch (Exception ex)
            {
                throw new Exception(ex.Message, ex);
            }
        }
    }
}

 調用方法:

        /// <summary>
        /// 設置程式開機自啟動
        /// </summary>
        private void SetAutoRun()
        {
            string strFilePath = Application.ExecutablePath;
            string strFileName = System.IO.Path.GetFileName(strFilePath);

            try
            {
                SystemHelper.SetAutoRun(strFilePath + " -autostart", strFileName, !menuAutoRun.Checked);
                menuAutoRun.Checked = !menuAutoRun.Checked;
            }
            catch (Exception ex)
            {
                MessageBox.Show(this, ex.Message, "錯誤提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }
        }        

設置開機啟動就是如此簡單。

【開機啟動並運行】

 那這個就不用說了,將命令行參數和開機註冊表操作結合起來就可以了。

示例代碼:

        /// <summary>
        /// 檢查是否開機啟動,並設置控制項狀態
        /// </summary>
        private void CheckAutoRun()
        { 
            string strFilePath = Application.ExecutablePath;
            string strFileName = System.IO.Path.GetFileName(strFilePath);

            if (SystemHelper.IsAutoRun(strFilePath + " -autostart", strFileName))
            {
                menuAutoRun.Checked = true;
            }
            else
            {
                menuAutoRun.Checked = false;
            }
        }

        private void AutoRun()
        {
            if (menuAutoRun.Checked)
            {
                string[] strArgs = Environment.GetCommandLineArgs();
                if (strArgs.Length >= 2 && strArgs[1].Equals("-autorun"))
                {
                    labText.Text = "我是開機自啟動運行...";
                }
            }
        }

 

 獻上 demo

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 引用鏈接:https://www.cnblogs.com/duwenxing/p/7421100.html 目的 用途 1.在引用的使用中,單純給某個變數去別名是毫無意義的,引用的目的主要用於在函數參數的傳遞中,解決大塊數據或對象的傳遞效率和空間不如意的問題 2.用引用傳遞函數的參數,能保證參數在傳 ...
  • 聲明:本文為www.cnc6.cn原創,轉載時請註明出處,謝謝! 一、編寫Person與City類,如下: 二、為以上兩個類建立一些數據,存儲於persons與cities中,如下: 三、Join第一種用法: 官方釋義:基於匹配鍵對兩個序列的元素進行關聯。使用預設的相等比較器對鍵進行比較。 這個與數 ...
  • 幫助類 using System;using System.Collections.Generic;using System.ComponentModel;using System.Linq;using System.Web; namespace WebApplication5{ public cl ...
  • <!DOCTYPE html><html xmlns="http://www.w3.org/1999/xhtml"><head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title></title> ...
  • 在創建多個控制項後,有些控制項會發生重疊,那麼就需要在滑鼠按下它時能顯示在最上層,下麵通過先將按下操作的控制項刪除然後再重建,就達到讓它顯示在最上層了 ...
  • 1)避免使用ArrayList。 因為任何對象添加到ArrayList都要封箱為System.Object類型,從ArrayList取出數據時,要拆箱回實際的類型。建議使用自定義的集合類型代替ArrayList。.net 2.0提供了一個新的類型,叫泛型,這是一個強類型,使用泛型集合就可以避免了封箱 ...
  • 好久沒有更新文章了,前段時間寫了一系列的文章放到桌面了,想著修修改改,後來系統中勒索病毒了還被公司網路安全的抓到是我電腦,後來裝系統文章給裝丟了。然後好長一段時間沒有寫了。 今天記錄一下AspNetCore 部署Docker+Centos 7 這裡說明一下:Docker 需要用Centos7版本的操 ...
  • 考慮到很多面試可能會考察冒泡排序的用法,所以特地花時間釐清了一下思路。下麵說一下我的思路:冒泡排序核心就是比較方法,冒泡排序的比較方法顧名思義就是像氣泡一樣,最大(或者最小)的數往上冒。普通比較幾個數,我們可以用if(a>b)然後c=a;b=a 。。。。這類方法,把大數暫存到c中,然後小的數存到原本 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...