Давно хотел написать программу? которая поможет отвлечься от компьютера на пару минут. Основная её задача - сообщить пользователю о том, что необходимо отвлечься от компьютера и отдохнуть.
Требования к проекту:
- Программу можно закрывать только в рабочий период;
- Программа не должна сворачиваться в период отдыха.
Далее я опишу проблемы возникшие при работе над проектом. Проект разрабатывается на Java, место его расположения здесь, используемое IDE - Eclipse.
Поехали.
Работа с циклом for, for-each
В процессе работы часто бывает нужно последовательно перебрать все элементы массива.Существует простая возможность прямого перебора всех элементов массива или коллекции. Это перебор "for-each", конструкция цикла не меняется для коллекций и массивов.
for (type var : arr) {
body-of-loop
}
где:
type - тип возвращаемой переменной var
arr - массив или коллекция которую перебирают
Рабочий пример:
int[] J = {1,2,3,4};
for (int i : J){
System.out.println(i);
}Стандартный перебор массива циклом for будет такой:
for (int i = 0; i < arr.length; i++) {
type var = arr[i];
body-of-loop
}
А для коллекции это выглядело бы вот так: for (Iteratoriter = coll.iterator(); iter.hasNext(); ) { type var = iter.next(); body-of-loop }
Диалоговое окно
Здесь вроде проблем нет, но лично я всё время забываю, как это делать. Думаю, будет полезно записать лишний раз.Итак простая команда:
JOptionPane.showMessageDialog(frame, "Сообщение");
где:
frame - это форма от которой построено диалоговое окно
"Сообщение" - это сообщение окна.
На всякий случай стоит сказать, что для использования JOptionPane необходимо импортировать javax.swing.JOptionPane, а то вдруг IDE не подскажет.
Остановка выполнения потока. Команда "sleep"
Иногда бывает необходимо остановить выполнение программы на определённый период. Делается это очень просто, главное запомнить в каком классе описан метод "sleep"try {
Thread.sleep(10000); // ждать 10 секунд
} catch (InterruptedException e) {
e.printStackTrace();
}
где:10000 - количество миллисекунд.
e.printStackTrace(); - выведет в консоль приложения стек ошибки.
Внешний вид JFrame, развёртывание окна на весь экран, отключение пиктограмм работы с окном.
Уж не знаю насколько корректно назван данный раздел, задача заключается в том, что нужно отключить кнопки сворачивания и разворачивания окна, а так же возможность его закрыть нажав "х".Над решением данной проблемы пришлось повозиться.
Для того, что бы построить форму максимального размера (раскрыть на весь экран) обычно советуют следующее:
JFrame fr = new JFrame(); // создание окна
fr.setVisible(true); // показать окно
fr.setExtendedState(fr.getExtendedState() | fr.MAXIMIZED_BOTH); // сделать окно максимальных размеров
fr.setAlwaysOnTop(true); // оставить окно поверх всех окон
Всё вроде просто и понятно. Но у меня не работало. Возможно были проблемы с операционкой, но окно не разворачивалось на весь экран.Так что пришлось пойти другим путём:
JFrame fr = new JFrame(); // создание окна
fr.setAlwaysOnTop(true); // оставляем всегда на верху
fr.setSize(Toolkit.getDefaultToolkit().getScreenSize()); // получаем разрешение экрана и устанавливаем максимальный размеры для окна
fr.setVisible(true); // показываем окно Результат выполнения этого кода меня устраивает гораздо больше.Для отключения кнопок окна и запрета его закрытия можно дописать следующие строчки:
fr.setDefaultCloseOperation(fr.DO_NOTHING_ON_CLOSE); // отключает возможность закрыть окно при нажатии "х"
fr.setUndecorated(true); // убираем заголовок окна и 3 кнопки работы с окном
Воспроизведение звукового .wav файла.
Механизм воспроизведения звукового файла оказался проще, чем показалось на первый взгляд.Обычно, в случаях когда нужно подать звуковой сигнал, я использовал BEEP, но с удивлением узнал, что домашний ноутбук, такой радостью не обладает. Так-что пришлось осваивать:
private void PlaySound() throws UnsupportedAudioFileException, IOException, LineUnavailableException {
// процедура проигрывающая один заранее заданный файл
AudioInputStream stream = AudioSystem.getAudioInputStream(new File("womp.wav")); // создаём аудио поток из файла
DataLine.Info info = new DataLine.Info(Clip.class, stream.getFormat()); // получаем информацию о звуке из потока
Clip clip = (Clip) AudioSystem.getLine(info); // инициализируем проигрыватель
clip.open(stream); // воспроизводим файл
clip.start(); // закрываем проигрыватель
}
где:"womp.wav" - звуковой файл находящийся в одном каталоге с исполняемым файлом
для работы со звуком необходим пакет javax.sound.sampled.*
Работа с XML.
Работа с XML документами является очень большой и сложной темой. Но я не могу пройти мимо и хочу оставить маленький пример, так сказать на будущее.Чтение XML файла простого формата
Пример обрабатывает простой файл следующего формата:<Head>
<tag1>value</tag1>
...
<tagN>value</tagN>
</Head>
В примере ниже идёт обращение по именам тегов:
try {
Document sets = DocumentBuilderFactory.newInstance().newDocumentBuilder().parse(path); // загружаем заданный файл
Element EyeSets = sets.getDocumentElement(); // получаем элементы документа
// получаем значение по именам
String sWaitPeriod = EyeSets.getElementsByTagName("tag1").item(0).getFirstChild().getNodeValue();
String sPracticePeriod = EyeSets.getElementsByTagName("tag2").item(0).getFirstChild().getNodeValue();
String sPracticeCount = EyeSets.getElementsByTagName("tag3").item(0).getFirstChild().getNodeValue();
// преобразование полученных данных в требуемый формат
try {
waitPeriod = Integer.parseInt(sWaitPeriod);
practicePeriod = Integer.parseInt(sPracticePeriod);
practiceCount = Integer.parseInt(sPracticeCount);
} catch (NumberFormatException nfe) {
JOptionPane.showMessageDialog(null, nfe.getMessage());
System.err.println(nfe.getMessage());
}
} catch (Exception e){
System.err.println(e.getMessage());
}
где:Загрузка XML файла простого формата
Сохранённый выше файл можно загрузить с помощью примера ниже:// задаём экземпляр потока выходного файла
FileOutputStream fo = null;
try {
// создаём экземпляр с заданным именем файла
fo = new FileOutputStream(path);
} catch (FileNotFoundException e1) {
e1.printStackTrace();
}
// создание экземпляра класса? генерирующего xml файл в указанный выходной поток
XMLStreamWriter writer;
try {
writer = XMLOutputFactory.newInstance().createXMLStreamWriter(fo);
try {
// начало создания файла
writer.writeStartDocument();
// основной тег
writer.writeStartElement("setings");
// открытие узла
writer.writeStartElement("tag1");
//запись значения узла
writer.writeCharacters(Integer.toString(waitPeriod));
// закрытие узла
writer.writeEndElement();
writer.writeStartElement("tag2");
writer.writeCharacters(Integer.toString(practicePeriod));
writer.writeEndElement();
writer.writeStartElement("tag3");
writer.writeCharacters(Integer.toString(practiceCount));
writer.writeEndElement();
// закрываем все открытые узлы
writer.writeEndDocument();
}
finally {
// закрываем класс
writer.close();
}
} catch (XMLStreamException e) {
e.printStackTrace();
}
где:path - путь где будет сохранён файл
Стоит отметить что существует 2 технологии работы с XML:
- SAX (Simple API for XML);
- DOM (Document Object Model).
В примерах выше вся работа велась через DOM объекты
Сериализация объектов в бинарный файл
Выше был приведён пример сохранения требуемых данных в XML файл. Но это не единственный способ сохранения состояний объектов. Существует возможность сериализации объекта в файл - для последующей его передачи куда либо или сохранения его текущих состояний.Необходимо помнить? что сериализуемые объекты должны наследовать интерфейс java.io.Serializable.
Функция для сохранения объекта очень проста:
public void writeSets(Vector<eyesset> ser) throws Exception{
System.out.println("write objects:");
FileOutputStream fos=new FileOutputStream("output.bin");
ObjectOutputStream oos=new ObjectOutputStream(fos);
oos.writeObject(ser);
oos.close();
}
где:Vector<eyesset> - коллекция объектов для сериализации.(может быть любым другим объектом реализующим интерфейс Serializable)
Для десериализации объекта можно использовать следующий пример:
/**
* Функция загружает настройки из сериализованного файла
* Изменяет список всех упражнений в текущем классе
*
* @return список всех упражнений
* @throws Exception FileNotFoundException - ошибка отсутствия загружаемого файла
* EOFException - ошибка обработки потока (поток достиг своего конца)
*
*/
public Vector<eyesset> readSets() throws Exception {
// загружаем все упражнения из сохранённого файла
File f = new File("output.bin");
if (f.exists()) {
System.out.println("Read objects:");
FileInputStream fis=new FileInputStream("output.bin");
ObjectInputStream ois=new ObjectInputStream(fis);
Vector<eyesset> readObject = (Vector<eyesset>)ois.readObject();
ois.close();
return readObject;
} else {return new Vector();} Выше, перед функцией, можно увидеть пример документирования кода ( JavaDoc). О том как писать JavaDoc можно почитать вот здес здесь
Переопределение отображения JList.
Довольно часто в списках JList требуется отображать только определённые данные из объекта. У программиста есть 2 варианта:- или создавать массив строк с готовыми данными для отображения, что на мой взгляд является не корректно;
- или переопределить отрисовку данных.
jlSet.setCellRenderer(new javax.swing.DefaultListCellRenderer(){
public Component getListCellRendererComponent(JList list,
Object value,
int index, boolean isSelected,
boolean cellHasFocus) {
Property prop = (Property)value;
setText(prop.getDisplayCoordinat());
return this;
}
});
Почитать первоисточник можно вот здесьНу вот кажется и всё.
Ждём продолжения, поскольку проект ещё не закончен и впереди показались проблемы, которые требуют своего решения.
Надеюсь на комментарии.
Продолжение часть 2


Спасибо, пригодилось
ОтветитьУдалить