wpf의 문자열 형식 현지화 문제
WPF 3.5에서SP1 i는 데이터 바인딩의 마지막 기능 StringFormat을 사용합니다.
<TextBlock Text="{Binding Path=Model.SelectedNoteBook.OriginalDate, StringFormat='f'}"
FontSize="20" TextTrimming="CharacterEllipsis" />
제가 직면한 문제는 날짜가 항상 영어로 포맷되어 있다는 것입니다.내 시스템이 프랑스어인데도?시스템 날짜를 강제로 따르려면 어떻게 해야 합니까?
// Ensure the current culture passed into bindings is the OS culture.
// By default, WPF uses en-US as the culture, regardless of the system settings.
FrameworkElement.LanguageProperty.OverrideMetadata(
typeof(FrameworkElement),
new FrameworkPropertyMetadata(
XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)));
다음 xml 네임스페이스를 정의합니다.
xmlns:gl="clr-namespace:System.Globalization;assembly=mscorlib"
이제 이 환상적인 해결책을 보십시오.
<TextBlock Text="{Binding Path=Model.SelectedNoteBook.OriginalDate, StringFormat='f', ConverterCulture={x:Static gl:CultureInfo.CurrentCulture}" FontSize="20"TextTrimming="CharacterEllipsis" />
저는 이것이 글로벌 수정이 아니라는 것을 잘 알고 있고 당신은 그것을 당신의 각 바인딩에 요구할 것입니다. 하지만 확실히 그것은 좋은 XAML입니까?제가 알기로는 다음 번에 바인딩이 업데이트될 때 올바른 정보를 사용할 것입니다.CultureInfo.CurrentCulture
또는 당신이 제공한 모든 것.
이 솔루션은 바인딩을 올바른 값으로 즉시 업데이트하지만 매우 드물고 유해하지 않은 것에 대한 많은 코드처럼 보입니다.
저는 로더론의 대답이 대부분의 경우에 효과가 있다는 것을 덧붙이고 싶었습니다.App.xaml.cs 에 다음 코드 줄을 입력하면 텍스트 블록의 날짜가 올바른 문화로 포맷됩니다.
FrameworkElement.LanguageProperty.OverrideMetadata(typeof(FrameworkElement), new FrameworkPropertyMetadata(System.Windows.Markup.XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)));
저는 '대부분의 경우'라고 말합니다.예를 들어, 다음과 같이 즉시 사용할 수 있습니다.
<TextBlock Text="{Binding Path=Date, StringFormat={}{0:d MMMM yyyy}}" />
--> "16 mei 2013" (this is in Dutch)
...그러나 텍스트 블록에서 실행을 사용하는 경우 DateTime은 기본 문화에서 형식이 지정됩니다.
<TextBlock>
<Run Text="Datum: " />
<Run Text="{Binding Path=Date, StringFormat={}{0:d MMMM yyyy}, Mode=OneWay}" />
</TextBlock>
--> "Datum: 16 may 2013" (this is in English, notice the
name of the month "may" vs. "mei")
이것이 작동하려면 Gusdor의 답변이 필요했습니다. 즉, ConverterCulture={x:Static gl:CultureInfo.바인딩에 CurrentCulture}이(가) 있습니다.
<TextBlock>
<Run Text="Datum: " />
<Run Text="{Binding Path=Date, StringFormat={}{0:d MMMM yyyy}, ConverterCulture={x:Static gl:CultureInfo.CurrentCulture}, Mode=OneWay}" />
</TextBlock>
--> "Datum: 16 mei 2013" (=Dutch)
이 추가 답변이 누군가에게 도움이 되길 바랍니다.
최상위 태그에 문화 바로 가기를 삽입하기만 하면 됩니다.
xml:lang="de-DE"
예:
<Window x:Class="MyApp"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xml:lang="de-DE"
Title="MyApp" Height="309" Width="497" Loaded="Window_Loaded">....</Window>
이미 언급했듯이 XAML은 불변 문화(en-US)를 기본값으로 하며 다음을 사용할 수 있습니다.
FrameworkElement.LanguageProperty.OverrideMetadata(
typeof(FrameworkElement),
new FrameworkPropertyMetadata(
XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)));
문화를 현재 문화의 언어에 대한 기본 문화로 설정합니다.그러나 설명이 틀렸습니다. 사용자가 만든 사용자 지정을 볼 수 없기 때문에 현재 문화를 사용하지 않습니다. 항상 언어의 기본값이 됩니다.
사용자 지정과 함께 현재 문화를 실제로 사용하려면 다음을 설정해야 합니다.ConverterCulture
와 함께StringFormat
에 있어서와 같이
Text="{Binding Day, StringFormat='d', ConverterCulture={x:Static gl:CultureInfo.CurrentCulture}}"
와 함께gl
루트 요소에서 글로벌 네임스페이스로 정의됨
xmlns:gl="clr-namespace:System.Globalization;assembly=mscorlib"
프로그램이 실행되는 동안 언어를 변경해야 하는 경우 루트 요소의 언어 속성만 변경하면 됩니다(즉각 효과가 있는지 아니면 하위 요소를 다시 만들어야 하는지는 확실하지 않습니다. 이 경우 최소한 작동합니다.)
element.Language = System.Windows.Markup.XmlLanguage.GetLanguage(culture.IetfLanguageTag);
현지화를 전환하는 전체 코드는 다음과 같은 요소에서도 사용됩니다.<Run />
다음과 같습니다.
Private Shared Sub SetXamlBindingLanguage()
'' For correct regional settings in WPF (e.g. system decimal / dot or comma)
Dim lang = System.Windows.Markup.XmlLanguage.GetLanguage(CultureInfo.CurrentCulture.IetfLanguageTag)
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(TextElement), New FrameworkPropertyMetadata(lang))
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(DefinitionBase), New FrameworkPropertyMetadata(lang))
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(FixedDocument), New FrameworkPropertyMetadata(lang))
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(FixedDocumentSequence), New FrameworkPropertyMetadata(lang))
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(FlowDocument), New FrameworkPropertyMetadata(lang))
FrameworkContentElement.LanguageProperty.OverrideMetadata(GetType(TableColumn), New FrameworkPropertyMetadata(lang))
FrameworkElement.LanguageProperty.OverrideMetadata(GetType(FrameworkElement), New FrameworkPropertyMetadata(lang))
End Sub
런타임에 문화 정보를 변경하려면 동작을 사용할 수 있습니다(아래 참조).
public class CultureBehavior<TControl> : Behavior<TControl>
where TControl : FrameworkElement
{
private readonly IEventAggregator _eventAggregator;
private readonly Action<CultureInfo> _handler;
public CultureBehavior()
{
_handler = (ci) => this.AssociatedObject.Language = XmlLanguage.GetLanguage(ci.IetfLanguageTag);
_eventAggregator = IoC.Container.Resolve<IEventAggregator>();
}
protected override void OnAttached()
{
base.OnAttached();
_eventAggregator
.GetEvent<LanguageChangedEvent>()
.Subscribe(_handler);
_handler.Invoke(CultureInfo.CurrentCulture);
}
protected override void OnDetaching()
{
_eventAggregator
.GetEvent<LanguageChangedEvent>()
.Unsubscribe(_handler);
base.OnDetaching();
}
}
XAML이 아닌 코드로 작업하는 경우 Converter Culture를 다음과 같이 설정할 수 있습니다.
binding.ConverterCulture = System.Globalization.CultureInfo.CurrentCulture;
기본 문화 정의를 사용하는 것과 사용자의 사용자 정의된 문화 정의를 사용하는 것 사이의 미묘한 차이를 지적한 @KZeise에 대한 찬사.
언급URL : https://stackoverflow.com/questions/520115/stringformat-localization-issues-in-wpf
'programing' 카테고리의 다른 글
목록 또는 I 목록 (0) | 2023.05.20 |
---|---|
Xcode/시뮬레이터:이전 iOS 버전을 실행하는 방법은 무엇입니까? (0) | 2023.05.20 |
"Microsoft의 이니셜라이저 유형이 표시됩니다.Azure SDK 2.9 설치 후 ccproj 파일을 열 때 'Cct.CctProjectNode'가 예외를 발생했습니다. (0) | 2023.05.20 |
단일 스크립트를 윈도우즈 배치 및 리눅스 Bash에서 모두 실행하시겠습니까? (0) | 2023.05.20 |
wpf 형식으로 창 닫기 버튼(창 오른쪽 상단 모서리의 빨간색 X 버튼) 이벤트를 포착하는 방법은 무엇입니까? (0) | 2023.05.20 |