使我的应用程序成为打开所有.txt文件的默认应用程序

时间:2014-09-16 02:12:08

标签: c# wpf winforms

发布我的应用程序后,我可以将我的app exe文件指定为打开.txt文件的默认文件。在这里如何获取调用该应用程序的文件的filePath?

    public MainWindow()
    {
        InitializeComponent();
        string filePath = "";
        FileStream fs = new FileStream(filePath, FileMode.Open, FileAccess.Read);
        StreamReader sr = new StreamReader(fs);
        txt.Text = sr.ReadToEnd();
        sr.Close();
        fs.Close();
    }

当用户双击某个来自资源管理器的txt文件时,如何获取filePath?

5 个答案:

答案 0 :(得分:2)

文件args通过命令行参数传递。因此,您需要检查Program.cs文件(可能)以查看string[] args参数。

void Main(string[] args)
{
    string filename;

    if(args != null && args.Length > 0)
        filename = args[0];
    else
        filename = null;

    // use filename as appropriate, perhaps via passing it to your entry Form.
}

本质上,当您将记事本作为默认文本编辑器双击explorer.exe时,test.txt(Windows资源管理器,桌面,开始菜单,您有什么)的调用看起来像是什么像这样:

notepad.exe C:\users\name\desktop\test.txt

它与您在命令行中用于调用robocopy的语法相同(尽管您可能需要更多参数):

robocopy source.txt destination.txt

通过此工作流程,您还可以覆盖默认文件关联行为,以启动您选择读取文件的程序,类似于程序化Open With...。以下将始终打开记事本,无论其他应用程序可能与.jpg扩展名相关联(可能不是记事本)。

notepad.exe C:\users\name\desktop\test.jpg

答案 1 :(得分:2)

有几种方法可以将您的应用程序作为特定文件类型的默认应用程序。

  1. 您可以手动更改注册表值,并为.txt扩展名提供应用程序路径。的 HKEY_CURRENT_USER \ Software \ Classes下
  2. 在设置项目中分配属性:项目属性 - >发布 - >选项 - >文件协议 - > [添加扩展程序]
  3. 您可以编写一些代码来更改注册表并将特定扩展名的默认应用程序关联起来。

  4. [DllImport("Kernel32.dll")]
    private static extern uint GetShortPathName(string lpszLongPath, 
        [Out] StringBuilder lpszShortPath, uint cchBuffer);
    
    // Return short path format of a file name
    private static string ToShortPathName(string longName)
    {
        StringBuilder s = new StringBuilder(1000);
        uint iSize = (uint)s.Capacity;
        uint iRet = GetShortPathName(longName, s, iSize);
        return s.ToString();
    }
    
    // Associate file extension with progID, description, icon and application
    public static void Associate(string extension, 
           string progID, string description, string icon, string application)
    {
        Registry.ClassesRoot.CreateSubKey(extension).SetValue("", progID);
        if (progID != null && progID.Length > 0)
            using (RegistryKey key = Registry.ClassesRoot.CreateSubKey(progID))
            {
                if (description != null)
                    key.SetValue("", description);
                if (icon != null)
                    key.CreateSubKey("DefaultIcon").SetValue("", ToShortPathName(icon));
                if (application != null)
                    key.CreateSubKey(@"Shell\Open\Command").SetValue("", 
                                ToShortPathName(application) + " \"%1\"");
            }
    }
    
    // Return true if extension already associated in registry
    public static bool IsAssociated(string extension)
    {
        return (Registry.ClassesRoot.OpenSubKey(extension, false) != null);
    }
    
    ///How to Associate
    ///.ext: give the extension here ie. .txt
    ///ClassID.ProgID: Give the unique id for your application. ie. MyFirstApplication1001
    ///ext File:Description of your application
    ///YourIcon.ico:Icon file
    ///YourApplication.exe:Your application name
    Associate(".ext", "ClassID.ProgID", "ext File", "YourIcon.ico", "YourApplication.exe");
    

    您还可以阅读本文并从here

    下载相同的示例

答案 2 :(得分:1)

有两种方法可以在.NET中获取命令行参数。您可以在Main方法上添加参数列表,也可以使用Environment.GetCommandLineArgs方法。

var allArgs = Environment.GetCommandLineArgs();
// The first element is the path to the EXE. Skip over it to get the actual arguments.
var userSpecifiedArguments = allArgs.Skip(1);

由于您正在使用WPF(因此无法控制Main方法),因此最好的选择是使用GetCommandLineArgs

答案 3 :(得分:0)

在Matthew Haugen的帮助下,我已经完成了这项工作并且正在为Forms Application工作

Program.cs的

static class Program
{
    [STAThread]
    static void Main(string[] args)
    {
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        Application.Run(new Form1(args != null && args.Length > 0 ? args[0] : ""));
    }
}

表格

public partial class Form1 : Form
{
    public Form1(string fileName)
    {
        InitializeComponent();
        if (fileName != "")
            using (var fs = new FileStream(fileName, FileMode.Open, FileAccess.Read))
            using (var sr = new StreamReader(fs)) textBox1.Text = sr.ReadToEnd();
    }
}

我已经假设它可能对Forms Application有所帮助。但我仍在寻找在WPF中做同样事情的答案。

答案 4 :(得分:0)

以下是WPF的解决方案

Matthew向我展示了如何在Windows窗体应用程序中执行此操作,我研究了一下并找到了wpf的解决方案。

这是我一步一步做的..

首先,我在App.Xaml.cs中添加了一个void Main函数

 public partial class App : Application
{
    [STAThread]

    public static void Main()
    {

    }
}

编译时显示错误说明应用程序的多个入口点。双击时,它会导航到存在实际入口点的App.g.cs文件中。

   public partial class App : System.Windows.Application {

    /// <summary>
    /// InitializeComponent
    /// </summary>
    [System.Diagnostics.DebuggerNonUserCodeAttribute()]
    [System.CodeDom.Compiler.GeneratedCodeAttribute("PresentationBuildTasks", "4.0.0.0")]
    public void InitializeComponent() {

        #line 4 "..\..\App.xaml"
        this.StartupUri = new System.Uri("MainWindow.xaml", System.UriKind.Relative);

        #line default
        #line hidden
    }

    /// <summary>
    /// Application Entry Point.
    /// </summary>
    [System.STAThreadAttribute()]
    [System.Diagnostics.DebuggerNonUserCodeAttribute()]
    [System.CodeDom.Compiler.GeneratedCodeAttribute("PresentationBuildTasks", "4.0.0.0")]
    public static void Main() {
        FileOpen.App app = new FileOpen.App();
        app.InitializeComponent();
        app.Run();
    }
}

现在我删除了所有行并将入口点复制到App.xaml.cs 并且还从App.xaml中删除了startupURI

<Application x:Class="FileOpen.App"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         >
<Application.Resources>

</Application.Resources>

现在是App.g.cs

public partial class App : System.Windows.Application {

    /// <summary>
    /// Application Entry Point.

}

和App.xaml.cs

public partial class App : Application
{
    [System.STAThreadAttribute()]
    [System.Diagnostics.DebuggerNonUserCodeAttribute()]
    [System.CodeDom.Compiler.GeneratedCodeAttribute("PresentationBuildTasks", "4.0.0.0")]
    public static void Main(string[] args)
    {
        MainWindow window = new MainWindow(args != null && args.Length > 0 ? args[0] : "");
        window.ShowDialog();
    }
}

和MainWindow

public partial class MainWindow : Window
{
    public MainWindow(string filePath)
    {
        InitializeComponent();
        if (filePath != "")
            using (var fs = new FileStream(filePath, FileMode.Open, FileAccess.Read))
            using (var sr = new StreamReader(fs)) txt.Text = sr.ReadToEnd();
    }
}