Kihagyás

Eseménykezelés és adatok megjelenítése

A JavaFX controllerhez hasonlóan a WPF ablak C# fájlja reagál a gombnyomásra és kezeli a felület elemeit. A MainWindow.xaml és MainWindow.xaml.cs ugyanannak a partial osztálynak két része. Az x:Name nevek az InitializeComponent() hívás után használhatók.

Felirat módosítása és beviteli mező olvasása

Az előző fejezet egyszerű felületéhez a következő C# kód tartozik:

MainWindow.xaml.cs
using System.Windows;

namespace HelloWpf;

public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }

    private void HelloButton_Click(object sender, RoutedEventArgs e)
    {
        string nev = NameTextBox.Text.Trim();
        WelcomeText.Text = string.IsNullOrEmpty(nev)
            ? "Adj meg egy nevet!"
            : $"Szia, {nev}!";
    }
}

A Click="HelloButton_Click" a XAML-ben összeköti a gombot a metódussal. A JavaFX @FXML mező és onAction mintájához hasonló, de a WPF a partial osztály generált részén keresztül teszi elérhetővé a névvel ellátott elemeket. Python Tkinterben a gomb command paraméteréhez függvényt rendelhetünk.

Táblázat feltöltése CSV-ből

A Java-fejezet TableView példájához hasonlóan készítsünk egy gombot, amely fájlt választ, majd DataGrid vezérlőben megjeleníti az adatokat. A gyakorlófájl első sora fejléc, a további sorok név;életkor alakúak:

diakok.csv
nev;kor
Anna;17
Béla;18

1. A felület

MainWindow.xaml
<Window x:Class="HelloWpf.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Diákok" Height="350" Width="450">
    <DockPanel Margin="16">
        <Button DockPanel.Dock="Top" Content="CSV megnyitása"
                Click="OpenFileButton_Click" Margin="0,0,0,12" />
        <DataGrid x:Name="StudentsGrid" AutoGenerateColumns="False"
                  IsReadOnly="True">
            <DataGrid.Columns>
                <DataGridTextColumn Header="Név" Binding="{Binding Nev}" Width="*" />
                <DataGridTextColumn Header="Életkor" Binding="{Binding Kor}" Width="*" />
            </DataGrid.Columns>
        </DataGrid>
    </DockPanel>
</Window>

2. A sorok osztálya

A DataGrid a nyilvános tulajdonságokat olvassa. Ha egy már megjelenített sor tulajdonsága is változik, értesítéshez INotifyPropertyChanged kell; ebben a példában a sorok betöltés után nem módosulnak.

Diak.cs
namespace HelloWpf;

public class Diak
{
    public string Nev { get; }
    public int Kor { get; }

    public Diak(string nev, int kor)
    {
        Nev = nev;
        Kor = kor;
    }
}

3. Fájlválasztás és adatbeolvasás

Az OpenFileDialog megnyitja a Windows fájlválasztó ablakát. A ShowDialog() == true csak sikeres választáskor igaz. Az ObservableCollection változásairól a táblázat értesül.

MainWindow.xaml.cs
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Windows;
using Microsoft.Win32;

namespace HelloWpf;

public partial class MainWindow : Window
{
    private readonly ObservableCollection<Diak> diakok = new();

    public MainWindow()
    {
        InitializeComponent();
        StudentsGrid.ItemsSource = diakok;
    }

    private void OpenFileButton_Click(object sender, RoutedEventArgs e)
    {
        OpenFileDialog dialog = new()
        {
            Filter = "CSV-fájlok (*.csv)|*.csv|Minden fájl (*.*)|*.*"
        };

        if (dialog.ShowDialog() != true) return;

        try
        {
            List<Diak> beolvasott = new();
            foreach (string sor in File.ReadLines(dialog.FileName).Skip(1))
            {
                string[] mezok = sor.Split(';');
                if (mezok.Length != 2 || !int.TryParse(mezok[1], out int kor))
                {
                    MessageBox.Show($"Hibás sor: {sor}");
                    return;
                }

                beolvasott.Add(new Diak(mezok[0], kor));
            }

            diakok.Clear();
            foreach (Diak diak in beolvasott) diakok.Add(diak);
        }
        catch (IOException ex)
        {
            MessageBox.Show($"A fájl nem olvasható: {ex.Message}");
        }
        catch (UnauthorizedAccessException ex)
        {
            MessageBox.Show($"Nincs hozzáférés a fájlhoz: {ex.Message}");
        }
    }
}

A példában előbb ideiglenes listába olvasunk, és csak sikeres feldolgozás után cseréljük le a táblázat adatait. Az egyszerű Split(';') csak gyakorló CSV-hez megfelelő; idézőjeles mezőket tartalmazó fájlhoz CSV-könyvtár szükséges.