为什么HTMLEditorKit不想在<b>元素内插入<i>元素?

时间:2019-11-16 02:02:53

标签: java html swing

完整的源代码可以找到here

如何在源中复制:

  1. 运行程序
  2. 点击粗体按钮
  3. 输入一些内容
  4. 在粗体文本内的某处
  5. 单击斜体按钮
  6. 输入更多内容
  7. 请注意斜体文本不是粗体。

MCVE:

您在这里。大部分是由Eclipse生成的,所以它很长。

public class MainFrame extends JFrame {

    private JPanel contentPane;

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            public void run() {
                try {
                    MainFrame frame = new MainFrame();
                    frame.setVisible(true);
                }
                catch (Exception e) {
                    e.printStackTrace();
                }
            }
        });
    }

    public MainFrame() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(100, 100, 450, 300);
        contentPane = new JPanel();
        contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
        contentPane.setLayout(new BorderLayout(0, 0));
        setContentPane(contentPane);

        JEditorPane editPane = new JEditorPane();
        editPane.setEditable(false);
        contentPane.add(editPane, BorderLayout.CENTER);

        HTMLEditorKit HTMLKit = new HTMLEditorKit();

        StyleSheet css = HTMLKit.getStyleSheet();
        css.addRule("body {font-family: Helvetica;}");
        HTMLKit.setDefaultCursor(Cursor.getPredefinedCursor(Cursor.TEXT_CURSOR));

        editPane.setEditorKit(HTMLKit);
        editPane.setOpaque(true);
        editPane.setText("<b>I \"WHAT?\"</b>");

        JButton btnInsertTheText = new JButton("Insert the text");
        btnInsertTheText.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                try {
                    HTMLKit.insertHTML((HTMLDocument) editPane.getDocument(), 3, "<i>SAID ", 0, 0, HTML.Tag.I);
                }
                catch (BadLocationException | IOException exc) {
                    // TODO Auto-generated catch block
                    exc.printStackTrace();
                }

                //System.out.println(editPane.getCaretPosition());
            }
        });
        contentPane.add(btnInsertTheText, BorderLayout.NORTH);
    }
}

运行示例,然后单击按钮。

所需的输出是: SAID “什么?”

实际输出为: SAID “什么?”

这是我正在构建的支持格式设置的文本编辑器。

所以现在发生的是,如果我尝试将<i>标记插入<b>标记中,则会插入<i>标记。结果? <b>标签要么移开,要么拆分!如何将一个插入另一个?

1 个答案:

答案 0 :(得分:1)

您还可以使用JTextPane显示HTML。

我发现它更容易,因为您可以使用文本属性标记文本,而不必担心HTML标签。

添加文本成为两个声明过程:

  1. 您首先插入文本,使其继承在插入位置当前有效的属性
  2. 然后将“斜体”属性应用于新添加的文本。

简单的例子:

import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.text.*;
import javax.swing.text.html.*;

public class TextPaneMRE extends JFrame
{
    /**
     * Launch the application.
     */
    public static void main(String[] args)
    {
        EventQueue.invokeLater(new Runnable() {
            public void run()
            {
                TextPaneMRE frame = new TextPaneMRE();
                frame.setVisible(true);
            }
        });
    }

    /**
     * Create the frame.
     */
    public TextPaneMRE()
    {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(100, 100, 450, 300);

        JTextPane textPane = new JTextPane();
        textPane.setContentType( "text/html" );
        textPane.setText("<b>I WHAT?</b>");
        textPane.setEditable(false);
        add(textPane, BorderLayout.CENTER);

        SimpleAttributeSet italic = new SimpleAttributeSet();
        StyleConstants.setItalic(italic, true);

        JButton btnInsertTheText = new JButton("Insert the text");
        btnInsertTheText.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e)
            {
                try
                {
                    StyledEditorKit editorKit = (StyledEditorKit)textPane.getEditorKit();
                    StyledDocument doc = (StyledDocument)textPane.getDocument();
                    String text = "SAID ";
                    doc.insertString(3, text, editorKit.getInputAttributes());
                    doc.setCharacterAttributes(3, text.length(), italic, false);
                    System.out.println("Text Pane: " + textPane.getText());
                }
                catch (BadLocationException exc)
                {
                    // TODO Auto-generated catch block
                    exc.printStackTrace();
                }
            }
        });

        add(btnInsertTheText, BorderLayout.NORTH);
        System.out.println("Text Pane: " + textPane.getText());
    }
}