mc_gem 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. checksums.yaml +7 -0
  2. data/Gemfile +12 -0
  3. data/Gemfile.lock +91 -0
  4. data/Lab1/arr1_3.txt +1 -0
  5. data/Lab1/lb1_1.rb +19 -0
  6. data/Lab1/lb1_2.rb +28 -0
  7. data/Lab1/lb1_3.rb +46 -0
  8. data/Lab1/lb1_4.rb +82 -0
  9. data/Lab2/1Class.jpg +0 -0
  10. data/Lab2/Web/main.rb +89 -0
  11. data/Lab2/Web/views/add.html +168 -0
  12. data/Lab2/Web/views/main.html +233 -0
  13. data/Lab2/data_storage/students1.txt +1 -0
  14. data/Lab2/data_storage/studentsRead.json +36 -0
  15. data/Lab2/data_storage/studentsRead.txt +3 -0
  16. data/Lab2/data_storage/studentsRead.yaml +26 -0
  17. data/Lab2/data_storage/studentsWrite.json +42 -0
  18. data/Lab2/data_storage/studentsWrite.txt +4 -0
  19. data/Lab2/data_storage/studentsWrite.yaml +31 -0
  20. data/Lab2/examples/Strategy.rb +38 -0
  21. data/Lab2/examples/adapter.rb +30 -0
  22. data/Lab2/examples/database.rb +15 -0
  23. data/Lab2/examples/observer_example.rb +51 -0
  24. data/Lab2/examples/pattern_pattern.rb +44 -0
  25. data/Lab2/examples/site_example.rb +21 -0
  26. data/Lab2/examples/views/about.erb +11 -0
  27. data/Lab2/examples/views/contact.erb +15 -0
  28. data/Lab2/examples/views/index.erb +11 -0
  29. data/Lab2/main.rb +6 -0
  30. data/Lab2/main_window.rb +31 -0
  31. data/Lab2/student_input_form.rb +71 -0
  32. data/Lab2/tab_students.rb +157 -0
  33. data/Lab2/test/student_test.rb +91 -0
  34. data/README.md +3 -0
  35. data/mc_gem/CHANGELOG.md +5 -0
  36. data/mc_gem/CODE_OF_CONDUCT.md +84 -0
  37. data/mc_gem/Documentation.md +33 -0
  38. data/mc_gem/Gemfile +13 -0
  39. data/mc_gem/LICENSE.txt +21 -0
  40. data/mc_gem/README.md +1 -0
  41. data/mc_gem/lib/mc_gem/version.rb +5 -0
  42. data/mc_gem/lib/mc_gem.rb +10 -0
  43. data/mc_gem/lib/source/adapters/student_list_adapter.rb +95 -0
  44. data/mc_gem/lib/source/containers/Data_list.rb +66 -0
  45. data/mc_gem/lib/source/containers/Data_list_student_short.rb +17 -0
  46. data/mc_gem/lib/source/containers/Data_table.rb +25 -0
  47. data/mc_gem/lib/source/controllers/student_edit_form_controller.rb +63 -0
  48. data/mc_gem/lib/source/controllers/student_input_form_controller.rb +56 -0
  49. data/mc_gem/lib/source/controllers/student_list_controller.rb +83 -0
  50. data/mc_gem/lib/source/converters/Converter.rb +11 -0
  51. data/mc_gem/lib/source/converters/Converter_json.rb +14 -0
  52. data/mc_gem/lib/source/converters/Converter_txt.rb +26 -0
  53. data/mc_gem/lib/source/converters/Converter_yaml.rb +14 -0
  54. data/mc_gem/lib/source/database/scripts/create_table.sql +10 -0
  55. data/mc_gem/lib/source/database/scripts/insert_data.sql +4 -0
  56. data/mc_gem/lib/source/database/student_list_db.rb +41 -0
  57. data/mc_gem/lib/source/database/students_db.rb +79 -0
  58. data/mc_gem/lib/source/model/Student.rb +106 -0
  59. data/mc_gem/lib/source/model/StudentBase.rb +50 -0
  60. data/mc_gem/lib/source/model/Student_short.rb +39 -0
  61. data/mc_gem/lib/source/repositories/Student_list.rb +65 -0
  62. data/mc_gem/lib/source/repositories/student_list_adv.rb +35 -0
  63. data/mc_gem/lib/source/util/LoggerHolder.rb +22 -0
  64. data/mc_gem/mc_gem.gemspec +17 -0
  65. data/mc_gem/sig/mvcStudentXD.rbs +4 -0
  66. metadata +121 -0
@@ -0,0 +1,233 @@
1
+ <html>
2
+ <head>
3
+ <style>
4
+ table.tbl td {
5
+ border: 1px solid black;
6
+ padding: 5px;
7
+ margin: 0px;
8
+ min-width: 100px;
9
+ height: 32px;
10
+ }
11
+
12
+ table.tbl tr {
13
+ padding: 5px;
14
+ margin: 5px;
15
+ }
16
+
17
+ .tbl {
18
+ overflow-x: scroll;
19
+ display:block;
20
+ }
21
+ .bt {
22
+ font-size: 15px;
23
+ padding: 5px 10px;
24
+ background-color: #5117d6;
25
+ color: #fff;
26
+ border: none;
27
+ border-radius: 5px;
28
+ cursor: pointer;
29
+ margin: 10px;
30
+ }
31
+
32
+ .bt:hover {
33
+ background-color: #22b91d;
34
+ }
35
+ </style>
36
+ </head>
37
+ <body style="margin: 0px;">
38
+ <div style="position: relative; height: 100%;">
39
+ <div style="display: flex; justify-content: flex-start; width: 100%;">
40
+
41
+ <div>
42
+ <div style="display: flex; margin: 16px; position: relative;">
43
+ <div style="width: 256px">
44
+
45
+ </div>
46
+ <div style="display: flex; width: 100%; text-align:center;margin-bottom: 20px;">
47
+ <button class = "bt" onclick="last_page()">Назад</button>
48
+ <div id="page_counter" style="text-align: center; width: 350px">
49
+ 1 из 5
50
+ </div>
51
+ <button class = "bt" onclick="next_page()">Вперед</button>
52
+ </div>
53
+
54
+ <div style="width: 256px">
55
+
56
+ </div>
57
+ </div>
58
+ <div style="display: flex; text-align:center;">
59
+ <div style="width: 20px; margin: auto;">
60
+
61
+ </div>
62
+
63
+ <div style="width: 1px; background-color: black; margin: auto;"></div>
64
+
65
+ <table class="tbl" style="margin: 0px; margin: auto;">
66
+ <thead style="margin: 0px; padding: 0px;">
67
+ <tr style="margin: 0px; padding: 0px;">
68
+ <td>ID</td>
69
+ <td>Фамилия</td>
70
+ <td>Имя</td>
71
+ <td>Отчество</td>
72
+ <td>GitHub</td>
73
+ <td>Телефон</td>
74
+ <td>Почта</td>
75
+ <td>Телеграм</td>
76
+ </td>
77
+ </tr>
78
+ </thead>
79
+ <tbody id="table_body">
80
+
81
+ </tbody>
82
+ </table>
83
+ <div style="width: 1px; background-color: black; margin: auto;"></div>
84
+
85
+ <div style="width: 256px; margin: auto; display: flex; flex-direction: column; margin: 8px;">
86
+ <button class = "bt" id="add" onclick="add_student()" >Добавить</button>
87
+ <button class = "bt" id="edit" onclick="edit_student()" >Изменить</button>
88
+ <button class = "bt" id="delete" onclick="delete_student()" >Удалить</button>
89
+ <button class = "bt" id="update" >Обновить</button>
90
+ </div>
91
+ </div>
92
+ </div>
93
+ </div>
94
+ </div>
95
+ <script>
96
+ let table = document.getElementById('table_body')
97
+
98
+ let selected_item = null
99
+
100
+ let add = document.getElementById('add')
101
+ let del = document.getElementById('delete')
102
+ let update = document.getElementById('update')
103
+ let edit = document.getElementById('edit')
104
+
105
+ function add_student() {
106
+ var http = new XMLHttpRequest();
107
+
108
+ http.open('POST', 'set_editing_idnull', false);
109
+ http.send();
110
+ window.location.href = '/add'
111
+ }
112
+
113
+ function edit_student() {
114
+ let id = document.getElementById('row_' + selected_item.toString() + "_column_0").textContent
115
+ var http = new XMLHttpRequest();
116
+
117
+ http.open('POST', 'set_editing_id' + id, false);
118
+ http.send();
119
+
120
+ window.location.href = '/add'
121
+ }
122
+
123
+ function generate_table_body() {
124
+ for(i = 0; i < 10; i++) {
125
+ let row = document.createElement('tr')
126
+ if (i === selected_item) {
127
+ row.style.backgroundColor = 'Red'
128
+ }
129
+ row.id = "row_" + i.toString()
130
+ row.onclick = (((x) => {
131
+ return () => {
132
+ let column = document.getElementById('row_' + x.toString() + "_column_1")
133
+ if (column.textContent !== "") {
134
+ selected_item = x
135
+ update_request()
136
+ } else {
137
+ selected_item = null
138
+ update_request()
139
+ }
140
+
141
+ }
142
+ }))(i)
143
+
144
+ for(j = 0; j < 8; j++) {
145
+ let column = document.createElement('td')
146
+ column.id = "row_" + i.toString() + "_column_" + j.toString()
147
+ row.appendChild(column)
148
+ }
149
+ table.appendChild(row)
150
+ }
151
+ }
152
+
153
+ function clear_table() {
154
+ table.innerHTML = ''
155
+ generate_table_body()
156
+ }
157
+
158
+ function delete_student() {
159
+ let column = document.getElementById('row_' + selected_item.toString() + "_column_0")
160
+
161
+ var http = new XMLHttpRequest();
162
+ http.open('POST', 'delete' + column.textContent, false);
163
+ http.send()
164
+
165
+ update_request()
166
+ }
167
+
168
+ function update_table(students) {
169
+ clear_table()
170
+ for(i = 0; i < students.length; i++) {
171
+ let attributes = [
172
+ students[i]['lastname'],
173
+ students[i]['firstname'],
174
+ students[i]['parental_name'],
175
+ students[i]['id'],
176
+ students[i]['git'],
177
+ students[i]['phone'],
178
+ students[i]['email'],
179
+ students[i]['telegram']
180
+ ]
181
+
182
+ for(j = 0; j < 8; j++) {
183
+ let column = document.getElementById('row_' + i.toString() + '_column_' + j.toString())
184
+ column.textContent = attributes[j]
185
+ }
186
+ }
187
+
188
+ if (selected_item != null) {
189
+ del.disabled = false
190
+ edit.disabled = false
191
+ } else {
192
+ del.disabled = true
193
+ edit.disabled = true
194
+ }
195
+ }
196
+
197
+ function next_page() {
198
+ var http = new XMLHttpRequest();
199
+ http.open('POST', 'next_page', false);
200
+ http.send()
201
+ update_request()
202
+ }
203
+
204
+ function last_page() {
205
+ var http = new XMLHttpRequest();
206
+ http.open('POST', 'last_page', false);
207
+ http.send()
208
+ update_request()
209
+ }
210
+
211
+ function update_request() {
212
+ var http = new XMLHttpRequest();
213
+ http.open('POST', 'students', false);
214
+ http.send()
215
+ let json = JSON.parse(http.responseText)
216
+ update_table(json)
217
+
218
+ var http = new XMLHttpRequest();
219
+ http.open('GET', 'get_page', false);
220
+ http.send()
221
+
222
+ var http2 = new XMLHttpRequest();
223
+ http2.open('GET', 'get_pages_count', false);
224
+ http2.send()
225
+
226
+ document.getElementById('page_counter').textContent = 'Страница ' + http.responseText + ' из ' + http2.responseText
227
+ }
228
+
229
+ generate_table_body()
230
+ update_request()
231
+ </script>
232
+ </body>
233
+ </html>
@@ -0,0 +1 @@
1
+ fio:Иванченко И. И.,email:iii@mail.ru,git:@fusfio:Сергеева С. С.,phone:89054037777,git:@rofio:Бирюков Б. Б.,telegram:@bbb,git:@duh
@@ -0,0 +1,36 @@
1
+ [
2
+ {
3
+ "last_name": "Иванченко",
4
+ "first_name": "Иван",
5
+ "parental_name": "Иванович",
6
+ "id": 1,
7
+ "email": "iii@mail.ru",
8
+ "git": "@fus"
9
+ },
10
+ {
11
+ "last_name": "Сергеева",
12
+ "first_name": "Станислава",
13
+ "parental_name": "Серова",
14
+ "id": 2,
15
+ "phone": "89054037777",
16
+ "git": "@ro"
17
+ },
18
+ {
19
+ "last_name": "Бирюков",
20
+ "first_name": "Бернард",
21
+ "parental_name": "Белов",
22
+ "id": 3,
23
+ "telegram": "@bbb",
24
+ "git": "@duh"
25
+ },
26
+ {
27
+ "last_name": "Иванов",
28
+ "first_name": "Иван",
29
+ "parental_name": "Иванович",
30
+ "id": 4,
31
+ "phone": "+79051111111",
32
+ "telegram": "@7",
33
+ "email":"s0163526@edu.kubsu.ru",
34
+ "git": "@6"
35
+ }
36
+ ]
@@ -0,0 +1,3 @@
1
+ last_name:Иванченко,first_name:Иван,parental_name:Иванович,id:1,email:iii@mail.ru,git:@fus
2
+ last_name:Сергеева,first_name:Станислава,parental_name:Серова,id:2,phone:89054037777,git:@ro
3
+ last_name:Бирюков,first_name:Бернард,parental_name:Белов,id:3,telegram:@bbb,git:@duh
@@ -0,0 +1,26 @@
1
+ - last_name: "Иванченко"
2
+ first_name: "Иван"
3
+ parental_name: "Иванович"
4
+ id: 1
5
+ email: "iii@mail.ru"
6
+ git: "@fus"
7
+ - last_name: "Сергеева"
8
+ first_name: "Станислава"
9
+ parental_name: "Серова"
10
+ id: 2
11
+ phone: "89054037777"
12
+ git: "@ro"
13
+ - last_name: "Бирюков"
14
+ first_name: "Бернард"
15
+ parental_name: "Белов"
16
+ id: 3
17
+ telegram: "@bbb"
18
+ git: "@duh"
19
+ - last_name: "Иванов"
20
+ first_name: "Иван"
21
+ parental_name: "Иванович"
22
+ id: 4
23
+ phone: "+79051111111"
24
+ telegram: "@7"
25
+ email: "s0163526@edu.kubsu.ru"
26
+ git: "@6"
@@ -0,0 +1,42 @@
1
+ [
2
+ {
3
+ "last_name": "Иванченко",
4
+ "first_name": "Иван",
5
+ "parental_name": "Иванович",
6
+ "id": 1,
7
+ "git": "@fus",
8
+ "email": "iii@mail.ru"
9
+ },
10
+ {
11
+ "last_name": "Сергеева",
12
+ "first_name": "Станислава",
13
+ "parental_name": "Серова",
14
+ "id": 2,
15
+ "phone": "89054037777",
16
+ "git": "@ro"
17
+ },
18
+ {
19
+ "last_name": "Бирюков",
20
+ "first_name": "Бернард",
21
+ "parental_name": "Белов",
22
+ "id": 3,
23
+ "git": "@duh",
24
+ "telegram": "@bbb"
25
+ },
26
+ {
27
+ "last_name": "Иванов",
28
+ "first_name": "Иван",
29
+ "parental_name": "Иванович",
30
+ "id": 4,
31
+ "phone": "+79051111111",
32
+ "git": "@6",
33
+ "telegram": "@7",
34
+ "email": "s0163526@edu.kubsu.ru"
35
+ },
36
+ {
37
+ "last_name": "Дорогов",
38
+ "first_name": "Дмитрий",
39
+ "parental_name": "Далдалович",
40
+ "id": 5
41
+ }
42
+ ]
@@ -0,0 +1,4 @@
1
+ last_name:Иванченко,first_name:Иван,parental_name:Иванович,id:1,git:@fus,email:iii@mail.ru
2
+ last_name:Сергеева,first_name:Станислава,parental_name:Серова,id:2,phone:89054037777,git:@ro
3
+ last_name:Бирюков,first_name:Бернард,parental_name:Белов,id:3,git:@duh,telegram:@bbb
4
+ last_name:Голубев,first_name:Глеб,parental_name:Газманович,id:4
@@ -0,0 +1,31 @@
1
+ ---
2
+ - last_name: Иванченко
3
+ first_name: Иван
4
+ parental_name: Иванович
5
+ id: 1
6
+ git: "@fus"
7
+ email: iii@mail.ru
8
+ - last_name: Сергеева
9
+ first_name: Станислава
10
+ parental_name: Серова
11
+ id: 2
12
+ phone: '89054037777'
13
+ git: "@ro"
14
+ - last_name: Бирюков
15
+ first_name: Бернард
16
+ parental_name: Белов
17
+ id: 3
18
+ git: "@duh"
19
+ telegram: "@bbb"
20
+ - last_name: Иванов
21
+ first_name: Иван
22
+ parental_name: Иванович
23
+ id: 4
24
+ phone: "+79051111111"
25
+ git: "@6"
26
+ telegram: "@7"
27
+ email: s0163526@edu.kubsu.ru
28
+ - last_name: Голубев
29
+ first_name: Глеб
30
+ parental_name: Газманович
31
+ id: 5
@@ -0,0 +1,38 @@
1
+ class Strategy
2
+ def execute
3
+ raise NotImplementedError, 'Определён в наследниках'
4
+ end
5
+ end
6
+
7
+ class Strategy1 < Strategy
8
+ def execute
9
+ puts 'Doing Strategy1...'
10
+ end
11
+ end
12
+
13
+ class Strategy2 < Strategy
14
+ def execute
15
+ puts 'Doing Strategy2...'
16
+ end
17
+ end
18
+
19
+ class Context
20
+ attr_accessor :strategy
21
+
22
+ def initialize(strategy)
23
+ self.strategy=strategy
24
+ end
25
+
26
+ def execute_strategy
27
+ strategy.execute
28
+ end
29
+
30
+ end
31
+
32
+ strategy1 = Strategy1.new
33
+ context = Context.new(strategy1)
34
+ context.execute_strategy
35
+
36
+ strategy2 = Strategy2.new
37
+ context.strategy = strategy2
38
+ context.execute_strategy
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ class Printer
4
+ def print(text)
5
+ puts text
6
+ end
7
+ end
8
+
9
+ class Display
10
+ def display(text)
11
+ puts text
12
+ end
13
+ end
14
+
15
+ class DisplayAdapter
16
+ def initialize(display)
17
+ @display = display
18
+ end
19
+
20
+ def print(text)
21
+ @display.display(text)
22
+ end
23
+ end
24
+
25
+ printer = Printer.new
26
+ display = Display.new
27
+ adapter = DisplayAdapter.new(display)
28
+
29
+ printer.print("Hello, world!") # выводит "Hello, world!"
30
+ adapter.print("Hello, world!") # также выводит "Hello, world!"
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ class Database
4
+ @@instance = nil
5
+
6
+ def self.instance
7
+ @@instance ||= Database.new
8
+ end
9
+
10
+ def execute
11
+ print("Establishing connection...")
12
+ end
13
+
14
+ private_class_method :new
15
+ end
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Класс Наблюдаемый объект
4
+ class Subject
5
+ attr_reader :state, :observers
6
+
7
+ def initialize(state)
8
+ @state = state
9
+ @observers = []
10
+ end
11
+
12
+ def add_observer(observer)
13
+ observers << observer
14
+ end
15
+
16
+ def remove_observer(observer)
17
+ observers.delete(observer)
18
+ end
19
+
20
+ def notify_observers
21
+ observers.each do |observer|
22
+ observer.update(self)
23
+ end
24
+ end
25
+
26
+ def update_state(state)
27
+ @state = state
28
+ notify_observers
29
+ end
30
+ end
31
+
32
+ # Класс Наблюдатель
33
+ class Observer
34
+ def update(subject)
35
+ puts "Subject has updated state to: #{subject.state}"
36
+ end
37
+ end
38
+
39
+ # Создаем объекты Наблюдаемый объект и Наблюдатель
40
+ subject = Subject.new("initial state")
41
+ observer = Observer.new
42
+
43
+ # Добавляем наблюдателя к наблюдаемому объекту
44
+ subject.add_observer(observer)
45
+
46
+ # Обновляем состояние наблюдаемого объекта
47
+ subject.update_state("new state")
48
+
49
+ # Результат выполнения:
50
+ # Subject has updated state to: new state
51
+
@@ -0,0 +1,44 @@
1
+ class Pat
2
+ attr_accessor :a, :b
3
+
4
+ def initialize(a, b)
5
+ self.a = a
6
+ self.b = b
7
+ end
8
+
9
+ def sum_alg
10
+ a+b
11
+ end
12
+
13
+ def mult_alg
14
+ a*b
15
+ end
16
+
17
+ def minus_alg
18
+ a-b
19
+ end
20
+
21
+ def alg
22
+ sum_alg+mult_alg+minus_alg
23
+ end
24
+ end
25
+
26
+ class PatInhetit1 < Pat
27
+ def sum_alg
28
+ a+b+2
29
+ end
30
+ end
31
+
32
+ class PatInhetit2 < Pat
33
+ def mult_alg
34
+ a*b*3
35
+ end
36
+ end
37
+
38
+ pat = Pat.new(4, 2)
39
+ pat1 = PatInhetit1.new(4, 2)
40
+ pat2 = PatInhetit2.new(4, 2)
41
+
42
+ puts(pat.alg)
43
+ puts(pat1.alg)
44
+ puts(pat2.alg)
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'sinatra'
4
+ require_relative '../main_window'
5
+
6
+ get '/' do
7
+ erb :index
8
+ end
9
+
10
+ get '/about' do
11
+ erb :about
12
+ end
13
+
14
+ get '/contact' do
15
+ erb :contact
16
+ end
17
+
18
+ get '/uni' do
19
+ MainWindow.new.create.show
20
+ end
21
+
@@ -0,0 +1,11 @@
1
+ <!-- about.erb -->
2
+ <!DOCTYPE html>
3
+ <html>
4
+ <head>
5
+ <title>Привет! Это мой сайт-визитка</title>
6
+ </head>
7
+ <body>
8
+ <h1>О нас</h1>
9
+ <p>Компания ЕКота занимается всем, что может принести вред.</p>
10
+ </body>
11
+ </html>
@@ -0,0 +1,15 @@
1
+ <!-- contact.erb -->
2
+ <!DOCTYPE html>
3
+ <html>
4
+ <head>
5
+ <title>Контакты</title>
6
+ </head>
7
+ <body>
8
+ <h1>Связь с нами</h1>
9
+ <p>Скорее всего, мы сами вас найдём, но если нет:</p>
10
+ <ul>
11
+ <li>Почта: info@mywebsite.com</li>
12
+ <li>Мобильный: 123-456-7890</li>
13
+ </ul>
14
+ </body>
15
+ </html>
@@ -0,0 +1,11 @@
1
+ <!-- index.erb -->
2
+ <!DOCTYPE html>
3
+ <html>
4
+ <head>
5
+ <title>Домашняя страница</title>
6
+ </head>
7
+ <body>
8
+ <h1>Добро пожаловать в обитель зла</h1>
9
+ <p>Я сейчас смотрю Твин Пикс</p>
10
+ </body>
11
+ </html>
data/Lab2/main.rb ADDED
@@ -0,0 +1,6 @@
1
+ require 'mysql2'
2
+ require 'mvcStudentXD'
3
+ require_relative 'main_window'
4
+
5
+ MainWindow.new.create
6
+ LoggerHolder.instance.level = Logger::DEBUG
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'mvcStudentXD'
4
+ require 'sinatra'
5
+ require 'thin'
6
+ require 'glimmer-dsl-libui'
7
+ require_relative 'tab_students'
8
+
9
+ class MainWindow
10
+ include Glimmer
11
+
12
+ def initialize
13
+ @view_tab_students = TabStudents.new
14
+ end
15
+
16
+ def create
17
+ window('Универ', 600, 300) {
18
+ tab {
19
+ tab_item('Студенты') {
20
+ @view_tab_students.create
21
+ }
22
+
23
+ tab_item('Вкладка 2') { }
24
+ tab_item('Вкладка 3') { }
25
+ }
26
+ }
27
+ end
28
+ end
29
+
30
+ main_window = MainWindow.new.create
31
+ main_window.show