TOC

This article has been localized into Turkish by the community.

WPF Komutları:

WPF Komutlarını Kullanmak

Önceki yazıda WPF komutlarının ne olduğu ve nasıl çalıştığı hakkında bir çok teori açıkladık. Bu bölümde bu komutları kullanıcı arabirimi elemanlarına ilişkilendirerek ve herşeyi birbirine bağlayan komut veri bağlamaları tanımlayarak nasıl gerçekten kullanacağınızı göreceğiz.

Çok basit bir örnekle başlayacağız :

<Window x:Class="WpfTutorialSamples.Commands.UsingCommandsSample"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="UsingCommandsSample" Height="100" Width="200">
    <Window.CommandBindings>
        <CommandBinding Command="ApplicationCommands.New" Executed="NewCommand_Executed" CanExecute="NewCommand_CanExecute" />
    </Window.CommandBindings>

    <StackPanel HorizontalAlignment="Center" VerticalAlignment="Center">
        <Button Command="ApplicationCommands.New">New</Button>
    </StackPanel>
</Window>
using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Input;

namespace WpfTutorialSamples.Commands
{
	public partial class UsingCommandsSample : Window
	{
		public UsingCommandsSample()
		{
			InitializeComponent();
		}

		private void NewCommand_CanExecute(object sender, CanExecuteRoutedEventArgs e)
		{
			e.CanExecute = true;
		}

		private void NewCommand_Executed(object sender, ExecutedRoutedEventArgs e)
		{
			MessageBox.Show("The New command was invoked");
		}
	}
}

Pencereye CommandBindings kolleksiyonuna ekleyerek bir komut veri bağlaması tanımlıyoruz. Command özelliğinde kullanmak istediğimiz komutu belirtiyoruz (.ApplicationCommands kategorisinden New ön tanımlı komutu), birlikte iki olay işleyici metod ismini de belirtiyoruz. Görsel arabirimde ise bir tek Button ve Command özelliğinde yine aynı komutumuzun adını veriyoruz.

Arkaplan kodunda iki olayı işliyoruz. CanExecute işleyen metod WPF'in uygulama boşta beklerken komutun mümkün olup olmadığına bakmak için çağıracağı metod ve biz bu komutun her zaman kullanılabilir olmasını istediğimizden içeriği de çok basit. Olay parametresi e'nin CanExecute özelliğine true değer vererek bunu yaparız.

Executed işleyici metodu ise komut çağrılınca basit bir mesaj kutusu gösterir. Örneği çalıştırır ve butona basarsanız bu mesajı görürsünüz. Bu New komutu ön tanımlı komutlardan olduğu için extra bir bonus kazanırsınız. Butona tıklamak yerine default tuş kombinasyonu olan Ctrl+N tuşlarına basabilirsiniz - aynı eylem gerçekleşecektir -

CanExecute metodunu kullanmak

İlk örnekte CanExecute olay işleyicisini sadece true değer dönecek şekilde yazdık, böylece butona her zaman tıklanabilir. Bununla beraber tabi ki bu tüm butonlar için tüm durumlarda geçerli değil - bir çok durumda uygulamanızın içinde bulunduğu şartlara göre butona tıklama imkanını açıp kapatmak istersiniz.

En çok rastlanan örnek Windows Clipboard kullanan Cut, Copy butonları sadece bir şey seçili olduğunda Paste butonu ise Clipboard'da önceden kopyalanmış bir şey varsa aktif olmalıdır. Bu örnekte aynen bunu gerçekleştiriyoruz :

<Window x:Class="WpfTutorialSamples.Commands.CommandCanExecuteSample"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="CommandCanExecuteSample" Height="200" Width="250">
    <Window.CommandBindings>
        <CommandBinding Command="ApplicationCommands.Cut" CanExecute="CutCommand_CanExecute" Executed="CutCommand_Executed" />
        <CommandBinding Command="ApplicationCommands.Paste" CanExecute="PasteCommand_CanExecute" Executed="PasteCommand_Executed" />
    </Window.CommandBindings>
    <DockPanel>
        <WrapPanel DockPanel.Dock="Top" Margin="3">
            <Button Command="ApplicationCommands.Cut" Width="60">_Cut</Button>
            <Button Command="ApplicationCommands.Paste" Width="60" Margin="3,0">_Paste</Button>
        </WrapPanel>
        <TextBox AcceptsReturn="True" Name="txtEditor" />
    </DockPanel>
</Window>
using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Input;

namespace WpfTutorialSamples.Commands
{
	public partial class CommandCanExecuteSample : Window
	{
		public CommandCanExecuteSample()
		{
			InitializeComponent();
		}

		private void CutCommand_CanExecute(object sender, CanExecuteRoutedEventArgs e)
		{
			e.CanExecute = (txtEditor != null) && (txtEditor.SelectionLength > 0);
		}

		private void CutCommand_Executed(object sender, ExecutedRoutedEventArgs e)
		{
			txtEditor.Cut();
		}

		private void PasteCommand_CanExecute(object sender, CanExecuteRoutedEventArgs e)
		{
			e.CanExecute = Clipboard.ContainsText();
		}

		private void PasteCommand_Executed(object sender, ExecutedRoutedEventArgs e)
		{
			txtEditor.Paste();
		}
	}
}

Bir çift buton ve bir TextBox kontrolünden oluşan basit bir arayüzümüz var. İlk buton keme işlemi ikinci ise yapıştırma işlemi yapacaktır.

Arkaplan kodunda her iki button için ikişer olay metodumuz var. Birinin adı _Executed ile bitiyor ve asıl işi yapıyor (butona tıklanınca yapılaması gerekeni), ve diğer metodlar da CanExecute metodları. Her birinde gördüğünüz gibi söz konusu aksiyonun yapılıp yapılamayacağına karar veren birer lojik uyguladım ve olay argümanı e'nin CanExecute özelliğinde bu değeri döndürdüm.

İşin harika yanı ise butonlarınızı güncellemek için habire bu metodları çağırmak zorunda değilsiniz. WPF uygulamanın boşta beklediği anı görünce otomatikman bunu yapar ve arayüzün hala güncel olmasını garanti eder.

Default komut davranışı ve CommandTarget özelliği

Önceki örnekte gördüğümüz gibi bir grup komutu kullanmak fazla miktarda kod yazmayı gerektiriyor, metod tanımlamaları ve hep benzer şeyler yapan lojik. Bu ihtimaldir ki WPF takımının bazılarını sizin için hazır sumasının sebebi. Gerçekte az önceki örnekteki tüm arkaplan kodlarını yazmadan yapabilirdik, çünkü WPF TextBox kontrolü Cut, Copy, Paste, Undo ve Redo gibi ortak işlemleri zaten hali hazırda işliyor.

WPF bunu Executed ve CanExecute olaylarını sizin için herhangi bir TextBox benzeri yazı kontrolü fokuslandığında kendisi işleyerek yapar. Bu olayları işleyen kod üzerine kendi kodunuzu önceki örnekteki gibi yazmakta serbestsiniz, ama sadece standart davranışı istiyorsanız işi WPF'e bırakabilirsiniz ve TextBox kontrolü işi sizin için yapar. Şimdi örneğimizin aslında ne kadar basit olabileceğini görelim :

<Window x:Class="WpfTutorialSamples.Commands.CommandsWithCommandTargetSample"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="CommandsWithCommandTargetSample" Height="200" Width="250">
    <DockPanel>
        <WrapPanel DockPanel.Dock="Top" Margin="3">
            <Button Command="ApplicationCommands.Cut" CommandTarget="{Binding ElementName=txtEditor}" Width="60">_Cut</Button>
            <Button Command="ApplicationCommands.Paste" CommandTarget="{Binding ElementName=txtEditor}" Width="60" Margin="3,0">_Paste</Button>
        </WrapPanel>
        <TextBox AcceptsReturn="True" Name="txtEditor" />
    </DockPanel>
</Window>

Bu örnek için arkaplan kodu gerekmiyor - biz bu ön tanımlı komutları sadece belirttiğimiz bir kontrolde uygulanmasını istediğimiz için WPF her şeyi bizim için yapar. TextBox kontrolü işi bizim yerimize yapıyor.

Butonlarda CommandTarget özelliklerini WPF komutlarını butonlara bağlamak için nasıl kullandığıma dikkat edin. Bu örneğe özel olarak buna ihtiyaç duyuluyor, çünkü WrapPanel elemanı bir Toolbar ya da Menü gibi fokuslanan elemanı bilemiyor, yoksa bu özelliği vermeye gerek kalmaz fokus alan elemanda komut uygulanırdı, ama her zaman CommandTarget özelliği belirtmek anlaşılırlık bakımından da iyi olacaktır.

Sonuç

WPF komutları ile uğraşmak oldukça düz bir iş, sadece biraz görsel koduna ihtiyaç duyuyor. Tabi ki size birçok yerden erişilen komutlara ulaşma imkanı gibi bir ödül veriyor, ya da WPF'in sizin için hazırladığı son örnekteki gibi kullanabiliyorsuunuz.


This article has been fully translated into the following languages: Is your preferred language not on the list? Click here to help us translate this article into your language!