Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/386.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 在JTextPane中获取所选文本的属性_Java_Attributes_Selection_Jtextpane_Caret - Fatal编程技术网

Java 在JTextPane中获取所选文本的属性

Java 在JTextPane中获取所选文本的属性,java,attributes,selection,jtextpane,caret,Java,Attributes,Selection,Jtextpane,Caret,我试图找出如何在JTextPane中获取所选文本的属性。 我发现最好的解决方案是使用getInputAttribute()和CaretListener。但是我对这个实现有一些问题 我的解决方案显示插入符号最后位置上的文本属性,但不显示插入符号的实际位置。我做错了什么?求你了 这是我的SSCCE: public class Testovani{ static JTextPane pane; static JLabel label; public static void main(String[

我试图找出如何在JTextPane中获取所选文本的属性。 我发现最好的解决方案是使用getInputAttribute()和CaretListener。但是我对这个实现有一些问题

我的解决方案显示插入符号最后位置上的文本属性,但不显示插入符号的实际位置。我做错了什么?求你了

这是我的SSCCE:

public class Testovani{
static JTextPane pane;
static JLabel label;

public static void main(String[] args) throws BadLocationException {
    JFrame frame = new JFrame();
    frame.setSize(350, 300);
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setLayout(new BorderLayout());

    pane = new JTextPane();
    label = new JLabel();
    pane.addCaretListener(new SelectionListener());

    MutableAttributeSet attrs = new SimpleAttributeSet();
    StyleConstants.setBold(attrs, true);
    pane.getDocument().insertString(0, "\n", null);
    pane.getDocument().insertString(0, "This is first row non bold", null);
    pane.getDocument().insertString(0, "\n", null);
    pane.getDocument().insertString(0, "This is second row bold", attrs);
    pane.getDocument().insertString(0, "\n", null);
    pane.getDocument().insertString(0, "This is third row bold", attrs);
    pane.getDocument().insertString(0, "\n", null);

    frame.add(pane);
    frame.add(label, BorderLayout.SOUTH);
    frame.setVisible(true);
}

private static class SelectionListener implements CaretListener{
    @Override
    public void caretUpdate(CaretEvent e) {
        AttributeSet attrs =((StyledEditorKit)pane.getEditorKit()).getInputAttributes();
        label.setText("Is bold: " + String.valueOf(StyleConstants.isBold(attrs)));
    }   
}}

我有两个额外的问题。这种方法是用于选择还是仅用于插入符号的位置?如果有一部分为粗体而第二部分为非粗体的文本选择,结果会是什么?

实际上,选择的属性是一个复杂的问题,需要您了解业务需求

假设选择了一段文本,您需要选择字体大小。但是 片段有3段不同大小的文本

选择开始位置位于10pt文本的中间,然后是一段12pt大小的文本,选择结束于14pt大小片段的中间

你想要多大尺寸的?10、12、14或(多个)

最简单的方法是使用InputAttribute

默认情况下,属性是从插入符号位置复制的,但您当然可以添加插入符号侦听器,并在每次更新时根据业务逻辑(处理具有不同属性的多个文本片段)检查和填充输入属性

更新:
尝试包装
属性集attrs=((StyledEditorKit)窗格.getEditorKit()).getInputAttribute()
在SwingUtilities.invokeLater()调用中,没有获取选择属性的预期行为,这仅仅是因为选择可以具有每个不同属性的字符元素

您必须了解,返回文本窗格为下一次输入计算出的最佳属性的
getInputAttributes
与返回当前插入符号位置属性的
getCharacterAttributes
之间存在差异。对于选择,插入符号是结束选择的位置。如果从左到右或从右到左选择文本,它可以是给定的
getSelectionStart
getSelectionEnd

无论如何,我建议您获取JTextPane的StyledDocument,然后从
getSelectionStart
getSelectionEnd
迭代字符元素:

for(int i=jtp.getSelectionStart(); i<jtp.getSelectionEnd(); i++) {
    AttributeSet set = jtp.getStyledDocument().getCharacterElement(i).getAttributes();
    //here, combine, analyse, do whatever you like with your AttributeSet
    //You can use StyleConstants.xxx to analyse the attributes
}

for(int i=jtp.getSelectionStart();i我使用@Sharcoux的解决方案,但做了一个更改:我确保始终至少有一个字符需要迭代。当没有选择时,
getSelectionStart()==getSelectionEnd()
。出于这个原因,我将对以下内容做一点小小的更改:

int iStart = jtp.getSelectionStart();
int iEnd = jtp.getSelectionEnd();
if(iStart > 0) iStart--;
else if(iEnd < jtp.getDocument().getEndPosition().getOffset()) iEnd++;
for(int i = iStart; i < iEnd; i++) {
    AttributeSet set = jtp.getStyledDocument().getCharacterElement(i).getAttributes();
    //here, combine, analyse, do whatever you like with your AttributeSet
    //You can use StyleConstants.xxx to analyse the attributes
}
int-iStart=jtp.getSelectionStart();
int iEnd=jtp.getSelectionEnd();
如果(iStart>0)iStart--;
else if(iEnd

唯一一个不改变任何内容的例子是当文档完全为空时,在这种情况下,
getInputAttribute
应该可以正常工作。

肯定是有用的答案,我稍后会使用它。但首先,我需要知道为什么方法getInputAttribute()在my CaretListener中,返回上一个插入符号位置的属性。这是因为这通常是预期的行为:如果您将插入符号放在粗体文本之后,您通常也希望您的输入是粗体的。非常感谢。它很有效。StanislavL中的更新答案解决了我的问题。谢谢,我已经为选定的插入符号使用了此选项但是,如果没有选择,它在某些特殊情况下无法正常工作。如果没有选择,我需要用于文本的属性,将写入什么。我希望,这是方法getInputAttribute()的返回看起来是。但它给了我最后一个插入符号位置的属性。不是以前的字符属性,而是文档中任何地方的前一个插入符号位置。(看图片。)我希望这不是预期的行为。那么我一定是做错了什么。你知道吗?拜托。这可能意味着在更新输入样式之前调用了你的caretListener。无论如何,我总是对JTextPane的默认样式计算有问题,所以我自己做了。你可以做的是停止转发输入属性,并在选择开始之前使用或字符的属性(即使没有选择也可以使用),或者如果插入符号正好位于新行(\n)之后或文档开头,则使用默认样式