Browse Source

some formatting code and add units docs

anschek 5 months ago
parent
commit
7a623ae0aa
36 changed files with 1371 additions and 92 deletions
  1. BIN
      EducationDepartment/.vs/EducationDepartment/DesignTimeBuild/.dtbcache.v2
  2. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/093e9d44-fb8d-49b4-b621-bbc90ef668e6.vsidx
  3. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/599ee1db-6dfd-4b9a-8f1a-67bb5396aca7.vsidx
  4. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/75628d7c-dc74-4be9-b52e-1ac1d3dcfe17.vsidx
  5. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/8ecacaed-7631-4322-b8ce-6b9e852cd6cd.vsidx
  6. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/943e9527-62c2-49dc-9eee-04edbf31aa47.vsidx
  7. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/9ce24ffa-3c0a-4229-8e2c-13fb0dcb2a34.vsidx
  8. BIN
      EducationDepartment/.vs/EducationDepartment/FileContentIndex/b667884e-6437-4583-9997-43a23cad17e1.vsidx
  9. BIN
      EducationDepartment/.vs/EducationDepartment/v17/.futdcache.v2
  10. BIN
      EducationDepartment/.vs/EducationDepartment/v17/.suo
  11. BIN
      EducationDepartment/.vs/ProjectEvaluation/educationdepartment.metadata.v7.bin
  12. BIN
      EducationDepartment/.vs/ProjectEvaluation/educationdepartment.projects.v7.bin
  13. BIN
      EducationDepartment/EducationDepartment.test/obj/Debug/net7.0/EducationDepartment.test.csproj.AssemblyReference.cache
  14. 0 6
      EducationDepartment/EducationDepartment/Models/Student.cs
  15. 1 14
      EducationDepartment/EducationDepartment/Models/User.cs
  16. 0 1
      EducationDepartment/EducationDepartment/ViewModels/AttendanceViewModel.cs
  17. 1 5
      EducationDepartment/EducationDepartment/ViewModels/EvaluationStudentViewModel.cs
  18. 6 17
      EducationDepartment/EducationDepartment/ViewModels/MainWindowViewModel.cs
  19. 0 8
      EducationDepartment/EducationDepartment/Views/Attendance.axaml
  20. 0 3
      EducationDepartment/EducationDepartment/Views/AuthorizationPage.axaml
  21. 0 19
      EducationDepartment/EducationDepartment/Views/MainWindow.axaml
  22. 1 16
      EducationDepartment/EducationDepartment/Views/Menu.axaml
  23. 3 2
      EducationDepartment/EducationDepartment/bin/Debug/net7.0/1.csv
  24. BIN
      EducationDepartment/EducationDepartment/bin/Debug/net7.0/EducationDepartment.dll
  25. BIN
      EducationDepartment/EducationDepartment/bin/Debug/net7.0/EducationDepartment.pdb
  26. 4 0
      EducationDepartment/EducationDepartment/bin/Debug/net7.0/marks.csv
  27. 1 1
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/Resources.Inputs.cache
  28. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.dll
  29. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.pdb
  30. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.ref.dll
  31. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/resources
  32. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/EducationDepartment.dll
  33. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/EducationDepartment.pdb
  34. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/ref/EducationDepartment.dll
  35. BIN
      EducationDepartment/EducationDepartment/obj/Debug/net7.0/refint/EducationDepartment.dll
  36. 1354 0
      модули.docx

BIN
EducationDepartment/.vs/EducationDepartment/DesignTimeBuild/.dtbcache.v2


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/0ed5241f-6ee2-479f-89ba-2b3068cc18bf.vsidx → EducationDepartment/.vs/EducationDepartment/FileContentIndex/093e9d44-fb8d-49b4-b621-bbc90ef668e6.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/599ee1db-6dfd-4b9a-8f1a-67bb5396aca7.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/21812adf-042c-4d68-919c-36cbbc982282.vsidx → EducationDepartment/.vs/EducationDepartment/FileContentIndex/75628d7c-dc74-4be9-b52e-1ac1d3dcfe17.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/2b2e77e0-69dc-4650-a91f-e7e2c705743d.vsidx → EducationDepartment/.vs/EducationDepartment/FileContentIndex/8ecacaed-7631-4322-b8ce-6b9e852cd6cd.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/943e9527-62c2-49dc-9eee-04edbf31aa47.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/9ce24ffa-3c0a-4229-8e2c-13fb0dcb2a34.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/FileContentIndex/b667884e-6437-4583-9997-43a23cad17e1.vsidx


BIN
EducationDepartment/.vs/EducationDepartment/v17/.futdcache.v2


BIN
EducationDepartment/.vs/EducationDepartment/v17/.suo


BIN
EducationDepartment/.vs/ProjectEvaluation/educationdepartment.metadata.v7.bin


BIN
EducationDepartment/.vs/ProjectEvaluation/educationdepartment.projects.v7.bin


BIN
EducationDepartment/EducationDepartment.test/obj/Debug/net7.0/EducationDepartment.test.csproj.AssemblyReference.cache


+ 0 - 6
EducationDepartment/EducationDepartment/Models/Student.cs

@@ -6,16 +6,10 @@ namespace EducationDepartment.Models;
 
 public partial class Student
 {
-    [Ignore]
     public int UserId { get; set; }
-    [Ignore]
     public int GroupId { get; set; }
-    [Ignore]
     public virtual ICollection<Attendance> Attendances { get; set; } = new List<Attendance>();
-
     public virtual Group Group { get; set; } = null!;
-    [Ignore]
     public virtual ICollection<Studentgrade> Studentgrades { get; set; } = new List<Studentgrade>();
-    [Ignore]
     public virtual User User { get; set; } = null!;
 }

+ 1 - 14
EducationDepartment/EducationDepartment/Models/User.cs

@@ -10,31 +10,18 @@ namespace EducationDepartment.Models;
 public partial class User
 {
     public int Id { get; set; }
-    [Name("Имя")]
     public string FirstName { get; set; } = null!;
-    [Name("Фамилия")]
     public string LastName { get; set; } = null!;
-    [Name("Отчество")]
     public string? MiddleName { get; set; }
-    [Name("Почта")]
     public string Mail { get; set; } = null!;
-    [Name("Номер телефона")]
     public string? PhoneNumber { get; set; }
-    [Name("Дата рождения")]
     public DateOnly? DateBirth { get; set; }
-    [Ignore]
     public int IdRole { get; set; }
-    [Name("Пароль")]
     public string Password { get; set; } = null!;
-    [Ignore]
     public virtual ICollection<Building> Buildings { get; set; } = new List<Building>();
-    [Ignore]
     public virtual Role IdRoleNavigation { get; set; } = null!;
-    
-    public virtual Student? Student { get; set; }
-    [Ignore]
+     public virtual Student? Student { get; set; }
     public virtual Teacher? Teacher { get; set; }
-
     public override string ToString()=>
         $"{LastName} {FirstName[0]}.{(MiddleName!=null?MiddleName[0]+".":"")}";
 }

+ 0 - 1
EducationDepartment/EducationDepartment/ViewModels/AttendanceViewModel.cs

@@ -125,7 +125,6 @@ namespace EducationDepartment.ViewModels
             }
             AttendanceTable = newTable;
         }
-
 		string NewStr(string oldStr)
 		{
 			int n = 16 - oldStr.Count()/4;

+ 1 - 5
EducationDepartment/EducationDepartment/ViewModels/EvaluationStudentViewModel.cs

@@ -55,11 +55,7 @@ namespace EducationDepartment.ViewModels
             }
             MarksTable = newTable;
         }
-        public void WriteMarks()
-        {
-            File.WriteAllText("1.csv", $"Ñòóäåíò: {student.User}\tÏðåäìåò: {selectedOption}");
-            Converter.WriteCsv(MarksTable, "1.csv");
-        }
+        public void WriteMarks() => Converter.WriteCsv(MarksTable, "marks.csv");
 
     }
 }

+ 6 - 17
EducationDepartment/EducationDepartment/ViewModels/MainWindowViewModel.cs

@@ -3,11 +3,7 @@ using EducationalDepartment.Views;
 using EducationDepartament.Views;
 using EducationDepartment.Models;
 using ReactiveUI;
-using System;
-using System.Collections.Generic;
 using System.Linq;
-using System.Threading;
-using Tmds.DBus.Protocol;
 
 namespace EducationDepartment.ViewModels
 {
@@ -25,7 +21,7 @@ namespace EducationDepartment.ViewModels
         public string Option { get => option; set => option = value; }
         public string OptionValue { get => optionValue; set => optionValue = value; }
         public void SaveChanges()=> dbConnect.SaveChanges();
-        //authorization+
+        //authorization
         AuthorizationViewModel authorizationVM = new AuthorizationViewModel();
         public AuthorizationViewModel AuthorizationVM { get => authorizationVM; set => this.RaiseAndSetIfChanged(ref authorizationVM, value); }
         public bool AuthorizationSuccess()
@@ -47,7 +43,7 @@ namespace EducationDepartment.ViewModels
                 AuthorizationVM.Password = "";
             }
         }
-        //user profile+
+        //user profile
         UserProfileViewModel userProfileVM;
         public UserProfileViewModel UserProfileVM { get => userProfileVM; set => this.RaiseAndSetIfChanged(ref userProfileVM, value); }
         public void LoadUserProfile()
@@ -55,43 +51,36 @@ namespace EducationDepartment.ViewModels
             if (user.IdRole == 2) UC = new ProfileStudent();
             else if (user.IdRole == 1) UC = new ProfileTeacher();
         }
-        //timetables+
+        //timetables
         TimetableViewModel timetableVM;
         public TimetableViewModel TimetableVM { get => timetableVM; set => this.RaiseAndSetIfChanged(ref timetableVM, value); }
-        string lessonDate = "";
-        public string LessonDate { get => lessonDate; set => lessonDate = value; }
         public void LoadTimetablePage()
         {
             TimetableVM = new TimetableViewModel(dbConnect);
-            Message = "";
             UC = new TimeTable();
         }
-        //disciplines+
+        //disciplines
         DisciplineViewModel disciplineVM;
         public DisciplineViewModel DisciplineVM { get => disciplineVM; set => this.RaiseAndSetIfChanged(ref disciplineVM, value); }
         public void LoadDisciplinePage()
         {
             DisciplineVM = new DisciplineViewModel(dbConnect);
-            Message = "";
             UC = new Disciplines();
         }
-        //attendance+
+        //attendance
         AttendanceViewModel attendanceVM;
         public AttendanceViewModel AttendanceVM { get => attendanceVM; set => this.RaiseAndSetIfChanged(ref attendanceVM, value); }
         public void LoadAttendancePage()
         {
             AttendanceVM = new AttendanceViewModel(dbConnect);
-            Message = "";
             UC = new EducationDepartament.Views.Attendance();
         }
-
-        //evalution -
+        //evalution
         EvaluationStudentViewModel evaluationStudentVM;
         public EvaluationStudentViewModel EvaluationStudentVM { get => evaluationStudentVM; set => this.RaiseAndSetIfChanged(ref evaluationStudentVM, value); }
         public void LoadEvaluationStudentPage()
         {
             EvaluationStudentVM = new EvaluationStudentViewModel(dbConnect, user.Id);
-            Message = "";
             UC = new EvaluationStudent();
         }
     }

+ 0 - 8
EducationDepartment/EducationDepartment/Views/Attendance.axaml

@@ -8,7 +8,6 @@
              x:Class="EducationDepartament.Views.Attendance">
 	<Viewbox>
 		<Grid Background="#09102A"  Width="1000" Height="530">
-
 			<Button Command="{Binding LoadHomePage}" Background="#09102A" HorizontalAlignment="Left" VerticalAlignment="Top">
 				<Image Width="100" Height="100" Source="avares://EducationDepartment/Assets/1logo.png" HorizontalAlignment="Left" VerticalAlignment="Top" Margin="-8,-6,0,0"/>
 				<Button.Styles>
@@ -27,8 +26,6 @@
 				</Ellipse><TextBlock Text="{Binding UserProfileVM.User}" Margin="0,0,0,0" HorizontalAlignment="Center" VerticalAlignment="Center" FontSize="10" Foreground="White"/>
 			</StackPanel>
 		</Border>
-
-
 		<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="0,45,0,0" Width="750" Height="380" HorizontalAlignment="Center"  VerticalAlignment="Center">
 			<StackPanel>
 				<TextBlock Text="Фильтр" Margin="0,10,0,10" HorizontalAlignment="Center" FontSize="14" Foreground="White"/>
@@ -41,7 +38,6 @@
 				<Button Content="Показать" Command="{Binding AttendanceVM.GetNewAttendance}" Width="100" Height="35" Margin="0,5,0,0" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" HorizontalAlignment="Center" Foreground="White" Background="#4158AE"/>
 				<TextBlock Text="{Binding AttendanceVM.ParameterName}" Margin="150,0,0,10" HorizontalAlignment="Left" FontSize="14" Foreground="White"/>
 				<TextBlock Text="% посещаемости" Margin="0,-28,150,10" HorizontalAlignment="Right"  FontSize="14" Foreground="White"/>
-
 				<ScrollViewer VerticalScrollBarVisibility="Visible" Height="170" Width="450">
 					<ItemsControl ItemsSource="{Binding AttendanceVM.AttendanceTable}" >
 						<ItemsControl.ItemTemplate>
@@ -58,13 +54,9 @@
 							</DataTemplate>
 						</ItemsControl.ItemTemplate>
 					</ItemsControl>
-					
-
 				</ScrollViewer>
 			</StackPanel>
 		</Border>
-		
-
 	</Grid>
 	</Viewbox>
 </UserControl>

+ 0 - 3
EducationDepartment/EducationDepartment/Views/AuthorizationPage.axaml

@@ -21,11 +21,8 @@
 				<TextBlock Text="{Binding Message}" Foreground="White" HorizontalAlignment="Center"  Margin="10"/>
 			</StackPanel>
 		</Border>
-		
 	</Grid>
 	</Viewbox>
-	
-
 </UserControl>
 
 

+ 0 - 19
EducationDepartment/EducationDepartment/Views/MainWindow.axaml

@@ -11,27 +11,8 @@
         WindowState="Maximized">
 
 	<Design.DataContext>
-		<!-- This only sets the DataContext for the previewer in an IDE,
-             to set the actual DataContext for runtime, set the DataContext property in code (look at App.axaml.cs) -->
 		<vm:MainWindowViewModel/>
 	</Design.DataContext>
-
-	<!--что-то придумать с перемещением экрана
-	<Viewbox>
-		<Grid Background="#09102A" Width="1000" Height="530">
-			--><!-- Темно-синий цвет фона --><!--
-
-			<StackPanel HorizontalAlignment="Center" VerticalAlignment="Center">
-				--><!-- Расположение --><!--
-				<TextBlock Text="Учебная часть" HorizontalAlignment="Center" FontSize="64" Foreground="White"/>
-				--><!-- Надпись --><!--
-				<Image Source="avares://EducationDepartment/Assets/1logo.png" Width="270" Height="270"/>
-				--><!-- Картинка --><!--
-				<ContentControl Content="{Binding UC}"/>
-			</StackPanel>
-
-		</Grid>
-	</Viewbox>-->
 	<ContentControl Content="{Binding UC}"/>
 </Window>
 

+ 1 - 16
EducationDepartment/EducationDepartment/Views/Menu.axaml

@@ -6,12 +6,8 @@
 			 xmlns:vm="using:EducationDepartment.ViewModels"
 			 x:DataType="vm:MainWindowViewModel"
              x:Class="EducationDepartament.Views.Menu">
-
-
-
 	<Viewbox>
 		<Grid Background="#09102A"  Width="1000" Height="530">
-
 			<Button Command="{Binding LoadHomePage}" Background="#09102A" HorizontalAlignment="Left" VerticalAlignment="Top">
 				<Image Width="100" Height="100" Source="avares://EducationDepartment/Assets/1logo.png" HorizontalAlignment="Left" VerticalAlignment="Top" Margin="-8,-6,0,0"/>
 				<Button.Styles>
@@ -31,9 +27,6 @@
 					<TextBlock Text="{Binding UserProfileVM.User}" Margin="0,0,0,0" HorizontalAlignment="Center" VerticalAlignment="Center" FontSize="10" Foreground="White"/>
 				</StackPanel>
 			</Border>
-
-		
-
 		<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="150,40,0,0" Width="330" Height="350" HorizontalAlignment="Left">
 		</Border>
 			<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="155,115,0,0" Width="320" Height="110" HorizontalAlignment="Left" VerticalAlignment="Top">
@@ -42,15 +35,13 @@
 					<TextBlock Text="• Просмотр своей информации" Margin="20,10,0,0" FontSize="12" Foreground="White"/>
 					<TextBlock Text="• Редактирование профиля" Margin="20,0,0,0" FontSize="12" Foreground="White"/>
 					<TextBlock Text="• Удаление профиля" Margin="20,0,0,0" FontSize="12" Foreground="White"/>
-					
 				</StackPanel>
 			</Border>
 			<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="155,230,0,0" Width="320" Height="110" HorizontalAlignment="Left" VerticalAlignment="Top">
 				<StackPanel>
 					<Button Content="Преподаватели" Margin="-1,-1,0,0" Width="150" CornerRadius="3" Height="35" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" HorizontalAlignment="Left" Foreground="White" Background="#4158AE"/>
 					<TextBlock Text="• Просмотр информации о преподавателях" Margin="20,10,0,0" FontSize="12" Foreground="White"/>
-					<TextBlock Text="• Фильтрация по корпусам" Margin="20,0,0,0" FontSize="12" Foreground="White"/>
-					
+					<TextBlock Text="• Фильтрация по корпусам" Margin="20,0,0,0" FontSize="12" Foreground="White"/>				
 				</StackPanel>
 			</Border>
 			<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="155,345,0,0" Width="320" Height="110" HorizontalAlignment="Left" VerticalAlignment="Top">
@@ -58,13 +49,8 @@
 					<Button Content="Студенты" Margin="-1,-1,0,0" Width="150" CornerRadius="3" Height="35" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" HorizontalAlignment="Left" Foreground="White" Background="#4158AE"/>
 					<TextBlock Text="• Просмотр информации о студентах" Margin="20,10,0,0" FontSize="12" Foreground="White"/>
 					<TextBlock Text="• Фильтрация по группам" Margin="20,0,0,0" FontSize="12" Foreground="White"/>
-					
 				</StackPanel>
 			</Border>
-
-		
-		
-		
 		<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="0,40,150,0" Width="330" Height="350" HorizontalAlignment="Right" VerticalAlignment="Center">
 		</Border>
 			<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="0,115,155,0" Width="320" Height="80" HorizontalAlignment="Right" VerticalAlignment="Top">
@@ -72,7 +58,6 @@
 					<Button Content="Дисциплины" Command="{Binding LoadDisciplinePage}" Margin="-1,-1,0,0" Width="150" Height="35" HorizontalContentAlignment="Center" VerticalContentAlignment="Center" HorizontalAlignment="Left" Foreground="White" Background="#4158AE"/>
 					<TextBlock Text="• Просмотр всех дисциплин" Margin="20,5,0,0" FontSize="12" Foreground="White"/>
 					<TextBlock Text="• Фильтрация по преподавателям" Margin="20,0,0,0" FontSize="12" Foreground="White"/>
-					
 				</StackPanel>
 			</Border>
 			<Border BorderBrush="#4158AE" BorderThickness="2" CornerRadius="3" Margin="0,200,155,0" Width="320" Height="80" HorizontalAlignment="Right" VerticalAlignment="Top">

+ 3 - 2
EducationDepartment/EducationDepartment/bin/Debug/net7.0/1.csv

@@ -1,2 +1,3 @@
-MarkDate;MarkValue
-"05.04.2024                                                                                ";2
+
+
+

BIN
EducationDepartment/EducationDepartment/bin/Debug/net7.0/EducationDepartment.dll


BIN
EducationDepartment/EducationDepartment/bin/Debug/net7.0/EducationDepartment.pdb


+ 4 - 0
EducationDepartment/EducationDepartment/bin/Debug/net7.0/marks.csv

@@ -0,0 +1,4 @@
+האעא;מצוםךא
+"07.10.2023                                                                                ";3
+"27.03.2024                                                                                ";4
+"26.03.2024                                                                                ";5

+ 1 - 1
EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/Resources.Inputs.cache

@@ -1 +1 @@
-a65b8aa994f0aa0416db44fccb27dcff6e8f7d5b
+2b840ea8bf5d44db36b1a2d8ce0d47c091795796

BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.dll


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.pdb


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/original.ref.dll


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/Avalonia/resources


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/EducationDepartment.dll


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/EducationDepartment.pdb


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/ref/EducationDepartment.dll


BIN
EducationDepartment/EducationDepartment/obj/Debug/net7.0/refint/EducationDepartment.dll


+ 1354 - 0
модули.docx

@@ -0,0 +1,1354 @@
+Средства разработки
+   В современном мире разработки программного обеспечения создание удобных и эффективных пользовательских интерфейсов становится все более важной задачей. Разработка оконных приложений требует не только умения создавать функциональные возможности, но и обеспечения интуитивно понятного и привлекательного пользовательского опыта.
+   В данном проекте оконное приложение разрабатывается с использованием паттерна проектирования MVVM (Model-View-ViewModel) на языке программирования C# с использованием фреймворка Avalonia. Этот подход позволяет разделять логику приложения, его представление и управление пользовательским интерфейсом, что способствует легкости сопровождения кода, его тестирования и повторного использования, а также легкости работы с разными процессами параллельно группой разработчиков. Как хранилище данных для программы выбрана СУБД PostgreSQL.
+   Для полного понимания темы, давайте рассмотрим основные понятия:
+ MVVM (Model-View-ViewModel): Этот паттерн проектирования представляет собой разделение пользовательского интерфейса на три ключевых компонента: Модель (Model), Представление (View) и Модель представления (ViewModel). Модель представления служит связующим звеном между моделью данных и пользовательским интерфейсом, обеспечивая отделение логики представления от бизнес-логики.
+ Avalonia: Это кроссплатформенный фреймворк для разработки графических пользовательских интерфейсов (GUI) на языках программирования C# и XAML. Avalonia позволяет создавать красивые и отзывчивые приложения, которые могут работать на различных операционных системах, включая Windows, macOS и Linux.
+ PostgreSQL  -  мощная объектно-реляционная система управления базами данных (СУБД), которая обеспечивает надежное хранение и эффективное управление данными. Она широко используется в различных приложениях благодаря своей открытой природе, расширяемости и поддержке стандартов SQL. В нашей работе мы будем использовать PostgreSQL в качестве хранилища данных для наших приложений, чтобы обеспечить сохранность и доступность данных пользователя.
+Models
+   Модели в паттерне MVVM представляют собой компоненты, которые отвечают за представление бизнес-логики и управление данными. Они являются моделями данных приложения, которые предоставляют информацию и методы для их обработки и манипулирования.
+   Для ИС <<Учебный центр>> разработана 19 моделей, 14 из которых являются отражениями таблиц базы данных, а остальные необходимы для дополнительных целей. Программный код моделей представлен в листингах Приложения В. Опишем каждую из моделей подробнее.
+Таблица 1  -  Модели ИС <<Учебная часть>>
+№
+Название
+Обозначение
+Назначение
+Дополнительные классы
+ 
+AttendanceInfo
+Информация о посещаемости
+Краткая информация об успеваемости для вывода данных в контроллер элемент в представлении
+ 
+Converter
+Конвертер
+Предоставляет статичные методы для чтения и записи csv-файлов
+ 
+MarksInfo
+Информация об оценках
+Краткая информация об оценках для вывода данных в контроллер элемент в представлении
+ 
+Schekaleva31pContext
+Контекст БД
+Класс, реализующий связь программы с базой данных
+Таблицы базы данных
+ 
+Attendance
+Посещаемость
+Хранение информации о студенте, расписании (дата, дисциплина, преподаватель) и пометка присутствовал/не присутствовал на занятии 
+ 
+Building
+Корпус
+Хранение информации об адресе учебного корпуса, заведующем (навигация на таблицу пользователей) и ссылка на список расписания для данного корпуса
+ 
+Department
+Факультет
+Название факультета, ссылки на список специальностей факультета, дисциплин и преподавателей
+ 
+Discipline
+Дисциплина
+Название дисциплины, факультет, на котором она читается, количество уделяемых академических часов и ссылка на список <<Дисциплины преподавателей>>, определяющий, какие преподаватели ведут данную дисциплину
+ 
+Group
+Группа
+Название группы, специальность, дата основания группы (когда студенты начались учиться), ссылка на список дисциплин группы, список студентов группы
+ 
+Groupdiscipline
+Дисциплина группы
+Номер семестра, дисциплина преподавателя, группа, ссылка на список оценок (студент получил оценку за дисциплину, которая ведется в его группе), список расписаний (в сетке расписания для преподавателей и студентов указывается дисциплина и кто с кем ее проводит)
+ 
+Role
+Роль
+Название роли (преподаватель или студент) и ссылка на список всех пользователей по роли
+ 
+Specialty
+Специальность
+Название специальность, ее факультет и ссылка на список групп специальности
+ 
+Student
+Студент
+Информация о пользователе (личные данные), его группа, ссылки на список успеваемости студента и его оценок
+ 
+Studentgrade
+Оценка студента
+Информация о студенте, дисциплине группы, даты оценки, самой оценке и названии работы 
+ 
+Teacher
+Преподаватель
+Информация о пользователе (личные данные), его факультет и ссылка на список дисциплин преподавателя
+ 
+Teachersdiscipline
+Дисциплина преподавателя
+Информация о преподавателе, его дисциплине и ссылка на список дисциплин группы, которым соответствует данный объект (какую дисциплину группы какой преподаватель ведет)
+ 
+Timetable
+Расписание
+Информация о дате занятия, номере занятия (паре), дисциплине группы, корпусе и ссылка на список посещаемости студентами этого занятия сетки расписания
+ 
+User
+Пользователь
+Личные данные о пользователе: ФИО, почта, номер телефона, дата рождения, пароль, роль пользователя в системе
+
+ViewModels
+   ViewModel (Модель представления) представляет собой прослойку между пользовательским интерфейсом (View) и моделью данных (Model). ViewModel обеспечивает связь между этими двумя компонентами, предоставляя данные и методы, необходимые для отображения информации на пользовательском интерфейсе и обработки пользовательских действий.
+   Для ИС <<Учебная часть>> разработано 7 моделей представления, одна из которых главная и содержит объекты остальных классов, отвечающих за функционал в рамках одной страницы. Программный код моделей представления изложен в листингах Приложения В. Опишем каждую из моделей представления подробнее:
+ MainWindowViewModel
+   Главная модель представление, которая вызывает все остальные при совершении команд перехода на другую страницу, при этом меняет пользовательский контроллер на контроллер нового представления и инициализирует соответствующую ему ViewModel.
+   Основные поля: 
+ dbConnect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ UserControl uc  -  пользовательский контроллер, который биндится к главному окну, и с помощью которого меняются страницы  -  после присваивания этой переменной нового значения отображается новое представление 
+ User? user  -  текущий пользователь, который открыл сеанс работы с программой
+ string message  -  поле, использующееся для отображения сообщений пользователю в случае ошибок или пустой информации основного контента
+   Основные методы:
+ bool AuthorizationSuccess()  -  метод сверяет логин и пароль с данными бд, и если данный пользователь существует, возвращает значение True
+ void LoadHomePage()  -  если функция AuthorizationSuccess() возвратила успех, то выбирается и загружается новый пользовательский контроллер  -  в зависимости от роли пользователя загружается профиль либо студента, либо преподавателя. Данный метод загружает меню программы, из которого возможны переходы во все остальные окна
+ void LoadUserProfile()  -  метод перехода в личный кабинет пользователя
+ void LoadTimetablePage()  -  метод, который инициализирует новую ViewModel для расписания и загружает страницу расписания, переводя ее в uc
+ void LoadDisciplinePage()  -  метод, который инициализирует новую ViewModel для дисциплин и загружает страницу дисциплин, переводя ее в uc
+ void LoadAttendancePage()  -  метод, который инициализирует новую ViewModel для посещаемости и загружает страницу посещаемости, переводя ее в uc
+ void LoadEvaluationStudentPage()  -  метод, который инициализирует новую ViewModel для успеваемости студента и загружает страницу оценок, переводя ее в uc.
+ AuthorizationViewModel
+   Хранит два свойства: логин и пароль, которые при процессе авторизация сверяются с имеющимися в базе данных.
+ UserProfileViewModel
+   Хранит следующую информацию о личных данных авторизированного пользователя:
+ Connect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ User User  -  текущий пользователь, который открыл сеанс работы с программой
+ string FirstName  -  имя пользователя
+ string LastName  -  фамилия пользователя
+ string DateBirht  -  дата рождения пользователя
+ string Group  -  группа пользователя, если он студент
+ List<string> Groups  -  список всех групп, отображаемых в comboBox в личном кабинете студента
+ List<string> Disciplines  -  список дисциплин пользователя, если он преподаватель
+ string Discipline  -  первая видимая дисциплина преподавателя
+   Имеет конструктор, который принимает аргументы: контекст базы данных, логин пользователя (почта).
+ TimetableViewModel
+   Хранит следующую информацию о расписании:
+ Connect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ List<Timetable>? Timetable  -  список полученного расписания, после применения всех фильтров
+ List<string> TeachersList  -  список преподавателей, для выбора расписания
+ List<string> GroupsList  -  список групп, для выбора расписания
+ string ClassDate  -  дата занятий
+ List<string> Options  -  список опций (преподаватель или группа)
+ string SelectedOption  -  выбранная пользователем опция
+ string OptionValue  -  выбранное пользователем значение (конкретный преподаватель или группа)
+ List<string> Values  -  список значений, из которых пользователь выбирает
+   Методы:
+ void NewTimetable()  -  создание нового расписания по отмеченным пользователем фильтрам
+ List<string> NewValues(string selectedOption)  -  получение новых значений по выбранной опции (список преподавателей если выбран <<Преподаватель>>, список групп если выбрана <<Группа>>)
+ virtual void OnPropertyChanged(string propertyName)  -  сообщение о том, что некоторое свойство изменено, что изменяет значение зависимых полей и перерисовывает представление
+Данная модель представления имеет конструктор, который принимает контекст базы данных.
+ DisciplineViewModel
+   Хранит следующую информацию о дисциплинах:
+ Connect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ List<Discipline>? Disciplines  -  список дисциплин, полученный после применения всех фильтров
+ List<string> Options  -  список опция (преподаватель и группа)
+ string SelectedOption  -  выбранная пользователем опция
+ string OptionValue  -  выбранное пользователем значение
+ List<string> Values  -  список значений, который определяется при изменение выбранной опции
+   Методы:
+ void OnPropertyChanged(string propertyName)  -  сообщение о том, что некоторое свойство изменено, что изменяет значение зависимых полей и перерисовывает представление
+ void NewDisciplines()  -  получение нового списка дисциплин по выбранных опции и значении
+ List<string> NewValues(string selectedOption)  -  получение списка новых значений при изменении опции
+Данная модель представления имеет конструктор, который принимает контекст базы данных.
+ AttendanceViewModel
+   Хранит информацию о посещаемости студентов, имеет конструктор, который принимает контекст базы данных, и имеет следующие поля и свойства:
+ Connect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ List<string> Options  -  список опций для просмотра посещаемости (группа или дисциплина)
+ string SelectedOption  -  выбранная пользователем опция
+ List<string> secondOptions  -  второй список опций, в котором выбирается конкретные дисциплина или группа
+ string SecondSelectedOption  -  вторая выбранная пользователем опция
+ List<string> Values  -  список значений, который формируется при выборе второй опции: для группы  -   это список студентов, для дисциплин  -  список групп
+ string OptionValue  -  выбранное пользователем последнее значение
+ string ParameterName  -  название параметра  -  имя, которое указывается над столбцом значений в представлении посещаемости
+ List<AttendanceInfo> AttendanceTable  -  таблица посещаемости, сформированная после применения всех фильтров
+   Методы:
+ void OnPropertyChanged(string propertyName)  -  сообщение о том, что некоторое свойство изменено, что изменяет значение зависимых полей и перерисовывает представление
+ List<string> NewOption()  -  метол для получения вторых опций при изменении выбранной первой опции
+ List<string> NewValues()  -  метод для получения списка значений при изменения второй выбранной опции
+ void GetNewAttendance()  -  метод получения новой таблицы посещаемости, который ставит значение параметру и заполняет данные в соответствии с выбранными опциями.
+ EvaluationStudentViewModel
+   Данная модель представления имеет конструктор, который принимает контекст базы данных и ID пользователя, который вошел в систему, т.е. он сможет видеть только свои оценки.
+   Хранит информацию об оценках пользователя и имеет следующие свойства и поля:
+ Connect  -  контекст соединения с базой данных, из которого можно получать информацию их хранилища, обновлять и добавлять новую
+ Student student  -  студент, оценки которого показываются (открыт его аккаунт)
+ List<string> Options  -  список опций (дисциплины, по которым можно смотреть оценки)
+ string SelectedOption  -  выбранная пользователем опция
+ List<MarksInfo> MarksTable  -  таблица, которая хранит оценки и даты их получения за выбранную дисциплину у авторизовавшегося студента
+Методы:
+ void OnPropertyChanged(string propertyName)  -  сообщение о том, что некоторое свойство изменено, что изменяет значение зависимых полей и перерисовывает представление
+ List<string> StudentOptions()  -  получения дисциплин, в которых участвует данный студент
+ void GetMarks()  -  получение нового списка оценок по выбранной дисциплине
+ void WriteMarks()  -  вывод полученного списка MarksTable в csv-файл.
+Views
+   View (Представление) представляет собой пользовательский интерфейс приложения, который отображает данные и позволяет пользователю взаимодействовать с ними. View отвечает за отображение данных, реагирование на пользовательские действия и обновление интерфейса в соответствии с изменениями данных.
+   Для ИС <<Учебная часть>> разработано 9 представлений, одно из которых является главным и служит хранилищем контента остальных представлений. Одно представление является одной страницей, которая отображает блок действий и информации, логически относящейся к данному фрагменту программы. Опишем каждую из моделей подробнее:
+Таблица 2  -  Представления ИС <<Учебная часть>>
+№
+Название
+Обозначение
+Действия и информация
+ 
+AttendancePage
+Страница посещаемости
+Имеет три фильтра:
+ "Группа"/"дисциплина"
+ Выбор группы/дисциплины
+ Выбор всей группы или студента/ всех группы на дисциплине или одной группы
+После чего пользователь нажимает кнопку <<Показать>> и получается фильтрованную посещаемость. 
+Для перехода в главное меню нажать иконку приложения вверху слева
+ 
+AuthorizationPage
+Станица авторизации
+Имеется два поля для ввода: логин и пароль, пользователь нажимает на <<войти>> и переходит в свой профиль, если данные не корректны, выводится соответствующая ошибка
+ 
+DisciplinesPage
+Страница дисциплин
+Имеет два фильтра:
+ "Группа"/"преподаватель"
+ Выбор группы/преподавателя
+После чего пользователь нажимает кнопку <<Показать>> и получается фильтрованные дисциплины. 
+Для перехода в главное меню нажать иконку приложения вверху слева
+ 
+EvaluationStudent
+Page
+Страница оценок пользователя
+Данная страница доступна в аккаунте пользователя и изначально показывает лишь те оценки, которые получал этот пользователь, имеет фильтрацию по дисциплинам, показывает оценки и дату, когда они были поставлены. Также есть кнопка <<печать>>, которая позволяет вывести список оценок в csv-файл.
+ 
+ProfileStudent
+Профиль студента
+Быстрый доступ к страницам: расписание, оценки, дисциплины. И редактирование информации о пользователе: ФИО, дата рождения. Группу пользователь сам себе изменять не может.
+Для перехода в главное меню нажать иконку приложения вверху слева
+ 
+ProfileTeacher
+Профиль преподавателя
+Быстрый доступ к страницам: расписание, оценки, дисциплины, посещаемость студентов. И редактирование информации о пользователе: ФИО, дата рождения. Дисциплины пользователь сам себе изменять не может.
+Для перехода в главное меню нажать иконку приложения вверху слева
+ 
+TimeTablePage
+Страница расписания
+Имеет три фильтра:
+ "Группа"/"преподаватель"
+ Выбор группы/преподавателя
+ Выбор даты
+После чего пользователь нажимает кнопку <<Показать>> и получается день расписания. 
+Для перехода в главное меню нажать иконку приложения вверху слева
+ 
+Menu
+Меню
+Список всех страниц, на которые может переходить пользователь: профиль, дисциплины, оценки, посещаемость.
+ 
+MainWindow
+Главное окно
+С помощью контроллера контента хранит в себе каждую из страниц и переходит из одной на другую
+
+ПРИЛОЖЕНИЕ В. ПРОГРАММНЫЙ КОД МОДУЛЕЙ
+Листинг 1  -  Модель <<Посещаемость>>
+namespace EducationDepartment.Models;
+
+public partial class Attendance
+{
+    public int Id { get; set; }
+
+    public int TimetableId { get; set; }
+
+    public int StudentId { get; set; }
+
+    public bool Attended { get; set; }
+
+    public virtual Student Student { get; set; } = null!;
+
+    public virtual Timetable Timetable { get; set; } = null!;
+}
+Листинг 2  -  Модель <<Информация о посещаемости>>
+namespace EducationDepartment.Models
+{
+    public class AttendanceInfo
+    {
+        public AttendanceInfo(string value, double percentage)
+        {
+            Value = value;
+            Percentage = percentage;
+        }
+        //discipline, group, student
+        public string Value { get; set; }
+        //attendance %
+        public double Percentage { get; set; }
+    }
+}
+Листинг 3  -  Модель <<Корпусы>>
+namespace EducationDepartment.Models;
+
+public partial class Building
+{
+    public int Id { get; set; }
+
+    public int Mgr { get; set; }
+
+    public string Address { get; set; } = null!;
+
+    public virtual User MgrNavigation { get; set; } = null!;
+
+    public virtual ICollection<Timetable> Timetables { get; set; } = new List<Timetable>();
+}
+Листинг 4  -  Модель <<Конвертер>>
+namespace EducationDepartment.Models
+{
+    public class Converter
+    {
+        public static bool WriteCsv<T>(List<T> objects, string path)
+        {
+            try
+            {
+                var config = new CsvConfiguration(CultureInfo.CurrentCulture)
+                {
+                    HasHeaderRecord = true,
+                    Delimiter = ";"
+                };
+
+                using (var writer = new StreamWriter(path))
+                using (var csv = new CsvWriter(writer, config))
+                {
+                    csv.WriteHeader<T>();
+                    csv.NextRecord();
+                    foreach (var record in objects)
+                    {
+                        csv.WriteRecord(record);
+                        csv.NextRecord();
+                    }
+                }
+                return true;
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"Исключение: {ex.Message}\n" +
+                    $"Метод: {ex.TargetSite}\n" +
+                    $"Трассировка стека: {ex.StackTrace}");
+                return false;
+            }
+        }
+
+        public static List<T>? ReadCsv<T>(string path)
+        {
+            var config = new CsvConfiguration(CultureInfo.CurrentCulture)
+            {
+                HasHeaderRecord = true,
+                Delimiter = ";"
+            };
+            try
+            {
+                using (var reader = new StreamReader(path))
+                using (var csv = new CsvReader(reader, config))
+                {
+                    return csv.GetRecords<T>().ToList();
+                }
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"Исключение: {ex.Message}\n" +
+                    $"Метод: {ex.TargetSite}\n" +
+                    $"Трассировка стека: {ex.StackTrace}");
+                return null;
+            }
+        }
+    }
+}
+
+Листинг 5  -  Модель <<Факультет>>
+namespace EducationDepartment.Models;
+
+public partial class Department
+{
+    public int Id { get; set; }
+
+    public string Name { get; set; } = null!;
+
+    public virtual ICollection<Discipline> Disciplines { get; set; } = new List<Discipline>();
+
+    public virtual ICollection<Specialty> Specialties { get; set; } = new List<Specialty>();
+
+    public virtual ICollection<Teacher> Teachers { get; set; } = new List<Teacher>();
+}
+
+Листинг 6  -  Модель <<Дисциплина>>
+namespace EducationDepartment.Models;
+
+public partial class Discipline
+{
+    public int Id { get; set; }
+
+    public string Name { get; set; } = null!;
+
+    public int DepartmentId { get; set; }
+
+    public int AcademicHours { get; set; }
+
+    public virtual Department Department { get; set; } = null!;
+
+    public virtual ICollection<Teachersdiscipline> Teachersdisciplines { get; set; } = new List<Teachersdiscipline>();
+}
+Листинг 7  -  Модель <<Группа>>
+namespace EducationDepartment.Models;
+
+public partial class Group
+{
+    [Ignore]
+    public int Id { get; set; }
+    [Ignore]
+    public int IdSpecialty { get; set; }
+    [Ignore]
+    public DateOnly StartDate { get; set; }
+    [Name("Группа")]
+    public string Name { get; set; } = null!;
+    [Ignore]
+    public virtual ICollection<Groupdiscipline> Groupdisciplines { get; set; } = new List<Groupdiscipline>();
+    [Ignore]
+    public virtual Specialty IdSpecialtyNavigation { get; set; } = null!;
+    [Ignore]
+    public virtual ICollection<Student> Students { get; set; } = new List<Student>();
+}
+
+Листинг 8  -  Модель <<Дисциплина группы>>
+namespace EducationDepartment.Models;
+
+public partial class Groupdiscipline
+{
+    public int Id { get; set; }
+
+    public int? Semester { get; set; }
+
+    public int TeacherDisciplineId { get; set; }
+
+    public int GroupId { get; set; }
+
+    public virtual Group Group { get; set; } = null!;
+
+    public virtual ICollection<Studentgrade> Studentgrades { get; set; } = new List<Studentgrade>();
+
+    public virtual Teachersdiscipline TeacherDiscipline { get; set; } = null!;
+
+    public virtual ICollection<Timetable> Timetables { get; set; } = new List<Timetable>();
+}
+Листинг 9  -  Модель <<Информация об оценках>>
+namespace EducationDepartment.Models
+{
+    public class MarksInfo
+    {
+        public MarksInfo(string markDate, double markValue)
+        {
+            MarkDate = markDate;
+            MarkValue = markValue;
+        }
+        [Name("дата")]
+        public string MarkDate {  get; set; }
+        [Name("оценка")]
+        public double MarkValue { get; set; }
+    }
+}
+Листинг 10  -  Модель <<Роль>>
+namespace EducationDepartment.Models;
+
+public partial class Role
+{
+    public int Id { get; set; }
+
+    public string? Name { get; set; }
+
+    public virtual ICollection<User> Users { get; set; } = new List<User>();
+}
+Листинг 11  -  Модель <<Контекст базы данных>>
+public partial class Schekaleva31pContext : DbContext
+{
+    public Schekaleva31pContext()
+    {
+    }
+
+    public Schekaleva31pContext(DbContextOptions<Schekaleva31pContext> options)
+        : base(options)
+    {
+    }
+
+    public virtual DbSet<Attendance> Attendances { get; set; }
+
+    public virtual DbSet<Building> Buildings { get; set; }
+
+    public virtual DbSet<Department> Departments { get; set; }
+
+    public virtual DbSet<Discipline> Disciplines { get; set; }
+
+    public virtual DbSet<Group> Groups { get; set; }
+
+    public virtual DbSet<Groupdiscipline> Groupdisciplines { get; set; }
+
+    public virtual DbSet<Role> Roles { get; set; }
+
+    public virtual DbSet<Specialty> Specialties { get; set; }
+
+    public virtual DbSet<Student> Students { get; set; }
+
+    public virtual DbSet<Studentgrade> Studentgrades { get; set; }
+
+    public virtual DbSet<Teacher> Teachers { get; set; }
+
+    public virtual DbSet<Teachersdiscipline> Teachersdisciplines { get; set; }
+
+    public virtual DbSet<Timetable> Timetables { get; set; }
+
+    public virtual DbSet<User> Users { get; set; }
+
+    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
+        //local
+        //=> optionsBuilder.UseNpgsql("Host=edu.pg.ngknn.local;Port=5432;Database=schekaleva31p;Username=31P;Password=12345");
+        //global
+        => optionsBuilder.UseNpgsql("Host=ngknn.ru;Port=5442;Database=schekaleva31p;Username=31P;Password=12345");
+protected override void OnModelCreating(ModelBuilder modelBuilder)
+    {
+        modelBuilder.Entity<Attendance>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("attendance_pkey");
+
+            entity.ToTable("attendance");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.Attended).HasColumnName("attended");
+            entity.Property(e => e.StudentId).HasColumnName("student_id");
+            entity.Property(e => e.TimetableId).HasColumnName("timetable_id");
+
+            entity.HasOne(d => d.Student).WithMany(p => p.Attendances)
+                .HasForeignKey(d => d.StudentId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("attendance_student_id_fkey");
+
+            entity.HasOne(d => d.Timetable).WithMany(p => p.Attendances)
+                .HasForeignKey(d => d.TimetableId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("attendance_timetable_id_fkey");
+        });
+
+        modelBuilder.Entity<Building>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("buildings_pkey");
+
+            entity.ToTable("buildings");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.Address)
+                .HasMaxLength(70)
+                .HasColumnName("address");
+            entity.Property(e => e.Mgr).HasColumnName("mgr");
+
+            entity.HasOne(d => d.MgrNavigation).WithMany(p => p.Buildings)
+                .HasForeignKey(d => d.Mgr)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("buildings_mgr_fkey");
+        });
+
+        modelBuilder.Entity<Department>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("departments_pkey");
+
+            entity.ToTable("departments");
+
+            entity.HasIndex(e => e.Name, "departments_name_key").IsUnique();
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.Name)
+                .HasMaxLength(70)
+                .HasColumnName("name");
+        });
+
+        modelBuilder.Entity<Discipline>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("disciplines_pkey");
+
+            entity.ToTable("disciplines");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.AcademicHours).HasColumnName("academic_hours");
+            entity.Property(e => e.DepartmentId).HasColumnName("department_id");
+            entity.Property(e => e.Name)
+                .HasMaxLength(60)
+                .HasColumnName("name");
+
+            entity.HasOne(d => d.Department).WithMany(p => p.Disciplines)
+                .HasForeignKey(d => d.DepartmentId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("disciplines_department_id_fkey");
+        });
+
+        modelBuilder.Entity<Group>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("Groups_pkey");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.IdSpecialty).HasColumnName("id_specialty");
+            entity.Property(e => e.Name)
+                .HasMaxLength(5)
+                .HasColumnName("name");
+            entity.Property(e => e.StartDate).HasColumnName("start_date");
+
+            entity.HasOne(d => d.IdSpecialtyNavigation).WithMany(p => p.Groups)
+                .HasForeignKey(d => d.IdSpecialty)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("Groups_id_specialty_fkey");
+        });
+
+        modelBuilder.Entity<Groupdiscipline>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("groupdiscipline_pkey");
+
+            entity.ToTable("groupdiscipline");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.GroupId).HasColumnName("group_id");
+            entity.Property(e => e.Semester).HasColumnName("semester");
+            entity.Property(e => e.TeacherDisciplineId).HasColumnName("teacher_discipline_id");
+
+            entity.HasOne(d => d.Group).WithMany(p => p.Groupdisciplines)
+                .HasForeignKey(d => d.GroupId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("groupdiscipline_group_id_fkey");
+
+            entity.HasOne(d => d.TeacherDiscipline).WithMany(p => p.Groupdisciplines)
+                .HasForeignKey(d => d.TeacherDisciplineId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("groupdiscipline_teacher_discipline_id_fkey");
+        });
+
+        modelBuilder.Entity<Role>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("roles_pkey");
+
+            entity.ToTable("roles");
+
+            entity.HasIndex(e => e.Name, "roles_name_key").IsUnique();
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.Name)
+                .HasMaxLength(30)
+                .HasColumnName("name");
+        });
+        modelBuilder.Entity<Specialty>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("specialties_pkey");
+
+            entity.ToTable("specialties");
+
+            entity.HasIndex(e => e.Name, "specialties_name_key").IsUnique();
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.IdDepartment).HasColumnName("id_department");
+            entity.Property(e => e.Name)
+                .HasMaxLength(70)
+                .HasColumnName("name");
+
+            entity.HasOne(d => d.IdDepartmentNavigation).WithMany(p => p.Specialties)
+                .HasForeignKey(d => d.IdDepartment)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("specialties_id_department_fkey");
+        });
+
+        modelBuilder.Entity<Student>(entity =>
+        {
+            entity.HasKey(e => e.UserId).HasName("students_pkey");
+
+            entity.ToTable("students");
+
+            entity.Property(e => e.UserId)
+                .ValueGeneratedNever()
+                .HasColumnName("user_id");
+            entity.Property(e => e.GroupId).HasColumnName("group_id");
+
+            entity.HasOne(d => d.Group).WithMany(p => p.Students)
+                .HasForeignKey(d => d.GroupId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("students_group_id_fkey");
+
+            entity.HasOne(d => d.User).WithOne(p => p.Student)
+                .HasForeignKey<Student>(d => d.UserId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("students_user_id_fkey");
+        });
+
+        modelBuilder.Entity<Studentgrade>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("studentgrades_pkey");
+
+            entity.ToTable("studentgrades");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.Grade).HasColumnName("grade");
+            entity.Property(e => e.GradedAt).HasColumnName("graded_at");
+            entity.Property(e => e.GroupDisciplineId).HasColumnName("group_discipline_id");
+            entity.Property(e => e.StudentId).HasColumnName("student_id");
+            entity.Property(e => e.WorkName)
+                .HasMaxLength(70)
+                .HasColumnName("work_name");
+
+            entity.HasOne(d => d.GroupDiscipline).WithMany(p => p.Studentgrades)
+                .HasForeignKey(d => d.GroupDisciplineId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("studentgrades_group_discipline_id_fkey");
+
+            entity.HasOne(d => d.Student).WithMany(p => p.Studentgrades)
+                .HasForeignKey(d => d.StudentId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("studentgrades_student_id_fkey");
+        });
+
+        modelBuilder.Entity<Teacher>(entity =>
+        {
+            entity.HasKey(e => e.UserId).HasName("teachers_pkey");
+
+            entity.ToTable("teachers");
+
+            entity.Property(e => e.UserId)
+                .ValueGeneratedNever()
+                .HasColumnName("user_id");
+            entity.Property(e => e.DepartmentId).HasColumnName("department_id");
+
+            entity.HasOne(d => d.Department).WithMany(p => p.Teachers)
+                .HasForeignKey(d => d.DepartmentId)
+                .HasConstraintName("teachers_department_id_fkey");
+
+            entity.HasOne(d => d.User).WithOne(p => p.Teacher)
+                .HasForeignKey<Teacher>(d => d.UserId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("teachers_user_id_fkey");
+        });
+
+        modelBuilder.Entity<Teachersdiscipline>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("teachersdisciplines_pkey");
+
+            entity.ToTable("teachersdisciplines");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.DisciplineId).HasColumnName("discipline_id");
+            entity.Property(e => e.TeacherId).HasColumnName("teacher_id");
+
+            entity.HasOne(d => d.Discipline).WithMany(p => p.Teachersdisciplines)
+                .HasForeignKey(d => d.DisciplineId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("teachersdisciplines_discipline_id_fkey");
+
+            entity.HasOne(d => d.Teacher).WithMany(p => p.Teachersdisciplines)
+                .HasForeignKey(d => d.TeacherId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("teachersdisciplines_teacher_id_fkey");
+        });
+
+        modelBuilder.Entity<Timetable>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("timetables_pkey");
+
+            entity.ToTable("timetables");
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.BuildingId).HasColumnName("building_id");
+            entity.Property(e => e.ClassDate).HasColumnName("class_date");
+            entity.Property(e => e.ClassNumber).HasColumnName("class_number");
+            entity.Property(e => e.GroupDisciplineId).HasColumnName("group_discipline_id");
+
+            entity.HasOne(d => d.Building).WithMany(p => p.Timetables)
+                .HasForeignKey(d => d.BuildingId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("timetables_buildind_id_fkey");
+
+            entity.HasOne(d => d.GroupDiscipline).WithMany(p => p.Timetables)
+                .HasForeignKey(d => d.GroupDisciplineId)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("timetables_group_discipline_id_fkey");
+        });
+
+        modelBuilder.Entity<User>(entity =>
+        {
+            entity.HasKey(e => e.Id).HasName("users_pkey");
+
+            entity.ToTable("users");
+
+            entity.HasIndex(e => e.Mail, "users_mail_key").IsUnique();
+
+            entity.HasIndex(e => e.PhoneNumber, "users_phone_number_key").IsUnique();
+
+            entity.Property(e => e.Id).HasColumnName("id");
+            entity.Property(e => e.DateBirth).HasColumnName("date_birth");
+            entity.Property(e => e.FirstName)
+                .HasMaxLength(30)
+                .HasColumnName("first_name");
+            entity.Property(e => e.IdRole).HasColumnName("id_role");
+            entity.Property(e => e.LastName)
+                .HasMaxLength(30)
+                .HasColumnName("last_name");
+            entity.Property(e => e.Mail)
+                .HasMaxLength(50)
+                .HasColumnName("mail");
+            entity.Property(e => e.MiddleName)
+                .HasMaxLength(30)
+                .HasColumnName("middle_name");
+            entity.Property(e => e.Password)
+                .HasMaxLength(30)
+                .HasColumnName("password");
+            entity.Property(e => e.PhoneNumber)
+                .HasMaxLength(20)
+                .HasColumnName("phone_number");
+
+            entity.HasOne(d => d.IdRoleNavigation).WithMany(p => p.Users)
+                .HasForeignKey(d => d.IdRole)
+                .OnDelete(DeleteBehavior.ClientSetNull)
+                .HasConstraintName("users_id_role_fkey");
+        });
+
+        OnModelCreatingPartial(modelBuilder);
+    }
+
+    partial void OnModelCreatingPartial(ModelBuilder modelBuilder);
+}
+Листинг 12  -  Модель <<Специальность>>
+namespace EducationDepartment.Models;
+
+public partial class Specialty
+{
+    public int Id { get; set; }
+
+    public string Name { get; set; } = null!;
+
+    public int IdDepartment { get; set; }
+
+    public virtual ICollection<Group> Groups { get; set; } = new List<Group>();
+
+    public virtual Department IdDepartmentNavigation { get; set; } = null!;
+}
+Листинг 13  -  Модель <<Студент>>
+namespace EducationDepartment.Models;
+
+public partial class Student
+{
+    public int UserId { get; set; }
+    public int GroupId { get; set; }
+    public virtual ICollection<Attendance> Attendances { get; set; } = new List<Attendance>();
+    public virtual Group Group { get; set; } = null!;
+    public virtual ICollection<Studentgrade> Studentgrades { get; set; } = new List<Studentgrade>();
+    public virtual User User { get; set; } = null!;
+}
+Листинг 14  -  Модель <<Оценка студента>>
+namespace EducationDepartment.Models;
+
+public partial class Studentgrade
+{
+    public int Id { get; set; }
+
+    public int StudentId { get; set; }
+
+    public int GroupDisciplineId { get; set; }
+
+    public DateOnly? GradedAt { get; set; }
+
+    public short Grade { get; set; }
+
+    public string? WorkName { get; set; }
+
+    public virtual Groupdiscipline GroupDiscipline { get; set; } = null!;
+
+    public virtual Student Student { get; set; } = null!;
+}
+Листинг 15  -  Модель <<Преподаватель>>
+namespace EducationDepartment.Models;
+
+public partial class Teacher
+{
+    public int UserId { get; set; }
+
+    public int? DepartmentId { get; set; }
+
+    public virtual Department? Department { get; set; }
+
+    public virtual ICollection<Teachersdiscipline> Teachersdisciplines { get; set; } = new List<Teachersdiscipline>();
+
+    public virtual User User { get; set; } = null!;
+}
+Листинг 16  -  Модель <<Дисциплина преподавателя>>
+namespace EducationDepartment.Models;
+
+public partial class Teachersdiscipline
+{
+    public int Id { get; set; }
+
+    public int TeacherId { get; set; }
+
+    public int DisciplineId { get; set; }
+
+    public virtual Discipline Discipline { get; set; } = null!;
+
+    public virtual ICollection<Groupdiscipline> Groupdisciplines { get; set; } = new List<Groupdiscipline>();
+
+    public virtual Teacher Teacher { get; set; } = null!;
+}
+Листинг 17  -  Модель <<Расписание>>
+namespace EducationDepartment.Models;
+
+public partial class Timetable
+{
+    public int Id { get; set; }
+
+    public DateOnly ClassDate { get; set; }
+
+    public short? ClassNumber { get; set; }
+
+    public int GroupDisciplineId { get; set; }
+
+    public int BuildingId { get; set; }
+
+    public virtual ICollection<Attendance> Attendances { get; set; } = new List<Attendance>();
+
+    public virtual Building Building { get; set; } = null!;
+
+    public virtual Groupdiscipline GroupDiscipline { get; set; } = null!;
+}
+Листинг 18  -  Модель <<Пользователь>>
+namespace EducationDepartment.Models;
+
+public partial class User
+{
+    public int Id { get; set; }
+    public string FirstName { get; set; } = null!;
+    public string LastName { get; set; } = null!;
+    public string? MiddleName { get; set; }
+    public string Mail { get; set; } = null!;
+    public string? PhoneNumber { get; set; }
+    public DateOnly? DateBirth { get; set; }
+    public int IdRole { get; set; }
+    public string Password { get; set; } = null!;
+    public virtual ICollection<Building> Buildings { get; set; } = new List<Building>();
+    public virtual Role IdRoleNavigation { get; set; } = null!;
+     public virtual Student? Student { get; set; }
+    public virtual Teacher? Teacher { get; set; }
+    public override string ToString()=>
+        $"{LastName} {FirstName[0]}.{(MiddleName!=null?MiddleName[0]+".":"")}";
+}
+Листинг 19  -  Модель представления <<Посещаемость>>
+namespace EducationDepartment.ViewModels
+{
+	public class AttendanceViewModel : INotifyPropertyChanged
+	{
+		Schekaleva31pContext connect;
+		public AttendanceViewModel(Schekaleva31pContext dbConnect) => connect = dbConnect;
+		public event PropertyChangedEventHandler? PropertyChanged;
+		protected virtual void OnPropertyChanged(string propertyName)
+		{
+			PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
+			if (propertyName == "SelectedOption")
+				SecondOptions = NewOption();
+			if(propertyName == "SecondSelectedOption")
+				Values = NewValues();
+		}
+		//1 filter
+		public List<string> Options => new List<string> { "Группа", "Дисциплина" };
+		string selectedOption;
+		public string SelectedOption { get => selectedOption; set { selectedOption = value; OnPropertyChanged(nameof(SelectedOption)); } }
+		//2 filter
+		List<string> secondOptions;//list group, list disciplines
+		public List<string> SecondOptions { get => NewOption(); set { secondOptions = value; OnPropertyChanged(nameof(SecondOptions)); } }
+		string secondSelectedOption;
+		public string SecondSelectedOption { get => secondSelectedOption; set { secondSelectedOption = value; OnPropertyChanged(nameof(SecondSelectedOption)); } }
+		public List<string> NewOption()
+		{
+			return selectedOption=="Группа"?
+				connect.Groups.Select(x=>x.Name).ToList() :
+				connect.Disciplines.Select(x=>x.Name).ToList();
+		}
+		//3 values
+		List<string> values;//all group, student| all groups, group
+		public List<string> Values { get => NewValues(); set { values = value; OnPropertyChanged(nameof(Values)); } }
+		List<string> NewValues()
+		{
+			if (selectedOption == "Группа")
+				return new List<string> { "Вся группа" }.Union(connect.Students.Include(x => x.User)
+					.Include(x => x.Group).Where(x => x.Group.Name == secondSelectedOption).Select(x => x.User.ToString()).ToList()).ToList();
+			else if (selectedOption == "Дисциплина")
+				return new List<string> { "Все группы" }.Union(connect.Groupdisciplines.Include(x => x.TeacherDiscipline.Discipline)
+					.Include(x => x.Group).ToList().Where(x => x.TeacherDiscipline.Discipline.Name == secondSelectedOption)
+					.Select(x => x.Group.Name).ToList()).ToList();
+			else return null;
+		}
+        string optionValue;
+        public string OptionValue { get => optionValue; set => optionValue = value; }
+        public string ParameterName { get => parameterName; set { parameterName = value; OnPropertyChanged(nameof(ParameterName)); } }
+        string parameterName;
+
+        List<AttendanceInfo> attendanceTable;
+        public List<AttendanceInfo> AttendanceTable { get => attendanceTable; set { attendanceTable = value; OnPropertyChanged(nameof(AttendanceTable)); } }
+        public void GetNewAttendance()
+		{
+			List<AttendanceInfo> newTable = new List<AttendanceInfo>();
+            if (selectedOption == "Группа")
+			{
+				if (OptionValue == "Вся группа") 
+				{
+					ParameterName = $"Студенты группы {secondSelectedOption}";
+					
+					foreach(var student in connect.Students.Include(x=>x.User).Include(x=>x.Group)
+						.Where(x=>x.Group.Name == secondSelectedOption).Select(x => x.User).ToList())
+					{
+						var data = connect.Attendances.Include(x => x.Student).Where(x => x.Student.User == student);
+						if (data.Count() == 0) newTable.Add(new AttendanceInfo(NewStr(student.ToString()), 100));
+                        else newTable.Add(new AttendanceInfo(NewStr(student.ToString()), 
+							Math.Round((double)(data.Count(x=>x.Attended))/data.Count()*100,2)));
+					}
+				} 
+				else
+                {
+                    ParameterName = $"Дисциплины студента {optionValue}";
+					foreach (var studentDiscipline in connect.Groupdisciplines.Include(x => x.TeacherDiscipline.Discipline)
+						.Include(x => x.Group).Where(x => x.Group.Name == secondSelectedOption).Select(x => x.TeacherDiscipline.Discipline).ToList())
+					{
+						var data = connect.Attendances.Include(x => x.Student).Include(x => x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline).ToList()
+							.Where(x => x.Student.User.ToString() == optionValue && x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline == studentDiscipline).ToList();
+						if(data.Count==0) newTable.Add(new AttendanceInfo(NewStr(studentDiscipline.Name), 100));
+                        else newTable.Add(new AttendanceInfo(NewStr(studentDiscipline.Name),
+							Math.Round((double)(data.Count(x => x.Attended)) / data.Count() * 100,2)
+							));
+					}
+                }
+            }
+            else if (selectedOption == "Дисциплина")
+			{
+				if (OptionValue == "Все группы")
+				{
+					ParameterName = $"Группы на '{secondSelectedOption}'";
+					foreach (var group in connect.Groupdisciplines.Include(x => x.Group).Include(x => x.TeacherDiscipline.Discipline)
+						.Where(x => x.TeacherDiscipline.Discipline.Name == secondSelectedOption).Select(x => x.Group))
+					{
+						Schekaleva31pContext newConnect = new Schekaleva31pContext();
+						var data = newConnect.Attendances.Include(x => x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline)
+							.Where(x => x.Timetable.GroupDiscipline.Group == group &&
+							x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline.Name == secondSelectedOption).ToList();
+						if (data.Count() == 0) newTable.Add(new AttendanceInfo(NewStr(group.Name), 100));
+						else
+							newTable.Add(new AttendanceInfo(NewStr(group.Name),
+								Math.Round((double)(data.Count(x => x.Attended)) / data.Count()*100,2)));
+					}
+				}
+				else
+				{
+					ParameterName = $"Студенты группы {optionValue}";
+					foreach(var studentOnDiscipline in connect.Students.Include(x=>x.Group).Where(x=>x.Group.Name == optionValue))
+					{
+                        Schekaleva31pContext newConnect = new Schekaleva31pContext();
+                        var data = newConnect.Attendances.Include(x => x.Student).Include(x => x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline).ToList()
+							.Where(x => x.Student == studentOnDiscipline && x.Timetable.GroupDiscipline.TeacherDiscipline.Discipline.Name == secondSelectedOption);
+						if (data.Count() == 0) newTable.Add(new AttendanceInfo(NewStr(newConnect.Users.First(x => x.Student == studentOnDiscipline).ToString()), 100));
+						else
+							newTable.Add(new AttendanceInfo(NewStr(newConnect.Users.First(x => x.Student == studentOnDiscipline).ToString()),
+								Math.Round((double)(data.Count(x => x.Attended)) / data.Count()*100,2)));
+                    }
+                }
+            }
+            AttendanceTable = newTable;
+        }
+		string NewStr(string oldStr)
+		{
+			int n = 16 - oldStr.Count()/4;
+			return oldStr + new string('\t', n);
+		}
+    }
+}
+Листинг 20 -  Модель представления <<Авторизация>>
+namespace EducationDepartment.ViewModels
+{
+    public class AuthorizationViewModel : ViewModelBase
+    {
+        string login = "";
+        string password = "";
+        public string Login { get => login; set => this.RaiseAndSetIfChanged(ref login, value); }
+        public string Password { get => password; set => this.RaiseAndSetIfChanged(ref password, value); }
+    }
+}
+Листинг 21 -  Модель представления <<Дисциплины>>
+namespace EducationDepartment.ViewModels
+{
+	public class DisciplineViewModel : INotifyPropertyChanged
+	{
+		public event PropertyChangedEventHandler? PropertyChanged;
+		protected virtual void OnPropertyChanged(string propertyName)
+		{
+			PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
+			if (propertyName == "SelectedOption")
+			Values = NewValues(SelectedOption);
+		}
+		Schekaleva31pContext connect;
+		List<Discipline>? disciplines;
+		public List<Discipline>? Disciplines { get => disciplines; set { disciplines = value; OnPropertyChanged(nameof(Disciplines)); } }
+		public DisciplineViewModel(Schekaleva31pContext dbConnect) => connect = dbConnect;
+		public void NewDisciplines()
+		{
+			if (selectedOption == "Преподаватель")
+				Disciplines = connect.Teachersdisciplines.Include(x => x.Teacher.User).Include(x => x.Discipline).ToList()
+					.Where(x => x.Teacher.User.ToString() == optionValue).Select(x => x.Discipline).ToList();
+			else if (selectedOption == "Группа")
+				Disciplines = connect.Groupdisciplines.Include(x => x.Group).Include(x => x.TeacherDiscipline.Discipline).ToList()
+					.Where(x => x.Group.Name == optionValue).Select(x => x.TeacherDiscipline.Discipline).ToList();
+			else Disciplines = null;
+		}
+		public List<string> Options => new List<string> { "Преподаватель", "Группа" };
+		string selectedOption;
+		public string SelectedOption
+		{
+			get { return selectedOption; }
+			set
+			{
+				selectedOption = value;
+				OnPropertyChanged(nameof(SelectedOption));
+			}
+		}
+		string optionValue;
+		public string OptionValue { get => optionValue; set => optionValue = value; }
+		List<string> values;
+		public List<string> Values { get => NewValues(selectedOption); set { values = value; OnPropertyChanged(nameof(Values)); } }
+		public List<string> NewValues(string selectedOption)
+		{
+			return selectedOption == "Преподаватель" ?
+			connect.Teachers.Include(x => x.User).Select(x => x.User.ToString()).ToList() :
+			connect.Groups.Select(x => x.Name).ToList();
+		}
+	}
+}
+Листинг 22 -  Модель представления <<Оценки студента>>
+namespace EducationDepartment.ViewModels
+{
+    public class EvaluationStudentViewModel: INotifyPropertyChanged
+    {
+        public event PropertyChangedEventHandler? PropertyChanged;
+        protected virtual void OnPropertyChanged(string propertyName)
+        {
+            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
+        }
+        Schekaleva31pContext connect;
+        Student student;
+        public EvaluationStudentViewModel(Schekaleva31pContext dbConnect, int UserId)
+        {
+            connect = dbConnect;
+            student = connect.Students.First(x=>x.UserId == UserId);
+            options = StudentOptions();
+        }
+        List<string> options;
+        public List<string> Options { get => options; set => options = value; }
+        string selectedOption = "";
+        public string SelectedOption
+        {
+            get { return selectedOption; }
+            set
+            { selectedOption = value;OnPropertyChanged(nameof(SelectedOption));}
+        }
+
+        List<string> StudentOptions()
+        {
+            return connect.Groupdisciplines.Include(x=>x.TeacherDiscipline.Discipline)
+                .Include(x=>x.Group).Where(x=>x.Group == student.Group).Select(x=>x.TeacherDiscipline.Discipline.Name).ToList();
+        }
+        List<MarksInfo> marksTable; 
+        public List<MarksInfo> MarksTable { get => marksTable; set { marksTable = value; OnPropertyChanged(nameof(MarksTable)); } }
+        public void GetMarks()
+        {
+            List<MarksInfo> newTable = new List<MarksInfo>();
+            foreach(var studentGrade in connect.Studentgrades.Include(x=>x.GroupDiscipline.TeacherDiscipline.Discipline)
+                .Include(x=>x.Student).ToList().Where(x=>x.Student==student && x.GroupDiscipline.TeacherDiscipline.Discipline.Name == selectedOption)
+                .ToList())
+            {
+                newTable.Add(new MarksInfo(studentGrade.GradedAt.ToString()+new string(' ',80),
+                    studentGrade.Grade             
+                    ));
+            }
+            MarksTable = newTable;
+        }
+        public void WriteMarks() => Converter.WriteCsv(MarksTable, "marks.csv");
+
+    }
+}
+Листинг 23 -  Главная модель представления
+namespace EducationDepartment.ViewModels
+{
+    public class MainWindowViewModel : ViewModelBase
+    {
+        //general
+        public static Schekaleva31pContext dbConnect = new Schekaleva31pContext();
+        UserControl uc = new AuthorizationPage();
+        string option = "";
+        string optionValue = "";
+        User? user = null;
+        string message = "";
+        public string Message { get => message;set=>this.RaiseAndSetIfChanged(ref message, value); }
+        public UserControl UC { get => uc; set => this.RaiseAndSetIfChanged(ref uc, value); }
+        public string Option { get => option; set => option = value; }
+        public string OptionValue { get => optionValue; set => optionValue = value; }
+        public void SaveChanges()=> dbConnect.SaveChanges();
+        //authorization
+        AuthorizationViewModel authorizationVM = new AuthorizationViewModel();
+        public AuthorizationViewModel AuthorizationVM { get => authorizationVM; set => this.RaiseAndSetIfChanged(ref authorizationVM, value); }
+        public bool AuthorizationSuccess()
+        {
+            user = dbConnect.Users.FirstOrDefault(u => u.Mail == AuthorizationVM.Login && u.Password == AuthorizationVM.Password);
+            if (user == null) return false;
+            return true;
+        }
+        public void LoadHomePage()
+        {
+            if (AuthorizationSuccess()) {
+            UC = new EducationDepartament.Views.Menu();
+                UserProfileVM = new UserProfileViewModel(dbConnect, user.Mail);
+            } 
+            else
+            {
+                Message = "Ошибка авторизации";
+                AuthorizationVM.Login = "";
+                AuthorizationVM.Password = "";
+            }
+        }
+        //user profile
+        UserProfileViewModel userProfileVM;
+        public UserProfileViewModel UserProfileVM { get => userProfileVM; set => this.RaiseAndSetIfChanged(ref userProfileVM, value); }
+        public void LoadUserProfile()
+        {
+            if (user.IdRole == 2) UC = new ProfileStudent();
+            else if (user.IdRole == 1) UC = new ProfileTeacher();
+        }
+        //timetables
+        TimetableViewModel timetableVM;
+        public TimetableViewModel TimetableVM { get => timetableVM; set => this.RaiseAndSetIfChanged(ref timetableVM, value); }
+        public void LoadTimetablePage()
+        {
+            TimetableVM = new TimetableViewModel(dbConnect);
+            UC = new TimeTable();
+        }
+        //disciplines
+        DisciplineViewModel disciplineVM;
+        public DisciplineViewModel DisciplineVM { get => disciplineVM; set => this.RaiseAndSetIfChanged(ref disciplineVM, value); }
+        public void LoadDisciplinePage()
+        {
+            DisciplineVM = new DisciplineViewModel(dbConnect);
+            UC = new Disciplines();
+        }
+        //attendance
+        AttendanceViewModel attendanceVM;
+        public AttendanceViewModel AttendanceVM { get => attendanceVM; set => this.RaiseAndSetIfChanged(ref attendanceVM, value); }
+        public void LoadAttendancePage()
+        {
+            AttendanceVM = new AttendanceViewModel(dbConnect);
+            UC = new EducationDepartament.Views.Attendance();
+        }
+        //evalution
+        EvaluationStudentViewModel evaluationStudentVM;
+        public EvaluationStudentViewModel EvaluationStudentVM { get => evaluationStudentVM; set => this.RaiseAndSetIfChanged(ref evaluationStudentVM, value); }
+        public void LoadEvaluationStudentPage()
+        {
+            EvaluationStudentVM = new EvaluationStudentViewModel(dbConnect, user.Id);
+            UC = new EvaluationStudent();
+        }
+    }
+}
+Листинг 24 -  Модель представления <<Расписание>>
+namespace EducationDepartment.ViewModels
+{    public class TimetableViewModel : INotifyPropertyChanged
+    {
+        public event PropertyChangedEventHandler? PropertyChanged;
+        protected virtual void OnPropertyChanged(string propertyName)
+        {
+            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
+            if (propertyName == "Values" || propertyName == "Timetable" || propertyName=="ClassDate") return;
+            Values = NewValues(SelectedOption);
+        }
+        
+        Schekaleva31pContext connect;
+        List<Timetable>? timetable;
+        public List<Timetable>? Timetable { get => timetable; set { timetable = value; OnPropertyChanged(nameof(Timetable)); } }
+        public List<string> TeachersList { get => connect.Teachers.Include(x => x.User).Select(x => x.User.ToString()).ToList(); }
+        public List<string> GroupsList { get => connect.Groups.Select(x => x.Name).ToList(); }
+        public TimetableViewModel(Schekaleva31pContext dbConnect) => connect = dbConnect;
+        private string classDate;
+        public string ClassDate { get => classDate; set { classDate = value; OnPropertyChanged(nameof(ClassDate)); } }
+        public void NewTimetable()
+        {
+            if (SelectedOption == "Преподаватель")
+            {
+                Timetable = connect.Timetables.Include(x => x.GroupDiscipline.TeacherDiscipline.Teacher.User)
+                .Include(x => x.GroupDiscipline.TeacherDiscipline.Discipline).Include(x => x.GroupDiscipline.Group).ToList()
+                .Where(x => x.GroupDiscipline.TeacherDiscipline.Teacher.User.ToString() == optionValue && x.ClassDate == DateOnly.FromDateTime(DateTime.Parse(ClassDate))).ToList();
+            }
+            else if (SelectedOption == "Группа")
+                Timetable = connect.Timetables.Include(x => x.GroupDiscipline.TeacherDiscipline.Teacher.User)
+                .Include(x => x.GroupDiscipline.TeacherDiscipline.Discipline).Include(x => x.GroupDiscipline.Group).ToList()
+                .Where(x => x.GroupDiscipline.Group.Name == optionValue && x.ClassDate == DateOnly.FromDateTime(DateTime.Parse(ClassDate))).ToList();
+            else Timetable = null;
+        }
+        //do parameter to date
+        public List<string> Options => new List<string> { "Преподаватель", "Группа" };
+        string selectedOption = "";
+        public string SelectedOption
+        {
+            get { return selectedOption; }
+            set
+            {
+                selectedOption = value;
+                OnPropertyChanged(nameof(SelectedOption));
+            }
+        }
+        string optionValue;
+        public string OptionValue { get=> optionValue;  set => optionValue = value; }
+        List<string> values;
+        public List<string> Values { get => NewValues(selectedOption); set { values = value; OnPropertyChanged(nameof(Values)); } }
+
+        public List<string> NewValues(string selectedOption)
+        {
+            return selectedOption == "Преподаватель" ?
+            connect.Teachers.Include(x => x.User).Select(x => x.User.ToString()).ToList() :
+            connect.Groups.Select(x => x.Name).ToList();
+        }
+    }
+}
+Листинг 25 -  Модель представления <<Профиль пользователя>>
+namespace EducationDepartment.ViewModels
+{
+    public class UserProfileViewModel : ReactiveObject
+    {
+        Schekaleva31pContext connect;
+        User user;
+        public User User { get => user; set => this.RaiseAndSetIfChanged(ref user, value); }
+        public string FirstName { get => user.FirstName; set => user.FirstName = value; }
+        public string LastName { get => user.LastName; set => user.LastName = value; }
+        public string DateBirht { get => user.DateBirth.ToString(); 
+            set => user.DateBirth = DateOnly.FromDateTime(DateTime.Parse(value)); }
+        public UserProfileViewModel(Schekaleva31pContext dbConnect, string userMail)
+        {
+            connect = dbConnect;
+            user = connect.Users.Include(x => x.Student.Group).Include(x=>x.IdRoleNavigation).FirstOrDefault(user => user.Mail == userMail);
+        }
+        public string Group { get => user.Student.Group.Name; }
+        public List<string> Groups { get => connect.Groups.Select(x => x.Name).ToList(); }
+        public string Discipline { get => Disciplines.First(); }
+        public List<string> Disciplines { get => connect.Teachersdisciplines.Include(x => x.Teacher.User)
+                .Where(x => x.Teacher.User == user).Select(x => x.Discipline.Name).ToList();}
+    }
+}
+ПРИЛОЖЕНИЕ Г. СКРИНШОТЫ ПРОГРАММЫ
+                                       
+Рисунок 1  -  Страница авторизации пользователей
+                                       
+Рисунок 2  -  Меню ИС <<Учебная часть>>
+                                       
+Рисунок 3  -  Личный кабинет пользователя
+                                       
+Рисунок 4  -  Дисциплины преподавателя
+                                       
+Рисунок 5  -  Дисциплины группы
+                                       
+Рисунок 6  -  Расписание группы на день
+                                       
+Рисунок 7  -  Посещаемость студента группы по предметам
+                                       
+Рисунок 8  -  Общая посещаемость каждого студента группы
+                                       
+Рисунок 9  -  Посещаемость предмета по всем группам
+                                       
+Рисунок 10  -  Посещаемость предмета студентами группы
+                                       
+Рисунок 11  -  Оценки студента по предметам
+                                       
+Рисунок 12  -  Импорт оценок студента в csv-файл