【问题标题】:Resource file wrapper not created for Portable class in Visual Studio 2015未为 Visual Studio 2015 中的可移植类创建资源文件包装器
【发布时间】:2016-09-05 03:58:09
【问题描述】:

我正在尝试在可移植类中包含一个资源文件,根据 Microsoft (App Resources for Libraries That Target Multiple Platforms) 的这篇文章,我应该将 Access Modifier 设置为 public:

要在 Visual Studio 中创建强类型包装器,请将 Visual Studio 资源设计器中的主资源文件的访问修饰符设置为 Public。这将创建一个包含强类型 ResourceManager 包装器的 [resourceFileName].designer.cs 或 [resourceFileName].designer.vb 文件。

然后我应该能够使用应该创建的包装类直接访问资源。我的资源文件名为 SharedResources.en-US.resx; SharedResources.fr-FR.resx 等...

所以我应该能够通过调用以下包装类来访问它:

string str = SharedResources.UnsupportedFeature;

但它不会为资源文件创建任何包装文件,即使在我从Internal 转到Public 之后也是如此。我想可能是因为我将它们存储在 Strings 文件夹中,所以我将各种资源文件移动到项目的根目录,但没有任何区别。

有人对我如何解决这个问题有任何想法或建议吗?

谢谢。

更新 1:

奇怪,我注意到当我创建一个刚刚叫 Resources.resx 的新资源文件时,它会在 Resources.Designer.cs 中创建以下内容:

namespace MyCompany.MyApp.Shared.Strings {
    using System;
    using System.Reflection;

    /// <summary>
    ///   A strongly-typed resource class, for looking up localized strings, etc.
    /// </summary>
    // This class was auto-generated by the StronglyTypedResourceBuilder
    // class via a tool like ResGen or Visual Studio.
    // To add or remove a member, edit your .ResX file then rerun ResGen
    // with the /str option, or rebuild your VS project.
    [global::System.CodeDom.Compiler.GeneratedCodeAttribute
    ("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
    [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]

    [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
    internal class Resources {  
        private static global::System.Resources.ResourceManager resourceMan;    
    private static global::System.Globalization.CultureInfo
        .resourceCulture;

        [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute
        ("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
    internal Resources() {
}

/// <summary>
///   Returns the cached ResourceManager instance used by this class.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute
    (global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Resources.ResourceManager ResourceManager 
    {
    get {
      if (object.ReferenceEquals(resourceMan, null)) {
             global::System.Resources.ResourceManager temp = new
             global::System.Resources.ResourceManager
             ("MyCompany.MyApp.Shared.Strings.Resources", 
             typeof(Resources).GetTypeInfo().Assembly);
    resourceMan = temp;
      }
      return resourceMan;
        }
    }

    /// <summary>
    ///   Overrides the current thread's CurrentUICulture property for all
    ///   resource lookups using this strongly typed resource class.
    /// </summary>
    [global::System.ComponentModel.EditorBrowsableAttribute
    (global::System.ComponentModel.EditorBrowsableState.Advanced)]
    internal static global::System.Globalization.CultureInfo Culture {
    get {
        return resourceCulture;
    }
    set {
        resourceCulture = value;
    }
    }

    /// <summary>
    ///   Looks up a localized string similar to Unsupported 
    ///   feature provided.
    /// </summary>
    internal static string UnsupportedFeature {
        get {
        return ResourceManager.GetString("UnsupportedFeature",
                   resourceCulture);
            }
        }
    }
}
  • 如果我重命名文件,此代码将被完全删除。
  • 如果我创建一个名为 Resources.fr-FR.resx 的文件,则不会创建代码。

我会玩弄上面的代码,看看能不能成功。

【问题讨论】:

    标签: c# visual-studio localization embedded-resource portable-class-library


    【解决方案1】:

    好的,我想通了。我提到的 Microsoft 文章中要么没有很好地解释它,要么我完全错过了那部分。无论哪种方式,您都可以通过以下方式使其工作:

    来自您的便携式库:

    1. 创建一个名为 Resources.resx 的默认名称(或任何您想要的名称,但名称要简单,即没有点、破折号等),否则它不会在 Resources.Designer.cs 中生成默认代码

    2. 确保如文章中所述将Access Modifier公开。

    3. 像往常一样通过资源编辑器添加资源字符串。

    4. 为您需要的相关语言创建一个新资源文件,并根据默认文件命名,但添加相关语言代码,即 Resources.fr-FR.resx。请注意,这不会包含 Resources.Designer.fr-FR.cs 中的任何代码(没关系!)

    5. 像往常一样通过资源编辑器添加资源字符串以匹配默认条目。

    6. 在您的可移植类库中创建一个与此类似的辅助类:

      内部类 LocalizeHelper { 公共枚举 LocalizeStringsEnum { 不支持的功能 }

      public static string GetText(LocalizeStringsEnum key)
      {
          switch (key)
          {
              case LocalizeStringsEnum.UnsupportedFeature:
                  return Resources.UnsupportedFeature;
              default:
                  // Should never be raised unless a key is not defined in the enum.
                  throw new ArgumentOutOfRangeException("Unknown key provided");
          }
      }
      
    7. 要从您的可移植类库中调用它,您可以这样调用它:

      public bool MyFunction() { 抛出新异常(LocalizeHelper.GetText (LocalizeStringsEnum.UnsupportedFeature)); }

    就是这样!

    来自您的应用:

    假设您的应用是 UWP 应用,请确保在 OnLaunched 方法中设置 PrimaryLanguageOverride

    protected override void OnLaunched(LaunchActivatedEventArgs e)
    {
        ApplicationLanguages.PrimaryLanguageOverride = "fr-FR"; //To test
        //ApplicationLanguages.PrimaryLanguageOverride =  //Run-time
        //GlobalizationPreferences.Languages[0];
    }
    

    那么在你的代码中,它会是这样的:

    try
    {
        bool test = MyPortableLib.MyFunction();
    }
    catch (Exception ex)
    {
        Debug.WriteLine(ex.Message);
    }
    

    以上内容将以法语(或您的主要语言设置的任何语言)显示异常。

    希望这会有所帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-05-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多