간단한 C# .NET 4.0 응용 프로그램을 개발 중이며 여러 언어로 현지화하고 싶습니다. 그러나 현지화를 위해 만든 위성 어셈블리 (즉, de/MyApp.resources.dll)는 해당 dll과 해당 폴더를 드래그하여 단순성을 파괴합니다.C# 단일 어셈블리 다국 언어 응용 프로그램 - 리소스가 제대로로드되지 않는다.
그래서 내가 dll을 주 어셈블리에 포함시키는 방법을 찾았으므로 최종 사용자에게 실행 파일 만 보내야했습니다. 나는 this very promising question을 우연히 만나고 그에게 총을 줬다. 내가 만든 다음
fart.exe "$(ProjectDir)*.Designer.cs "System.ComponentModel.ComponentResourceManager" "SingleAssemblyComponentResourceManager"
:
은 제안 된 솔루션에 클래스를 도입 한 후, 나는 사전 빌드 명령 FART을 사용하여 .Designer.cs 파일에 SingleAssemblyResourceManager와는 ResourceManager의 찾을 수있는 모든 발행 수를 교체 배치과 같이 파일 :
$(ProjectDir)postbuild.bat $(TargetDir) $(TargetName)
:
"%ProgramFiles%\ILRepack.exe" /t:exe /out:%1TempProg.exe %1%2.exe %1es\%2.resources.dll
IF %ERRORLEVEL% NEQ 0 GOTO END
"%ProgramFiles%\ILRepack.exe" /t:exe /out:%1TempProg2.exe %1TempProg.exe %1de\%2.resources.dll
IF %ERRORLEVEL% NEQ 0 GOTO END
"%ProgramFiles%\ILRepack.exe" /t:exe /out:%1SA_%2.exe %1TempProg2.exe %1tr\%2.resources.dll
IF %ERRORLEVEL% NEQ 0 GOTO END
del %1%2.exe
del %1%2.pdb
del %1TempProg.exe
del %1TempProg.pdb
del %1TempProg2.exe
del %1TempProg2.pdb
rmdir %1es /S /Q
rmdir %1de /S /Q
rmdir %1tr /S /Q
:END
그리고는 빌드 후 명령에서 호출
참고 :이 경우 TargetName과 ProjectName은 동일합니다.
성공적으로 빌드되었지만 예상대로 작동하지 않습니다 ... 양식이 InstalledUICulture 언어 (사용 가능한 경우)로 표시되어야합니다.
Thread.CurrentThread.CurrentUICulture = CultureInfo.InstalledUICulture;
프로그램의 "표준"버전에서 속임수를 썼는지 :이를 위해, 나는이 줄을 InitializeComponent를() 이전에 추가했다. 더 이상. 하나! 또한 ComboBox를 통해 런타임에 언어를 변경할 수있는 약간의 컨트롤을 추가했습니다.
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
if (comboBox1.SelectedItem.ToString() == "English (Default)")
{
Thread.CurrentThread.CurrentUICulture = new CultureInfo("en");
ChangeLanguage("en");
}
else if (comboBox1.SelectedItem.ToString() == "Español")
{
Thread.CurrentThread.CurrentUICulture = new CultureInfo("es");
ChangeLanguage("es");
}
else if (comboBox1.SelectedItem.ToString() == "Deutsch")
{
Thread.CurrentThread.CurrentUICulture = new CultureInfo("de");
ChangeLanguage("de");
}
else if (comboBox1.SelectedItem.ToString() == "Turkce")
{
Thread.CurrentThread.CurrentUICulture = new CultureInfo("tr");
ChangeLanguage("tr");
}
}
private void ChangeLanguage(string lang)
{
foreach (Control c in this.Controls)
{
SingleAssemblyComponentResourceManager resources = new SingleAssemblyComponentResourceManager(typeof(Form1));
resources.ApplyResources(c, c.Name, new CultureInfo(lang));
if (c.ToString().StartsWith("System.Windows.Forms.GroupBox"))
{
foreach (Control child in c.Controls)
{
SingleAssemblyComponentResourceManager resources_child = new SingleAssemblyComponentResourceManager(typeof(Form1));
resources_child.ApplyResources(child, child.Name, new CultureInfo(lang));
}
}
}
}
을 그리고이 양식 언어를 변경 않습니다 다음과 같이 코드입니다. 따라서 dll은 실제로 exe에 포함됩니다. 그렇다면 왜 InitializeComponent는 적절한 리소스를로드하지 않습니까? Designer 코드를 검사하고 ResourceManager가 SingleAssemblyResourceManager로 대체되었습니다.
또한 단추 모양의 텍스트 이외에 MessageBoxes 및 기타 등등의 언어마다 strings.resx 파일이 있는데 그 중 하나는 작동하지 않는 것 같습니다. 하지만 그것은 또 다른 질문 일 수 있습니다.
원래 솔루션은 NET 2.0 환경 용으로 설계되었으며 ResourceSet이 더 이상 사용되지 않는다는 것을 알고 있지만 은이어야한다고 생각합니다.
내가 들여다보아야 할 부분에 대한 유용한 정보는 정말 멋지다.
내가 .NET 2.0 .NET 4.0에서 변경 같은 문제에 직면했다 (이것은 SingleAssemblyComponentResourceManager 및 .NET 2.0와 매력으로 일) 코드의 귀하의 라인 InitializeComponent()를 호출하기 전에; 마술처럼 고정시켰다. 그래도 여전히 현악기 부분은 나에게도 효과가 없다! :/이것에 대한 새로운 해결책이 있습니까? – Gerrit