Приложение Java Chat — проблемы с несколькими шрифтами, вставкой смайликов и таблиц

Я делаю приложение чата Java. Я уже сделал основы, и все работает нормально. Теперь я хотел добавить возможность менять шрифты и вставлять смайлики. Я также хотел добавить небольшую метку времени рядом с каждым сообщением.

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

  • I learned that it can be achieved using HTML. So I tried the HTML Editor Kit & it worked pretty well. Smilies, fonts & time was inserted.
    • However, I also have a requirement to save that chat conversation into a file (for chat history purposes). I know there is a Document behind all this. I tried using its methods to save/load, but having some problems. Code is below.
    • Кроме того, размер шрифта является проблемой, так как его диапазон составляет 1-7, и я хотел бы иметь нормальные диапазоны, как в MS Word.
    • Наконец, мои знания HTML очень базовые, и в наши дни HTML используется с CCS, о которой я ничего не знаю. Большинство веб-сайтов не рекомендуют использовать HTML-теги, поскольку последняя версия их даже не поддерживает. Это создаст проблему для моего приложения? Если это так, я хотел бы использовать другой метод для достижения вышеизложенного - не хочу использовать устаревшие вещи, даже если это для простого проекта колледжа.

КОД: я создал эти общие переменные:

HTMLEditorKit kit = new HTMLEditorKit();
HTMLDocument HTMLdoc = new HTMLDocument();
jTextPane1.setEditorKit(kit);
jTextPane1.setDocument(HTMLdoc);

В JButton у меня есть следующий код для вставки текста/чата:

kit.insertHTML(HTMLdoc, HTMLdoc.getLength(), "<tr>"
+ "<td width=\"50\" valign=\"top\">NAME:</td>"
+ "<td width=\"250\"><font size=\"3\" face=\"Monospaced\">" + addSmiles(JOptionPane.showInputDialog(null)) + "</font></td>"
+ "<td width=\"100\" valign=\"top\"><font size=\"1\">"
+ new SimpleDateFormat("hh:mm a").format(Calendar.getInstance().getTime()).toString() + "</font></td>"
+ "</tr>", 0, 0, null);

Метод addSmiles просто перебирает каждое слово и заменяет «:)» тегом img.

Чтобы сохранить/перезагрузить беседу, я использовал этот базовый код:

kit.read(new FileReader("asd.htm"), HTMLdoc, 0);
kit.write(new FileWriter("asd.htm"), HTMLdoc, 0, HTMLdoc.getLength());

Пишет нормально, а чтение выдает ошибку.

java.lang.RuntimeException: Must insert new content into body element

Я чувствую, что неправильно использовал метод insertHTML. Может ли кто-нибудь дать мне хорошую ссылку, которая показывает его использование? Особенно последние три аргумента (pop & pushDepth, insertTag) с примерами. Документы Oracle, не объясняйте это к моему удовольствию. :/

  • Я использовал стандартный StyledDocuemnt с SimpleAttributeSet для поддержки нескольких шрифтов. Я использовал RTFEditorKit и успешно сохранил/загрузил чаты. Но не мог вставить смайлики и таблицу для временных меток. Я наткнулся на одну ссылку здесь. Он пытается рисовать таблицы в JTextPane. Было трудно понять, но если вы, ребята, порекомендуете это, я серьезно рассмотрю это.

Надеюсь, я объяснил свою проблему прилично и не слишком долго! :D С нетерпением жду ваших ответов.

--------- РЕДАКТИРОВАТЬ :---------

Я немного изменил свой код:

Инициализации:

HTMLEditorKit kit = new HTMLEditorKit();
jTextPane1.setEditorKit(kit);
HTMLDocument HTMLdoc = (HTMLDocument) jTextPane1.getDocument();
HTMLdoc.putProperty("IgnoreCharsetDirective", true);

Я вставляю в документ начальные строки с соответствующим try-catch:

kit.insertHTML(HTMLdoc, 0, "<html><head><meta http-equiv=\"content-type\" content=\"text/html; charset=UTF-8\">", 0, 0, null);
kit.insertHTML(HTMLdoc, HTMLdoc.getLength(), "<table id=\"TBL\"></table>", 0, 0, null);

В любом чате я использую ту же строку HTML, что и раньше, просто изменил метод, используемый для вставки:

HTMLdoc.insertBeforeEnd(HTMLdoc.getElement("TBL"), "<tr>"
+ "<td width=\"50\" valign=\"top\">NAME:</td>"
+ "<td width=\"250\"><font size=\"3\" face=\"Monospaced\">" + addSmiles(JOptionPane.showInputDialog(null)) + "</font></td>"
+ "<td width=\"100\" valign=\"top\">" + new SimpleDateFormat("hh:mm a").format(Calendar.getInstance().getTime()).toString() + "</td>"
+ "</tr>");

Наконец, чтобы сохранить чат:

OutputStreamWriter out = new OutputStreamWriter(new FileOutputStream("asd"), "UTF-8");
kit.write(out, HTMLdoc, 0, HTMLdoc.getLength());
out.close();

До этого момента все работает прекрасно. Когда я открываю файл «asd», он правильно отображает HTML. Я даже могу открыть его в браузере и правильно просмотреть данные.

Чтобы получить данные и вставить их обратно в JTextPane/Document:

InputStreamReader in = new InputStreamReader(new FileInputStream("asd"), "UTF-8");
kit.read(in, HTMLdoc, 0);
in.close();

В этом случае я получаю сообщение об ошибке:

Exception in thread "AWT-EventQueue-0" java.lang.RuntimeException: Must insert new content into body element-
at javax.swing.text.html.HTMLDocument$HTMLReader.generateEndsSpecsForMidInsert(HTMLDocument.java:2353)
at javax.swing.text.html.HTMLDocument$HTMLReader.<init>(HTMLDocument.java:2300)
at javax.swing.text.html.HTMLDocument$HTMLReader.<init>(HTMLDocument.java:2174)
at javax.swing.text.html.HTMLDocument$HTMLReader.<init>(HTMLDocument.java:2169)
at javax.swing.text.html.HTMLDocument.getReader(HTMLDocument.java:326)
at javax.swing.text.html.HTMLEditorKit.read(HTMLEditorKit.java:260)
at ChatGUI.NewJFrame.jBtnRWActionPerformed(NewJFrame.java:157)

Где строка 157 указывает на инструкцию kit.read. Может ли кто-нибудь сказать мне, что я делаю неправильно здесь?

ПОВТОРИТЬ ИЗМЕНЕНИЕ---------------------------------------

Я понял свою ошибку :). Пришлось очистить документ перед чтением: HTMLdoc.remove(0, HTMLdoc.getLength()); Теперь все работает!!


person Vineet    schedule 15.03.2013    source источник


Ответы (1)


Здесь чтение Javadoc очень полезно.

Лучше всего держать элемент таблицы где-нибудь. Затем

// Assuming the table has attribute id="TBL":
Element tableElement = htmlDoc.getElement("TBL");
htmlDoc.insertBeforeEnd(tableElement, "<tr>...</tr>");

Я бы действительно посоветовал использовать таблицу стилей, которая может сократить HTML. Возможно, как <style type="text/css"> в HTML (для хранения).

Смайлики также можно делать с изображениями; как атрибут alt для ":)".

Лучше всего использовать Unicode, UTF-8, а не текущую кодировку операционной системы.

new InputStreamReader(new FileInputStream(file), "UTF-8")
new OutputStreamWriter(new FileOutputStream(file), "UTF-8")

С кодировкой, указанной в файле:

<html><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
person Joop Eggen    schedule 15.03.2013
comment
Отредактировал мой первоначальный пост с новым кодом. Не могли бы вы также уточнить, как использовать этот атрибут alt в теге img? Спасибо - person Vineet; 16.03.2013
comment
Извините, просто <img src="..." alt=";)">, чтобы получатель мог создать код, наведя указатель мыши, а преобразование в обычный текст (если вы это сделаете) можно заменить альтернативным текстом. - person Joop Eggen; 16.03.2013