Question :
I have a Data Grid in WPF that has columns of CPF, RG, ZIP, and others, I need to do the formatting for:
CPF: 111.111.111-11
RG: 11.111.111-1 With number at end
RG: 11.111.111-A With letter at the end
CEP: 11111-11
Just fill in the data and do not format.
<Window x_Class="ProjSistema.Wpf.Cadastro.Teste"
xmlns_x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Teste" Height="300" Width="300">
<Grid>
<DataGrid Name="dtgTeste" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Header="CPF" MinWidth="100" Binding=" {Binding CPF, StringFormat={}{0:###.###.###-##}}"/>
<DataGridTextColumn Header="RG" MinWidth="100" Binding="{Binding RG, StringFormat={}{0:##.###.###-#}}" />
<DataGridTextColumn Header="CEP" MinWidth="100" Binding="{Binding CEP, StringFormat={}{0:#####-##}}" />
</DataGrid.Columns>
</DataGrid>
</Grid>
public partial class Teste : Window
{
public Teste()
{
InitializeComponent();
List<PropriedadeTeste> lstTeste = new List<PropriedadeTeste>();
PropriedadeTeste propTeste = new PropriedadeTeste();
propTeste.CPF = "11111111111";
propTeste.RG = "111111111";
propTeste.CEP = "11111111";
lstTeste.Add(propTeste);
dtgTeste.ItemsSource = lstTeste;
}
}
Answer :
You can apply the StringFormat to Binding this way:
<DataGrid Name="dtgTeste" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Header="CPF" Binding="{Binding CPF, StringFormat={}{0:###.###.###-##}}"/>
<DataGridTextColumn Header="RG" Binding="{Binding RG, StringFormat={}{0:##.###.###-#}}" />
<DataGridTextColumn Header="CEP" Binding="{Binding CEP, StringFormat={}{0:#####-##}}" />
</DataGrid.Columns>
</DataGrid>
There are also other methods creating a custom class to do the formatting.
Basically you will create a class or struct that contains the data you want to bind to the datagrid and this class will be responsible for receiving and formatting the data (since this data type can not be formatted)
(in the example below format a field TimeSpan
in Text with values in mm:ss
and its corresponding in centesimal basis (total minutes)
public class InformacaoGridMeio: ViewModelBase
{
public long Id { get; set; }
public int Execucao { get; set; }
public TimeSpan TempoExecucaoTime { get; set; }
public string TempoExecucao => TempoExecucaoTime != TimeSpan.Zero
? $"{TempoExecucaoTime.Minutes:00}:{TempoExecucaoTime.Seconds:00} ({TempoExecucaoTime.TotalMinutes:00.00})"
: "--:-- (--,--)";
}
After creating this class, create your property in the ViewModel and this property is bound to the DataGrid
public ObservableCollection<InformacaoGridMeio> DataGridMeio
{
get { return _gridMeio; }
set { _gridMeio = value; OnPropertyChanged("DataGridMeio"); }
}
<DataGrid ColumnWidth="*"
AutoGenerateColumns="False"
SelectionMode="Single"
HorizontalContentAlignment="Center"
ItemsSource="{Binding DataGridMeio}"
VerticalScrollBarVisibility="Auto"
HorizontalScrollBarVisibility="Auto"
ScrollViewer.CanContentScroll="True"
>
Make a friend convert.
<DataGridTextColumn Header="CPF" MinWidth="100" Binding=" {Binding CPF, Converter={StaticResource NationalRegistrationConverter}}"/>
Follow the converter I use.
/// <summary>
/// Valida um texto para ver se é um CNPJ ou CPF
/// </summary>
[ValueConversion(typeof(object), typeof(String))]
public class NationalRegistrationValueConverter : IValueConverter
{
/// <summary>
/// Converte o valor para o bindind de um objeto source
/// </summary>
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
// Se não estiver vazio
if (value != null)
{
// Variaveis
string OldValue = ((string)value).ToString().Trim();
string NewValue = "";
// Se tiver 10 caracteres
if (OldValue.Length == 11)
{
// Recebe o valor formatado
NewValue = OldValue.Insert(3, ".").Insert(7, ".").Insert(11, "-"); ;
}
// Se tiver 11 caracteres
else if (OldValue.Length == 14)
{
// Recebe o valor formatado
NewValue = OldValue.Insert(2, ".").Insert(6, ".").Insert(10, "/").Insert(15, "-");
}
// Retorna o novo valor
return NewValue;
}
// Retorna o valor que veio
return value;
}
/// <summary>
/// Converte o valor do binding devolta para o objeto source
/// </summary>
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
// Se nao estiver vazio
if (value != null)
{
// Recebe o valor sem os caracteres especiais
string OldValue = value.ToString().Replace("-", string.Empty).Replace("/", "").Replace(".", "");
// Retorna o valor em decimal
return OldValue;
}
// Retorna o valor
return value;
}
}
Do not forget to declare in the feature of your window or control the convert.
<Window.Resources>
<control:NationalRegistrationValueConverter x_Key="NationalRegistrationConverter"/>
</Window.Resources>