Блокнот на языке Vala

от автора

В этом посте я расскажу о простом блокноте на языке программирования Vala. Программа создавалась с использованием среды разработки GNOME Builder и редактора интерфейсов Glade.

Внешний вид

Вот так приложение выглядит:

Слева можно видеть список всех заметок, которые автоматически сохраняются в специальной папке. Имя по умолчанию для любой заметки имеет вид даты и времени ее создания. Нажав на последнюю кнопку в хидербаре, можно назначить другое имя. Исходный код приложения находится здесь.

Иерархия элементов интерфейса в редакторе Glade:

Создание заметки

Нажав на первую кнопку, пользователь сразу же создает заметку с именем по умолчанию. За это отвечает следующий метод:

private void on_add_clicked(){         GLib.File file = GLib.File.new_for_path(directory_path+"/"+date_time());         try {             FileUtils.set_contents (file.get_path(), "");//создаем пустой файл         } catch (Error e) {             stderr.printf ("Error: %s\n", e.message);         }         if(!is_empty(text_view.buffer.text)){               text_view.buffer.text = "";         }          show_notes();//показываем список заметок       }

Метод date_time, который дает имя заметке:

private string date_time(){          var now = new DateTime.now_local ();          return now.format("%d")+"."+now.format("%m")+"."+now.format("%Y")+"  "+now.format("%H")+":"+now.format("%M")+":"+now.format("%S");     }

Идем дальше. Метод для показа списка:

private void show_notes () {            list_store.clear();            list = new GLib.List<string> ();             try {             Dir dir = Dir.open (directory_path, 0);             string? file_name = null;             while ((file_name = dir.read_name ()) != null) {                 list.append(file_name);             }         } catch (FileError err) {             stderr.printf (err.message);         }          Gtk.TreeIter iter;            foreach (string item in list) {                list_store.append(out iter);                list_store.set(iter, Columns.TEXT, item);            }        }

Метод вызывается каждый раз, когда нужно обновить список.

Удаление заметки

За удаление заметок отвечает вот такой метод:

private void on_delete_clicked(){          var selection = tree_view.get_selection();            selection.set_mode(Gtk.SelectionMode.SINGLE);            Gtk.TreeModel model;            Gtk.TreeIter iter;            if (!selection.get_selected(out model, out iter)) {                alert("Choose a note");                return;            }            GLib.File file = GLib.File.new_for_path(directory_path+"/"+item);          var dialog_delete_file = new Gtk.MessageDialog(this, Gtk.DialogFlags.MODAL,Gtk.MessageType.QUESTION, Gtk.ButtonsType.OK_CANCEL, "Delete note "+file.get_basename()+" ?");          dialog_delete_file.set_title("Question");          Gtk.ResponseType result = (Gtk.ResponseType)dialog_delete_file.run ();          dialog_delete_file.destroy();          if(result==Gtk.ResponseType.OK){          FileUtils.remove (directory_path+"/"+item);//удаляем файл          if(file.query_exists()){             alert("Delete failed");//не получилось удалить          }else{              show_notes();              text_view.buffer.text = "";//очищаем текстовую область          }       }    }

Удаление происходит только после подтверждения этого действия пользователем.

Сохранение заметок

Для сохранение заметок существует следующий код:

private void on_save_clicked(){          var selection = tree_view.get_selection();            selection.set_mode(Gtk.SelectionMode.SINGLE);            Gtk.TreeModel model;            Gtk.TreeIter iter;            if (!selection.get_selected(out model, out iter)) {                alert("Choose a note");                return;            }          if(is_empty(text_view.buffer.text)){              alert("Nothing to save");              return;          }          GLib.File file = GLib.File.new_for_path(directory_path+"/"+item);         var dialog_save_file = new Gtk.MessageDialog(this, Gtk.DialogFlags.MODAL,Gtk.MessageType.QUESTION, Gtk.ButtonsType.OK_CANCEL, "Save note "+file.get_basename()+" ?");          dialog_save_file.set_title("Question");          Gtk.ResponseType result = (Gtk.ResponseType)dialog_save_file.run ();          if(result==Gtk.ResponseType.OK){          try {             FileUtils.set_contents (file.get_path(), text_view.buffer.text);//записываем в файл содержимое текстовой области         } catch (Error e) {             stderr.printf ("Error: %s\n", e.message);         }           show_notes();       }       dialog_save_file.destroy();       }

Здесь, при сохранении сначала идет проверка, а есть ли вообще, что сохранять. В случае, если текст не обнаружен, пользователь получает соответствующее сообщение.

Сохранение заметок под другим именем

Для того чтобы поменять имя заметки используется такой метод:

private void on_save_as_clicked(){         var selection = tree_view.get_selection();            selection.set_mode(Gtk.SelectionMode.SINGLE);            Gtk.TreeModel model;            Gtk.TreeIter iter;            if (!selection.get_selected(out model, out iter)) {                alert("Choose a note");//нужно выбрать заметку из списка                return;            }         if(is_empty(text_view.buffer.text)){              alert("Nothing to save");//нечего сохранять              return;          }         var dialog_save_note = new Gtk.Dialog.with_buttons ("Save note", this, Gtk.DialogFlags.MODAL); 		var content_area = dialog_save_note.get_content_area ();         entry_name = new Gtk.Entry();         var label_name = new Gtk.Label.with_mnemonic ("_Name:");         var hbox = new Gtk.Box (Gtk.Orientation.HORIZONTAL, 20);         hbox.set_border_width(15);         hbox.pack_start (label_name, false, true, 0);         hbox.pack_start (entry_name, true, true, 0); 		content_area.add (hbox); 		dialog_save_note.add_button ("OK", Gtk.ResponseType.OK); 		dialog_save_note.add_button ("CLOSE", Gtk.ResponseType.CLOSE); 		dialog_save_note.response.connect (on_save_response); 		dialog_save_note.show_all ();       }

В вышеприведенном коде создается простенькое диалоговое окно для ввода нового имени заметки:

Для обработки нажатий на кнопки OK и CLOSE понадобится метод on_save_response:

private void on_save_response (Gtk.Dialog dialog, int response_id) {         switch (response_id) { 		case Gtk.ResponseType.OK: 		if(is_empty(entry_name.get_text())){ 		    alert("Enter the name");//нужно ввести имя         entry_name.grab_focus();         return; 		} 		GLib.File select_file = GLib.File.new_for_path(directory_path+"/"+item); 		GLib.File edit_file = GLib.File.new_for_path(directory_path+"/"+entry_name.get_text().strip()); 		if (select_file.get_basename() != edit_file.get_basename() && !edit_file.query_exists()){                 FileUtils.rename(select_file.get_path(), edit_file.get_path());//переименовываем файл                 if(!edit_file.query_exists()){                     alert("Rename failed");//не получилось переименовать                     return;                 }                 try {                  FileUtils.set_contents (edit_file.get_path(), text_view.buffer.text);               } catch (Error e) {                      stderr.printf ("Error: %s\n", e.message);             }             }else{                 if (select_file.get_basename() != edit_file.get_basename()) {                     alert("A note with the same name already exists");//такое имя уже есть                     entry_name.grab_focus();                     return;                 }                 try {                  FileUtils.set_contents (edit_file.get_path(), text_view.buffer.text);               } catch (Error e) {                      stderr.printf ("Error: %s\n", e.message);              }             }             show_notes();         dialog.destroy(); 		break; 	case Gtk.ResponseType.CLOSE: 	        dialog.destroy(); 	        break; 	case Gtk.ResponseType.DELETE_EVENT: 		dialog.destroy(); 		break; 		} }

Обязательно нужно проверить существует ли заметка с таким же именем и если существует, то предложить пользователю ввести другое имя.

Отображение текста заметки

Чтобы показать содержимое заметки используется такой код:

private void on_select_item () {            var selection = tree_view.get_selection();            selection.set_mode(Gtk.SelectionMode.SINGLE);            Gtk.TreeModel model;            Gtk.TreeIter iter;            if (!selection.get_selected(out model, out iter)) {                return;            }            Gtk.TreePath path = model.get_path(iter);            var index = int.parse(path.to_string());            if (index >= 0) {                item = list.nth_data(index);            }           string text;             try {                 FileUtils.get_contents (directory_path+"/"+item, out text);             } catch (Error e) {                stderr.printf ("Error: %s\n", e.message);             }             text_view.buffer.text = text;//показываем текст заметки        }

На этом все! До встречи в следующих постах!


Дата-центр ITSOFT — размещение и аренда серверов и стоек в двух дата-центрах в Москве. За последние годы UPTIME 100%. Размещение GPU-ферм и ASIC-майнеров, аренда GPU-серверов, лицензии связи, SSL-сертификаты, администрирование серверов и поддержка сайтов.

ссылка на оригинал статьи https://habr.com/ru/company/itsoft/blog/553488/


Комментарии

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *