wykład 1

Transkrypt

wykład 1
Programowanie obiektowe i zdarzeniowe
wykład 1 – Wprowadzenie do programowania zdarzeniowego
Wymagania wstępne: Znajomość podstaw programowania.
Efekty kształcenia: Umiejętność tworzenia prostych aplikacji okienkowych w środowisku
Microsoft Visual Studio, wykorzystujących techniki programowania obiektowego w języku C#.
Treści kształcenia:
1. Wprowadzenie do WPF. Tworzenie interfejsu użytkownika.
2. Pojecie klasy i obiektu. Składniki klas – pola i metody. Konstruktory.
3. Okna dialogowe i kontrolki zawartości. Wiązanie danych.
4. Kompozycja. Kolekcje. Kontrolki list.
5. Dziedziczenie.
6. Polimorfizm.
7. Wyjątki. Style.
8. Grafika i animacja w WPF.
Oprogramowanie: Microsoft Visual Studio 2008 lub nowsze (może być w wersji Express)
wraz z dostępnym w nim systemem pomocy (MSDN).
Dodatkowa literatura:
1. Adam Boduch, Wstęp do programowania w języku C#, Helion
2. Krzysztof Rychlicki-Kicior, Tworzenie aplikacji graficznych w .NET 3.0, Helion
3. Matthew MacDonald, Pro WPF in C# 2008: Windows Presentation Foundation with
.NET 3.5
1/34
Co to jest programowanie obiektowe? Co to jest programowanie zdarzeniowe?
Typowa aplikacja konsolowa (w C):
#include "stdio.h"
int main()
{
int a, b, c;
printf("Podaj pierwszą liczbę: ");
scanf("%d", &a);
printf("Podaj drugą liczbę: ");
scanf("%d", &b);
c = a + b;
printf("Suma = %d", c);
return 0;
}
2/34
Co to jest programowanie obiektowe? Co to jest programowanie zdarzeniowe?
Typowa aplikacja konsolowa (w C++):
#include "iostream"
using namespace std;
int main()
{
int a, b, c;
cout << "Podaj pierwszą liczbę: ";
cin >> a;
cout << "Podaj drugą liczbę: ";
cin >> b;
c = a + b;
cout << "Suma = " << c;
return 0;
}
3/34
Co to jest programowanie obiektowe? Co to jest programowanie zdarzeniowe?
Typowa aplikacja konsolowa (w C#):
using System;
namespace ConsoleApplication1 {
class Program {
static void Main(string[] args)
{
int a, b, c;
Console.Write("Podaj pierwszą liczbę: ");
a = int.Parse(Console.ReadLine());
Console.Write("Podaj drugą liczbę: ");
b = int.Parse(Console.ReadLine());
c = a + b;
Console.Write("Suma = {0}", c);
Console.ReadKey();
}
}
}
4/34
Jak powinna wyglądać aplikacja okienkowa?
Krok pierwszy – tworzenie interfejsu użytkownika (wizualne lub w kodzie).
5/34
Jak powinna wyglądać aplikacja okienkowa?
Krok drugi – obsługa zdarzeń.
(chcemy, aby akcja użytkownika spowodowała
wykonanie naszego kodu)
void Oblicz(...)
{
...
...
...
}
6/34
Jak powinna wyglądać aplikacja okienkowa?
Krok trzeci – interakcja z kontrolkami.
(chcemy odczytać wprowadzone przez
użytkownika dane, wykonać obliczenia
i wyświetlić wynik)
void Oblicz(...)
{
...
...
...
}
7/34
Dlaczego programowanie obiektowe?
•
•
•
•
Jest bliższe postrzeganiu świata przez człowieka, który najpierw dostrzega pewne
rzeczy, pojęcia (obiekty), a nie wykonywane przez nie czynności (funkcje).
W programowaniu obiektowym, program to zbiór obiektów posiadających
określone cechy (właściwości). Mogą one wchodzić między sobą w interakcje lub
łączyć się w bardziej złożone struktury.
Obiekt to serwer usług – może wykonać pewną operację, jeśli zostanie poproszony.
Taka usługa nazywa się metodą obiektu.
W aplikacji okienkowej obiektami są np. elementy, z których składamy interfejs
użytkownika – okno, pola tekstowe, przyciski, etc.
Język C# (C Sharp):
• Prosty, nowoczesny, uniwersalny, język zorientowany obiektowo.
• Zaprojektowany przez Microsoft, powiązany z platformą .NET.
• Programy w nim napisane wymagają środowiska uruchomieniowego (takiego
jak .NET lub Mono).
8/34
WPF – Windows Presentation Foundation
•
•
•
•
•
•
•
•
•
Interfejs programowania aplikacji okienkowych w systemie Windows.
Wykorzystuje DirectX do rysowania okien i zawartości.
Niezależność od rozdzielczości (oparcie się na „jednostkach
logicznych”=1/96 cala) – umożliwia łatwe skalowanie i dopasowanie do
rozdzielczości ekranu.
Ułożenie kontrolek: dynamiczne, oparte na zawartości (dopasowują się do swojej
zawartości oraz dostępnego miejsca).
Obiektowy model rysowania oparty na grafice wektorowej.
Wsparcie dla mediów i grafiki 3D.
Deklaratywne tworzenie animacji.
Style i szablony – pozwalają dopasowywać formatowanie i sposób renderowania
elementów interfejsu.
Deklaratywne*) tworzenie interfejsu użytkownika (XAML) – pozwala oddzielić
wygląd interfejsu od kodu.
*) Deklaratywne – czyli nie opisujemy kroków prowadzących do rozwiązania (algorytmu), a
jedynie samo rozwiązanie. Nie mówmy jak ma być coś zrobione, ale co ma być zrobione.
9/34
XAML – Extensible Application Markup Language
•
•
•
•
•
•
oparty na XMLu*) (deklaratywny) język do tworzenia interfejsu
definiuje ułożenie (oraz inne cechy) kontrolek w oknie
pozwala na podział pracy pomiędzy programistów i grafików (twórców interfejsu)
XAML nie jest obowiązkowy – to samo można zrobić w kodzie, ale wymaga to
większego nakładu pracy
można korzystać z narzędzi wizualnych do generowania plików XAML (np.
Microsoft Expression Blend)
warto znać XAMLa aby móc w pełni wykorzystywać możliwości WPFa
*) XML – uniwersalny język znaczników do strukturalnego reprezentowania danych
10/34
11/34
XML – wprowadzenie
prawidłowy plik XML
<!-- komentarz -->
znacznik otwierający
<lista>
<osoba>
Kowalski
</osoba>
<osoba imię="Piotr" nazwisko="Nowak">
<telefon numer="0123456789"/>
</osoba>
</lista>
atrybuty
znacznik pusty
znacznik zamykający
12/34
XML – wprowadzenie
nieprawidłowy plik XML
<lista>
<osoba>Nowak</Osoba>
<osoba>
<adres>
</osoba>
</adres>
</lista>
<osoba>
Kowalski
</osoba>
13/34
XAML
•
•
•
każdy znacznik odpowiada określonemu elementowi interfejsu
możliwe jest zagnieżdżanie – używane do określenia zawierania np. jednych
elementów w innych
ustawianie właściwości przez atrybuty
<Window ...
Title="Okienko" Height="200" Width="300" FontSize="14">
<Grid>
<Button Margin="30">
Nie dotykać
</Button>
</Grid>
</Window>
14/34
Element <Window> – okno aplikacji
<Window ...
Title="Okienko" Height="200" Width="300" FontSize="14">
<Grid>
<Button Margin="30">
Nie dotykać
</Button>
</Grid>
</Window>
Przykładowe atrybuty okna:
• Title – tekst na pasku tytułowym
• Height – wysokość
• Width – szerokość
• FontSize – rozmiar czcionki używanej przez wszystkie kontrolki w oknie
15/34
Układy zawartości
<Window ...
Title="Okienko" Height="200" Width="300" FontSize="14">
<Grid>
<Button Margin="30">
Nie dotykać
</Button>
</Grid>
</Window>
Okno może zawierać tylko jeden element. Aby umieścić ich więcej musimy wykorzystać
specjalny element, który posłuży za kontener dla innych kontrolek.
• jest on odpowiedzialny za ułożenie kontrolek w oknie
• dba o dopasowanie kontrolek do zawartości
• oraz do dostępnego miejsca
•
•
•
•
elementy nie powinny mieć ustalonego rozmiaru
nie powinny mieć ustalonego położenia (współrzędnych)
o te aspekty będzie dbał kontener
różne rodzaje (typy) kontenerów będą kierować się różną logiką rozmieszczania
elementów
16/34
<StackPanel>
<Window ...>
<StackPanel>
<Button>jeden</Button>
<Button>dwa</Button>
<Button>trzy</Button>
<Button>cztery</Button>
</StackPanel>
</Window>
17/34
<StackPanel>
<Window ...>
<StackPanel Orientation="Horizontal">
<Button>jeden</Button>
<Button>dwa</Button>
<Button>trzy</Button>
<Button>cztery</Button>
</StackPanel>
</Window>
18/34
Przy pomocy atrybutów możemy sterować ułożeniem kontrolek:
<Window ...>
<StackPanel Orientation="Horizontal">
<Button VerticalAlignment="Top">jeden</Button>
<Button VerticalAlignment="Center">dwa</Button>
<Button VerticalAlignment="Bottom">trzy</Button>
<Button VerticalAlignment="Stretch">cztery</Button>
</StackPanel>
</Window>
•
•
VerticalAlignment
HorizontalAlignment
19/34
Margin – dodaje odstęp od krawędzi kontenera i sąsiednich elementów:
<Window ...>
<StackPanel>
<Button HorizontalAlignment="Left" Margin="5">
jeden</Button>
<Button HorizontalAlignment="Right" Margin="5">
dwa</Button>
<Button Margin="5">trzy</Button>
<Button Margin="15, 5">cztery</Button>
<Button Margin="30, 5, 15, 0">pięć</Button>
</StackPanel>
</Window>
•
marginesy sąsiadujących
kontrolek sumują się!
20/34
Podobnie sterujemy ułożeniem zawartości wewnątrz kontrolki:
<Window ...>
<StackPanel>
<Button HorizontalContentAlignment="Left">
jeden</Button>
<Button HorizontalContentAlignment="Right">
dwa</Button>
<Button HorizontalContentAlignment="Center">
trzy</Button>
<Button>cztery</Button>
</StackPanel>
</Window>
•
•
VerticalContentAlignment
HorizontalContentAlignment
21/34
Podobnie sterujemy ułożeniem zawartości wewnątrz kontrolki:
<Window ...>
<StackPanel>
<Button HorizontalAlignment="Center">
jeden</Button>
<Button HorizontalAlignment="Center" Padding="5">
dwa</Button>
<Button HorizontalAlignment="Center" Padding="15, 5">
trzy</Button>
<Button HorizontalAlignment="Center"
Padding="30, 0, 15, 5">cztery</Button>
</StackPanel>
</Window>
•
Padding steruje odstępem
od zawartości kontrolki
22/34
<WrapPanel>
<Window ...>
<WrapPanel>
<Button Margin="5">jeden</Button>
<Button Margin="5">dwa</Button>
<Button Margin="5">trzy</Button>
<Button Margin="5">cztery</Button>
<Button Margin="5">pięć</Button>
<Button Margin="5">sześć</Button>
</WrapPanel>
</Window>
23/34
<DockPanel>
„dołączone
właściwości”
<Window ...>
<DockPanel>
<Button DockPanel.Dock="Top">jeden</Button>
<Button DockPanel.Dock="Left">dwa</Button>
<Button DockPanel.Dock="Right">trzy</Button>
<Button DockPanel.Dock="Bottom">cztery</Button>
<Button DockPanel.Dock="Top">pięć</Button>
<Button DockPanel.Dock="Right">sześć</Button>
<Button>siedem</Button>
</DockPanel>
</Window>
•
kolejność elementów
ma znaczenie!
24/34
<Grid>
<Window ...>
<Grid ShowGridLines="True">
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
<ColumnDefinition/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
...
...
...
</Grid>
</Window>
•
•
tylko do
testu
elementy umieszczamy
w polach siatki
krok pierwszy –
zdefiniowanie siatki
25/34
<Grid>
<Window ...>
<Grid>
<Grid.RowDefinitions>...</Grid.RowDefinitions>
<Grid.ColumnDefinitions>...</Grid.ColumnDefinitions>
<Button>jeden</Button>
<Button Grid.Row="1">dwa</Button>
<Button Grid.Column="2">trzy</Button>
<Button Grid.Row="1" Grid.Column="1">cztery</Button>
</Grid>
</Window>
•
krok drugi –
rozmieszczenie elementów
26/34
<Grid>
<Window ...>
<Grid>
<Grid.RowDefinitions>...</Grid.RowDefinitions>
<Grid.ColumnDefinitions>...</Grid.ColumnDefinitions>
<Button Grid.ColumnSpan="2">jeden</Button>
<Button Grid.Row="1">dwa</Button>
<Button Grid.Column="2" Grid.RowSpan="2">trzy</Button>
<Button Grid.Row="1" Grid.Column="1">cztery</Button>
</Grid>
</Window>
•
element może rozciągać się
na więcej niż jedno pole siatki
27/34
<Grid>
<Window ...>
<Grid>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto"/>
<ColumnDefinition Width="*"/>
<ColumnDefinition Width="70"/>
</Grid.ColumnDefinitions>
...
...
</Grid>
</Window>
•
•
Width dla kolumn
Height dla wierszy
28/34
Kontenery można dowolnie zagnieżdżać:
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto"/>
<ColumnDefinition Width="auto"/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<StackPanel> ... </StackPanel>
<StackPanel Grid.Column="1" Orientation="Horizontal">
...
</StackPanel>
<WrapPanel Grid.Column="2">
...
</WrapPanel>
</Grid>
29/34
A jak zaprojektujemy nasze okienko?
<Window ...
Title="Obliczenia" Height="200" Width="300"
FontSize="14">
...
</Window>
30/34
<Window ...>
<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
<RowDefinition Height="auto"/>
</Grid.RowDefinitions>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="auto"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
</Grid>
</Window>
•
•
•
•
cztery wiersze, dwie kolumny
wysokość wierszy dopasowuje się
do zawartości
szerokość pierwszej kolumny
dopasowuje się do zawartości
szerokość kolumny z polem
tekstowym – rozciągnięta
31/34
<Window ...>
<Grid>
<Grid.RowDefinitions>...</Grid.RowDefinitions>
<Grid.ColumnDefinitions>...</Grid.ColumnDefinitions>
<Label Margin="5">Pierwsza liczba:</Label>
<Label Margin="5" Grid.Row="1">Druga liczba:</Label>
<Label Margin="5" Grid.Row="2">Wynik:</Label>
<TextBox Margin="5" Grid.Column="1"/>
<TextBox Margin="5" Grid.Row="1" Grid.Column="1"/>
<TextBox Margin="5" Grid.Row="2" Grid.Column="1"
IsReadOnly="True"/>
<Button Grid.Row="3" Grid.ColumnSpan="2" Margin="5"
Padding="10,3" HorizontalAlignment="Right">
Oblicz</Button>
</Grid>
</Window>
•
•
•
Label – etykieta
TextBox – pole tekstowe
◦ IsReadOnly – tylko do odczytu
przycisk zajmuje cały wiersz
32/34
Jak dodać obsługę zdarzeń?
również przy pomocy atrybutów:
•
<Button Click="Oblicz" ...>Oblicz</Button>
// zawartość pliku Window1.xaml.cs:
namespace WpfApplication1
{
public partial class Window1 : Window
{
public Window1()
{
InitializeComponent();
}
private void Oblicz(object sender, RoutedEventArgs e)
{
}
}
}
Ta funkcja zostanie
wywołana, gdy użytkownik
naciśnie przycisk „Oblicz”
33/34
Jak odczytać dane z okna w kodzie programu?
•
najpierw musimy nazwać elementy, do których chcemy mieć dostęp:
<TextBox Name="pierwsze" .../>
<TextBox Name="drugie" .../>
<TextBox Name="wynik" ... IsReadOnly="True"/>
•
następnie w pliku *.cs:
private void Oblicz(object sender, RoutedEventArgs e)
{
int a = int.Parse(pierwsze.Text);
int b = int.Parse(drugie.Text);
int c = a + b;
wynik.Text = c.ToString();
}
•
•
•
pierwsze.Text – zawartość pola tekstowego
int.Parse(...) – konwersja tekstu na liczbę
c.ToString() – konwersja zmiennej na tekst
34/34

Podobne dokumenty