
- •1. Вводная часть
- •2. Знакомство со средой разработки на примере создания простого консольного приложения
- •3. Модификация консольного приложения
- •4. Публикация
- •5. О приложении к Лабораторной работе № 1
- •Лабораторная работа № 2: Создание простого приложения Windows Forms
- •Создание простого приложения Windows Forms
- •Модификация приложения Windows Forms
- •Завершающая часть
- •2. Создание простого приложения Windows Forms
- •3. Модификация приложения Windows Forms
- •4. Завершающая часть
- •5. О приложении к Лабораторной работе № 2
- •3. Лабораторная работа № 3: Windows Forms и использование некоторых элементов управления Лабораторная работа № 3: Windows Forms и использование некоторых элементов управления
- •Вводная часть
- •О приложении к Лабораторной работе № 3
- •1. Вводная часть
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms
- •4. Модификация приложения Windows Forms: элемент управления MenuStrip
- •5. Модификация приложения Windows Forms: элемент управления Button
- •6. Модификация приложения Windows Forms: элемент управления ToolTip
- •7. Модификация приложения Windows Forms: элемент управления ComboBox
- •8. Модификация приложения Windows Forms: элемент управления WebBrowser
- •9. Модификация приложения Windows Forms: добавляем исходный код
- •10. Завершающая часть
- •11. О приложение к Лабораторной работе № 3
- •4. Лабораторная работа № 4: Windows Forms — работа с формами Лабораторная работа № 4: Windows Forms — работа с формами
- •Вводная часть
- •О приложении к Лабораторной работе № 4
- •1. Вводная часть
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms
- •4. Модификация приложения Windows Forms: добавление новой формы
- •5. Модификация приложения Windows Forms: динамическое связывание параметров двух форм и передача параметра через прямой доступ к элементу формы
- •6. Модификация приложения Windows Forms: динамическое связывание параметров двух форм и передача параметра через передачу метода в конструктор формы
- •7. Модификация приложения Windows Forms: динамическое связывание параметров двух форм и передача параметра через класс делегата
- •8. Модификация приложения Windows Forms: динамическое связывание параметров двух форм и передача параметра через свойства
- •9. Завершающая часть
- •10. О приложении к Лабораторной работе № 4
- •5. Лабораторная работа № 5: Windows Forms — элементы управления Лабораторная работа № 5: Windows Forms — элементы управления
- •Вводная часть
- •О приложении к Лабораторной работе № 5
- •1. Вводная часть
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms
- •4. Модификация приложения Windows Forms: динамическое добавление и уничтожение элемента управления
- •5. Модификация приложения Windows Forms: стандартные диалоговые окна
- •6. Модификация приложения Windows Forms: открытие файла, сохранение файла и работа с текстом
- •7. Модификация приложения Windows Forms: прочее
- •8. Завершающая часть
- •9. О приложении к Лабораторной работе № 5
- •Лабораторная работа № 6: SolidWorks — работа с SolidWorks
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: eDrawings 2012
- •4. Модификация приложения Windows Forms: организация работы с SolidWorks через приложение
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 6
- •Лабораторная работа № 7: SolidWorks — использование SwCSharpAddin, работа с макросом и шаблоном детали
- •2. Создание приложения SwCSharpAddin
- •3. Модификация приложения SwCSharpAddin: макрос отрисовки болта
- •4. Модификация приложения SwCSharpAddin: построение через шаблон детали
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 7
- •8. Лабораторная работа № 8: Создание простого приложения Windows Foundation Presentation Лабораторная работа № 8: Создание простого приложения Windows Foundation Presentation
- •Вводная часть
- •О приложении к Лабораторной работе № 8
- •1. Вводная часть
- •2. Создание приложения Windows Foundation Presentation
- •3. Модификация приложения Windows Foundation Presentation
- •4. Модификация приложения Windows Foundation Presentation: добавление нового элемента из библиотеки компонентов wpf
- •5. Модификация приложения Windows Forms: расширение функциональности приложения и работа с оформление
- •6. Модификация приложения Windows Foundation Presentation: различные возможности wpf
- •7. Модификация приложения Windows Foundation Presentation: немного о стилях и шаблонах
- •8. Завершающая часть
- •9. О приложении к Лабораторной работе № 8
- •Лабораторная работа № 9: Создание приложения-презентации Windows Foundation Presentation
- •2. Создание приложения Windows Foundation Presentation
- •3. Модификация приложения Windows Foundation Presentation
- •4. Модификация приложения Windows Foundation Presentation: работа с решением в Expression Blend
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 9
- •Лабораторная работа № 10: Работа с базами данных — xml и ole
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: odbc
- •4. Модификация приложения Windows Forms: ole
- •5. Модификация приложения Windows Forms: xml
- •6. Завершающая часть
- •7. О приложении к Лабораторной работе № 10
- •Лабораторная работа № 11: Динамическая связь приложений через библиотеку классов
- •2. Удалённый объект: создание библиотеки классов удалённого объекта
- •3. Клиент: создание приложения Windows Forms
- •4. Сервер: создание консольного приложения
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 11
- •Лабораторная работа № 12: Автоматизация Microsoft Office Word
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: создание и заполнение нового документа Microsoft Word
- •4. Модификация приложения Windows Forms: работа с шаблонами
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 12
- •Лабораторная работа № 13: Автоматизация Microsoft Office Excel
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: создание и заполнение нового документа Microsoft Excel
- •4. Модификация приложения Windows Forms: чтение данных с документа Microsoft Excel
- •5. Модификация приложения Windows Forms: прочие возможности Microsoft Excel
- •6. Завершающая часть
- •7. О приложении к Лабораторной работе № 13
- •Лабораторная работа № 14: Простой растровый редактор
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: подготовка интерфейса редактора
- •4. Модификация приложения Windows Forms: функциональность растрового редактора
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 14
- •15. Лабораторная работа № 15: Векторный редактор изображений Лабораторная работа № 15: Векторный редактор изображений
- •Вводная часть
- •О приложении к Лабораторной работе № 15
- •1. Вводная часть
- •2. Создание решения, приложения Windows Forms и библиотеки классов
- •3. Модификация приложения Windows Forms: подготовка интерфейса редактора и добавление файлов ресурсов
- •4. О будущей функциональности векторного редактора изображений
- •5. Модификация приложения Windows Forms: подготовка библиотеки классов
- •6. Модификация приложения Windows Forms: функциональность векторного редактора
- •7. Завершающая часть
- •8. О приложении к Лабораторной работе № 15
- •Лабораторная работа № 16: Windows Communication Foundation
- •2. Создание приложения wcf:
- •3. Модификация приложения wcf: приложение-клиент для wcf-службы
- •4. Создание приложения Windows Forms: сервер чата на wcf
- •5. Создание приложения Windows Forms: клиент чата на wcf
- •6. Завершающая часть
- •7. О приложении к Лабораторной работе № 16
- •Лабораторная работа № 17: Знакомство с Silverlight
- •2. Создание приложения Silverlight:
- •3. Модификация приложения Silverlight: первые шаги и полноэкранный режим
- •4. Модификация приложения Silverlight: простой проигрыватель mp3-файлов
- •5. Модификация приложения Silverlight: работа с анимацией
- •6. Завершающая часть
- •7. О приложении к Лабораторной работе № 17
- •Лабораторная работа № 18: Знакомство с asp.Net
- •2. Создание веб-приложения asp.Net
- •3. Модификация веб-приложения asp.Net: реализация различной функциональности
- •4. Модификация веб-приложения asp.Net: ajax
- •5. Завершающая часть
- •6. О приложении к Лабораторной работе № 18
- •Вводная часть
- •О приложении к Лабораторной работе № 19
- •1. Вводная часть
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: подготовка интерфейса и добавление TabControl
- •4. Модификация приложения Windows Forms: вкладка «Просто фон!»
- •5. Модификация приложения Windows Forms: вкладка «Объекты и градиент»
- •6. Модификация приложения Windows Forms: вкладка «Мой монитор сломался!»
- •7. Модификация приложения Windows Forms: вкладка «Векторные часы»
- •8. Модификация приложения Windows Forms: вкладка «Огонь!!!»
- •9. Модификация приложения Windows Forms: вкладка «Дождик»
- •10. Завершающая часть
- •11. О приложении к Лабораторной работе № 19
- •Лабораторная работа № 20: Inventor — работа с Inventor
- •Вводная часть
- •О приложении к Лабораторной работе № 20
- •1. Вводная часть
- •2. Создание приложения Windows Forms
- •3. Модификация приложения Windows Forms: запуск и завершение приложения Inventor
- •4. Модификация приложения Windows Forms: создание новых документов
- •5. Модификация приложения Windows Forms: доступ к элементам документов Inventor
- •6. Завершающая часть
- •7. О приложении к Лабораторной работе № 20
- •Лабораторная работа № 21: Знакомство с языком f# (Эф-шарп) на примере простого приложения для командной строки
- •Вводная часть
- •О приложении к Лабораторной работе № 21
- •1. Вводная часть
- •2. Основные положения при работе с f#
- •3. Создание приложения «Учебник по f#»
- •4. Создание консольного приложения
- •5. О приложении к Лабораторной работе № 21
- •Лабораторная работа № 22: Различные примеры на f#
- •2. Создание приложения «Приложение f#»
- •3. Модификация приложения f#: match
- •4. Модификация приложения f#: создание форм и рисование объектов на форме
- •5. Модификация приложения f#: работа с базой данных Microsoft Access
- •6. О приложении к Лабораторной работе № 22
- •23. Дополнительная лабораторная работа № 1
- •24. Дополнительная лабораторная работа № 2
- •25. Дополнительная лабораторная работа № 3
- •Вводная часть
- •1. Вводная часть
- •2. Создание приложения Windows Foundation Presentation
- •3. Модификация приложения Windows Foundation Presentation: добавление ресурсов
- •4. Модификация приложения Windows Foundation Presentation: добавление исходного кода
- •5. Модификация приложения Windows Foundation Presentation: оформление элемента ListBox
- •6. Завершающая часть
- •7. О приложении к данной работе
7. Модификация приложения Windows Foundation Presentation: немного о стилях и шаблонах
В WPF существует две принципиальные концепции для разработки своих собственных элементов управления и уникального оформления. Это понятия шаблона и стиля.
Стили позволяют разработчику WPF вести общий список значений свойств в удобном месте. До некоторой степени они напоминают таблицы CSS в веб-разработке. Как правило, стили находятся в разделе ресурсов или в отдельном словаре ресурсов. Благодаря стилям в платформе WPF реализуются элементы управления с поддержкой темы.
Элемент Style обладает следующими свойствами:
BasedOn |
Возвращает или задает определенный стиль, являющийся основой текущего стиля |
Dispatcher |
Возвращает объект Dispatcher, с которым связан этот объект DispatcherObject (наследуемый от DispatcherObject) |
IsSealed |
Возвращает значение, указывающее, доступен ли стиль только для чтения |
Resources |
Возвращает или задает коллекцию ресурсов, которые могут использоваться в области видимости данного стиля |
TargetType |
Возвращает или задает тип, для которого предназначен данный стиль |
Setters |
Возвращает коллекцию объектов Setter и EventSetter |
Triggers |
Возвращает коллекцию объектов TriggerBase, применяющих значения свойств на основе заданных условий |
Из этих свойств самые важные следующие:
BasedOn («наследование» стиля, каждый стиль поддерживает только одно значение).
<Style x:Key="Style1">
...
</Style>
<Style x:Key="Style2" BasedOn="{StaticResource Style1}">
...
</Style>
TargetType (ограничивает типы элементов управления, которые могут использовать данный стиль).
Например, если свойству TargetType объекта Style присвоено значение Button, этот стиль нельзя использовать для элемента управления типа TextBox. Задать свойство TargetType следует так:
<Style TargetType="{x:Type Button}">
...
</Style>
Setters (задают событию или свойству некоторое значение; при задании события они подключают это событие; при задании свойства они присваивают свойству значение).
Объекты EventSetter используются для задания событий, например для связывания события Click элемента Button, как в примере ниже. Однако значительно чаще объекты Setter используются просто для задания значений свойствам (второй участок кода):
<Style TargetType="{x:Type Button}">
<EventSetter Event="Click" Handler="b1SetColor"/>
</Style>
<Style TargetType="{x:Type Button}">
<Setter Property="BackGround" Value="Yellow"/>
</Style>
Triggers (по сути, объекты Trigger позволяют применять изменения при выполнении определенных условий (например, когда значение некоторого свойства становится равным true или когда происходит некоторое событие).
В примере показан именованный стиль, доступный для элементов управления Button. В стиле определен элемент Trigger, который изменяет свойство Foreground элемента Button, когда свойство IsPressed равно true:
<Style x:Key="Triggers" TargetType="Button">
<Style.Triggers>
<Trigger Property="IsPressed" Value="true">
<Setter Property = "Foreground" Value="Green"/>
</Trigger>
</Style.Triggers>
</Style>
Напишем же небольшое приложение, демонстрирующее шаблоны и стили и добавим его в текущее приложение. Вызов окна с новой функциональностью будем производить по кнопке. Окно сделаем немодальным. Разместим кнопку Изменённые кнопки (button8) где-нибудь на свободном участке приложения. Добавим новое окно (Window) и зададим ему имя ButtonStylesWindow.xaml. XAML-код нового окна сделаем таким:
<Window x:Class="LWP08WPF01.ButtonStylesWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:LWP08WPF01"
Title="Приложение WPF (C#) :: Изменённые кнопки" SizeToContent="WidthAndHeight" Name="lol">
<Window.Resources>
<Style TargetType="Button" x:Key="BaseButtonStyle">
<Setter Property="HorizontalAlignment" Value="Center" />
<Setter Property="VerticalAlignment" Value="Center" />
<Setter Property="Margin" Value="10" />
</Style>
<Style TargetType="Button" x:Key="BigButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Width" Value="170" />
<Setter Property="Height" Value="50" />
<Setter Property="FontSize" Value="16" />
</Style>
<Style TargetType="Button" x:Key="SmallButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Width" Value="150" />
<Setter Property="Height" Value="25" />
<Setter Property="FontSize" Value="12" />
</Style>
<Style TargetType="Button" x:Key="RedButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Foreground" Value="Red" />
</Style>
<Style TargetType="Button" x:Key="GreenButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Foreground" Value="Green" />
</Style>
<Style TargetType="Button" x:Key="BoldButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="FontWeight" Value="Bold" />
</Style>
</Window.Resources>
<Grid Margin="30">
<Grid.ColumnDefinitions>
<ColumnDefinition />
<ColumnDefinition />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<Button Style="{local:MultiStyle BigButtonStyle GreenButtonStyle}" Content="Большая, зелёная"/>
<Button Style="{local:MultiStyle BigButtonStyle RedButtonStyle}" Content="Большая, красная" Grid.Column="1"/>
<Button Style="{local:MultiStyle SmallButtonStyle GreenButtonStyle}" Content="Мальная, зелёная" Grid.Row="1"/>
<Button Style="{local:MultiStyle SmallButtonStyle RedButtonStyle}" Content="Маленькая, красная" Grid.Row="1" Grid.Column="1"/>
<Button Style="{local:MultiStyle BigButtonStyle GreenButtonStyle BoldButtonStyle}" Content="Б., зелёная, жирная" Grid.Row="2"/>
<Button Style="{local:MultiStyle BigButtonStyle RedButtonStyle BoldButtonStyle}" Content="Б., красная, жирная" Grid.Row="2" Grid.Column="1"/>
<Button Style="{local:MultiStyle SmallButtonStyle GreenButtonStyle BoldButtonStyle}" Content="М., зелёная, жирная" Grid.Row="3" />
<Button Style="{local:MultiStyle SmallButtonStyle RedButtonStyle BoldButtonStyle}" Content="М., красная, жирная" Grid.Row="3" Grid.Column="1"/>
</Grid>
</Window>
Добавим два следующих файла с кодом (добавляем как Код -> Класс). Имя первого файла: ButtonStylesExtension.cs (расширение стилей кнопок). Содержимое файла делаем таким (комментарии включены):
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Markup;
using System.Windows;
namespace LWP08WPF01
{
[MarkupExtensionReturnType(typeof(Style))] // Сообщаем что класс Style может возвращать расширение разметки (typeof используется для получение объекта типа, является альтернативой создания экземпляра класса new и получение типа методом GetType() )
public class MultiStyleExtension : MarkupExtension // Создаём класс как базовый класс для расширенной разметки XAML
{
private string[] resourceKeys;
/// <summary>
/// Публичный конструктор.
/// </summary>
/// <param name="inputResourceKeys">Конструктор ввода должен быть строкой, состоящей из одного или нескольких имен стилей, разделенных пробелами.</param>
public MultiStyleExtension(string inputResourceKeys) // получаем входящий ключ на ресурс
{
if (inputResourceKeys == null) // Если ничего не получаем, генерируем (throw) новое (new) исключение ArgumentNullException (пустой аргумент) для ключа
{
throw new ArgumentNullException("inputResourceKeys");
}
this.resourceKeys = inputResourceKeys.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); // Выполняем слияние строк для ключа, удаляя лишни символы пробелов
if (this.resourceKeys.Length == 0) // Если не вышло изначально (0) или мы убили ключ для ресурса, генерируем новое исключение об отсутсвиии ключа
{
throw new ArgumentException("Нет указанных входных ключей ресурсов.");
}
}
/// <summary>
/// Возвращает стиль, который объединяет все стили с ключами, указанными в конструкторе.
/// </summary>
/// <param name="serviceProvider">Поставщиков услуг для данного расширения разметки.</param>
/// <returns>Стиль, который объединяет все стили с ключами, указанными в конструкторе.</returns>
public override object ProvideValue(IServiceProvider serviceProvider)
{
Style resultStyle = new Style(); // Создаём объект класса Style
try
{
foreach (string currentResourceKey in resourceKeys) // Пробегаем в цикле по всем ключам ресорусов (foreach повторяет группу вложенных операторов для каждого элемента массива или коллекции объектов)
{
Style currentStyle = new StaticResourceExtension(currentResourceKey).ProvideValue(serviceProvider) as Style; // Передаём через конструктор исходный ключ конкретного текущего стиля
if (currentStyle == null) // Проверям что стиль есть, если нет, то выполняем вывод ошибки (генерируем новое исключение)
{
throw new InvalidOperationException("Не удалось найти стиль для ключа ресурса: " + currentResourceKey + ".");
}
resultStyle.Merge(currentStyle); // Выполняем слияние для текущего стиля (смотрим файл StyleExtensionMethods.cs)
}
}
catch
{
// Ловим ошибку: IXamlSchemaContextProvider
}
return resultStyle; // Возвращаем готовый стиль
}
}
}
Второй файл (StyleExtensionMethods.cs) будет содержать нужный нам метод Merge():
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
namespace LWP08WPF01
{
public static class StyleExtensionMethods
{
/// <summary>
/// Слияние двух стилей передается в качестве параметров. Первый стиль будет изменен, чтобы получить всю информацию, присутствующую во втором.
/// Если имеет место совпадение стилей, второй стиль имеет больший приоритет.
/// </summary>
/// <param name="style1">Первый стиль для слияния, который будет изменен, чтобы получить информацию из второго.</param>
/// <param name="style2">Второй стиль для слияния, который передают информацию для первого стиля.</param>
public static void Merge(this Style style1, Style style2)
{
if (style1 == null) { throw new ArgumentNullException("style1"); }
if (style2 == null) { throw new ArgumentNullException("style2"); }
if (style1.TargetType.IsAssignableFrom(style2.TargetType)) // проверка типов, если совпадают "сливаем" TargetType стиля
{
style1.TargetType = style2.TargetType;
}
if (style2.BasedOn != null) // Если базовый стиль второго стиля не нуль
{
Merge(style1, style2.BasedOn); // Сливаем базовый стиль style2.VaseOn в style1
}
foreach (SetterBase currentSetter in style2.Setters) // Пробегаем по все объектам типа Setter второго стиля и записываем каждый найденный в первый стиль
{
style1.Setters.Add(currentSetter);
}
foreach (TriggerBase currentTrigger in style2.Triggers) // Пробегаем по всем объектам типа Trigger
{
style1.Triggers.Add(currentTrigger);
}
// Этот код нужен только при использовании DynamicResources
foreach (object key in style2.Resources.Keys)
{
style1.Resources[key] = style2.Resources[key];
}
}
}
}
Конструктор сформирует представление окна:
Рис. 7. 1. Конструктор окна ButtonStylesWindow.xaml
Выделим
мышкой любую кнопку в конке и посмотрим
на свойства. Ищем поле Общее:
Style,
нажимаем на значок «ромбика» (
).
Жмём на него, далее Применить
ресурс…,
увидим следующее:
Откроется список всех доступных стилей для этой кнопки. Выбор конкретного стиля осуществляется например для кнокпи Большая, зелёная так. Объявляем базовый стиль от кнопки Button, даём ему имя BaseButtonStyle:
<Style TargetType="Button" x:Key="BaseButtonStyle">
<Setter Property="HorizontalAlignment" Value="Center" />
<Setter Property="VerticalAlignment" Value="Center" />
<Setter Property="Margin" Value="10" />
</Style>
Далее создаём на основе кнопки базового стиль стиль «большой» кнопки и даём стилю имя BigButtonStyle:
<Style TargetType="Button" x:Key="BigButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Width" Value="170" />
<Setter Property="Height" Value="50" />
<Setter Property="FontSize" Value="16" />
</Style>
Теперь создаём стиль зелёной кнопки:
<Style TargetType="Button" x:Key="GreenButtonStyle" BasedOn="{StaticResource BaseButtonStyle}">
<Setter Property="Foreground" Value="Green" />
</Style>
И применяем всё это к макету кнопки всталенной на форму:
<Button Style="{local:MultiStyle BigButtonStyle GreenButtonStyle}" Content="Большая, зелёная"/>
Как видим, такую кнопку можно создать и без всех этих стилей, просто задав необходимые свойства. Однако шаблонизация стилей хороша когда меняется не один два параметра для элемента, а ОЧЕНЬ много и кардинально. И на настройку каждой кнопки просто уйдёт много времени, тогда как можно воспользоваться заранее приготовленным шаблоном.
Обработчик кнопки вызова последнего окна такой:
private void button8_Click(object sender, RoutedEventArgs e)
{
ButtonStylesWindow Window = new ButtonStylesWindow();
Window.Show();
}