簡體   English   中英

從資源寫入文件,其中資源可以是文本或圖像

[英]Write from Resource to file where resource could be text or image

我在嘗試將資源文件寫入磁盤時遇到問題(所有資源文件屬於同一項目和程序集)。

如果我加

var temp = Assembly.GetExecutingAssembly().GetManifestResourceNames();

這將以以下格式返回string[]

Gener.OptionsDialogForm.resources
Gener.ProgressDialog.resources
Gener.Properties.Resources.resources
Gener.g.resources
Gener.Resources.reusable.css
Gener.Resources.other.jpg

數組的最后2個是我想要的僅有2個文件,但我認為不能保證總是如此。 更改代碼后,數組可能會以另一順序通過,所以我無法在給定索引( temp[4] )上顯式調用該項目。

所以我可以

foreach (string item in Assembly
             .GetExecutingAssembly()
             .GetManifestResourceNames())
{
    if (!item.Contains("Gener.Resources."))
        continue;

    //Do whatever I need to do
}

但這太可怕了! 我用這種方法面臨另一個問題。 這不會擴展返回的文件名,只是Name ,因此,我不知道擴展名是什么。

這是當前的代碼

    public void CopyAllFiles()
    {
        var files = Resources.ResourceManager.GetResourceSet(System.Globalization.CultureInfo.CurrentUICulture, true, true);
        //var temp = Assembly.GetExecutingAssembly().GetManifestResourceNames();

        foreach (DictionaryEntry item in files)
        {
            using (var resourceFileStream = Assembly.GetExecutingAssembly().GetManifestResourceStream("Gener.Resources." + item.Key.ToString() + ".css")) // this won't work, I can't hard code .css as the extension could be different
            {
                Stream stream = new FileStream(this.DirPath, FileMode.Create, FileAccess.Write);
                resourceFileStream.CopyTo(stream);
                stream.Dispose();
            }             
        }
        files.Dispose();            
    }

但這似乎...錯了...這是其他人會怎么做的嗎,我確定我丟失了某些東西,而這樣的任務很常見,那就是有更好的解決方案?

資源名稱是可預測的,您可以將名稱傳遞給Assembly.GetManifestResourceStream()方法。

更有效率的是,Visual Studio為此提供了一個設計器,因此您不必猜測需要傳遞的字符串。 使用“項目+屬性”的“資源”選項卡。 單擊添加資源按鈕的下拉箭頭,然后選擇您的文件。 現在,您可以在代碼中使用變量名引用資源。 喜歡:

  File.WriteAllText(path, Properties.Resources.reusable);

請考慮在運行時將資源復制到文件的一般想法。 只需使用安裝程序或XCopy一次復制文件,即可獲得完全相同的結果。 顯着的優點是這些資源將不再占用內存地址空間,並且當您沒有對該目錄的寫訪問權時,也不會遇到麻煩。 這在啟用UAC時很常見。

這就是我用的! 希望它會幫助其他人。 感覺有些駭人聽聞,但行得通!

    /// <summary>
    /// Copies all the files from the Resource Manifest to the relevant folders. 
    /// </summary>
    internal void CopyAllFiles()
    {
        var resourceFiles = Assembly.GetExecutingAssembly().GetManifestResourceNames();

        foreach (var item in resourceFiles)
        {
            string basePath = Resources.ResourceManager.BaseName.Replace("Properties.", "");

            if (!item.Contains(basePath))
                continue;


            var destination = this._rootFolder + "\\" + this._javaScriptFolder + "\\" + item.Replace(basePath + ".", "");

            using (Stream resouceFile = Assembly.GetExecutingAssembly().GetManifestResourceStream(item))
            using (Stream output = File.Create(destination))
            {
                resouceFile.CopyTo(output);
            }
        }
    }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM