Podpora tisku je zabezpečená třídou PrintDocument ze jmenného prostoru System.Windows.Printing. Tato třída nám umožňuje jak tisk celé aplikace, tak tisk jednotlivých částí aplikace. Kromě toho můžeme tisknout komponenty, které nejsou součástí vizuálního stromu.
Při vyvolání tisku se uživateli zobrazí standardní dialogové okno pro tisk.
Třída PrintDocument nabízí tři události, které jsou vyvolány v průběhu tiskové operace.
Události jsou:
Událost BeginPrint můžeme použít na přípravu dokumentu k tisku a k jiným úkonům, které se provedou před samotným tiskem.
Pomocí události PrintPage nastavíme komponentu, která se má tisknout. To se nastavuje přes vlastnost PageVisual z parametru PrintPageEventArgs. PageVisual je typu UIElement. Můžeme tisknout jak celou aplikaci, tak i její část. Pokud chceme tisknout celou aplikaci, pak jako PageVisual nastavíme kořenový prvek aplikace (LayoutRoot).
Událost EndPrint signalizuje konec tisku a zde můžeme podniknout úkony vztahující se k ukončení tisku. Můžeme například informovat uživatele, že tisk byl úspěšně dokončen. Popřípadě můžeme obsloužit chyby, které při tisku mohly nastat.
K otevření dialogu se používá metoda Print(string documentName), jako parametr je předáno jméno tisknutého dokumentu. Metoda Print musí být vyvolána akcí uživatele, aby nedošlo k vyvolání vyjímky(Security Exception).
Jednoduše můžeme tisk popsat jako posloupnost následujících kroků:
Pokud chceme tisknout více stran, pak je nutné nastavit vlastnost HasMorePages z PrintPageEventArgs na hodnotu true. Je ale nutné, aby si programátor tisk jednotlivých stran obsloužil sám. Současná třída PrintDocument je koncipována na tisk jedné strany a tisk více stran není až tak jednoduchý úkol. Více informací, jak se s tiskem více stran vypořádat, najdete na adrese http://bit.ly/degIFU .
V aplikaci budu mít objekt, který jsem si nakreslil v rámci nástroje Expression Design. Tento objekt je popsán pomocí jazyka XAML. Dále zde budu mít dvě tlačítka, která budou provádět samotný tisk. První tlačítko vytiskne celý obsah aplikace, zatímco druhé pouze daný objekt.
Jelikož XAML kód není v této aplikaci podstatný, ukážeme si pouze aplikační logiku. Každé ze dvou tlačítek implementuje událost kliknutí (Click). Podívejme se, jak by tisk vypadal v případě tisku celé aplikace.
V rámci metody, která reaguje na událost kliknutí, přidáme následující kód:
private void Button_Click(object sender, RoutedEventArgs e)
{
//1. Vytvoříme instanci třídy PrintDocument
PrintDocument doc = new PrintDocument();
//vyvolána před samotným tiskem
doc.BeginPrint += (s, args) =>
{
//TODO volitelné nastavení před samotným tiskem
};
//vyvolána po tisku
doc.EndPrint += (s, args) =>
{
//TODO volitelné nastavení po samotném tisku
};
//2. událost je vyvolána pro každou tisknutou stránku aplikace
doc.PrintPage += (s, args) =>
{
//nastavení obsahu tisku, v tomto případě celá aplikace
args.PageVisual = LayoutRoot;
};
//3. Zobraz uživateli dialog pro tisk
doc.Print("Celá aplikace");
}
Jako tisknutý prvek jsme nastavili celou aplikaci. To znamená, že jsme vlastnosti PageVisual přiřadili kořenový element aplikace. V našem případě je to komponenta Grid se jménem LayoutRoot.
Nyní požadujeme tisk jednoho objektu. My si vybereme objekt, který jsem si před tím připravil v Expression Designu. Tento objekt je pojmenován jako “moucha”. Proto do vlastnosti PageVisual bude předáno jméno objektu “moucha”. Kód aplikace je totožný s předešlým příkladem až na vlastnost PageVisual.
private void button1_Click(object sender, RoutedEventArgs e)
{
//1. Vytvoříme instanci třídy PrintDocument
PrintDocument doc = new PrintDocument();
//vyvolána před samotným tiskem
doc.BeginPrint += (s, args) =>
{
//TODO volitelné nastavení před samotným tiskem
};
//vyvolána po tisku
doc.EndPrint += (s, args) =>
{
//TODO volitelné nastavení po samotném tisku
};
//2. událost je vyvolána pro každou tisknutou stránku aplikace
doc.PrintPage += (s, args) =>
{
//nastavení obsahu tisku, v tomto případě objekt moucha
args.PageVisual = moucha;
};
//3. Zobraz u6ivateli dialog pro tisk
doc.Print("Moucha");
}
Pro kontrolu tisku doporučuji tisk do XPS Microsoft Document Writeru.
Občas můžeme chtít, aby tisknutý objekt zabíral celou tisknutelnou oblast. To se dá udělat tak, že tisknutelnému elementu nastavíme výšku a šířku podle vlastnosti PrintableArea z parametru PrintPageEventArgs. Poté můžeme vrátit objekt na původní hodnoty například v rámci události EndPrint. Více informací o této možnosti najdete na adrese http://bit.ly/a3oQpe , kde je to aplikováno na grafech z balíku Silverlight Toolkit.
Podpora tisku je sice dobrá, ale ne zrovna nejlepší. V případě tisku dat např. z Gridu (několik stovek řádků na několika stránkách) bude velikost výsledného dokumentu hodně velká.
Působí jako Microsoft Student Partner a pracuje jako vývojář v jedné nadnárodní firmě. Zajímá se o webové technologie a počítačovou grafiku. Pozornost také věnuje hernímu průmyslu
email: davidb@devedu.cz
web: www.aglight.cz