【问题标题】:JTable, JTextArea or JEditorPane to highlight lines of code?JTable、JTextArea 或 JEditorPane 来突出显示代码行?
【发布时间】:2012-03-24 10:02:28
【问题描述】:

更新:

通过添加以下代码,我在此答案 here 中找到了部分解决方案:

class CustomRenderer extends DefaultTableCellRenderer 
{
    public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)
    {
        Component c = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
        c.setBackground(new java.awt.Color(255, 72, 72));
        return c;
    }
}

然后将它传递给我的 JTable 对象:

jTable2.setDefaultRenderer(String.class, new CustomRenderer());

这可以正常工作,现在表格行是红色的:

我现在唯一需要知道的是如何将着色限制为单行和单个单元格。

经过进一步研究,我需要一个 setCellRender() 方法,以便我可以在特定单元格上设置自定义渲染,但此方法不存在。


问题:

我想创建一个逐步执行伪代码的可视化组件。

为此,我创建了一个 JTable,现在我正在寻找方法来突出显示每一行(或单元格,因为只有一列)以显示正在执行的行。

我在下面的最终 GUI 中包含了一个模型。正如您在 Pseudocode 面板中看到的那样,我突出显示了最后一行。

请忽略与问题无关的箭头。

我已经开始在 Netbeans Matisse 中实现模型(这是 3 种算法中的 1 种)。但是我不知道如何突出显示 JTable 组件中的单行 code line 1

使用不同类型的组件会更容易吗?

稍后我还需要能够为单个单元格重新着色,如模型的 Table JPanel 中所示。如何实现?

【问题讨论】:

  • 我可以在特定单元格上设置自定义渲染 - 不,这不是您需要的 :-) 相反,您需要一个自定义渲染器来决定其渲染的视觉效果组件基于传入getXXCellRendererComponent的参数,见fi docs.oracle.com/javase/tutorial/uiswing/components/table.html
  • 我明白了。所以我将自定义渲染器设置为所有单元格,然后在自定义渲染器方法中检查哪个单元格需要突出显示?我仍然不知道如何在自定义渲染器方法中检查我所在的单元格。
  • 我不明白你不明白的 ;-) 方法的参数告诉你所有你需要知道的。您确实阅读了我上面链接的教程,不是吗?
  • 如果我在 getTableCellRendererComponent 方法中执行条件语句 - if(column == 0 && row == 1) c.setBackground(new java.awt.Color(255, 72, 72)); 它仍然会将所有单元格涂成红色。

标签: java swing jtable jtextcomponent


【解决方案1】:

1) 使用JTextPane 支持样式文本,您有三种选择

  • 使用HighLighter

  • 使用 Html 格式化文本(Java6 当前形式支持 Html3.2 并且减少了对 css 的支持,肯定与 Html5 相比)

  • 将两个 a.m. 选项组合在一起

  • 编写自己的 EditorKit 或 HtmlEditorKit(感谢 @stryba)

2) 对于JTable,将所需的值传递给prepareRenderer(),而不是实现getTableCellRendererComponent()

3) 如果 JSlider 的值是可修改的(来自另一个 JComponents),则查找 BoundedRangeModel

【讨论】:

  • 只是在第 1 点上再添加一个可能)您还可以使用自己的View 创建自己的EditorKit,这是一项更多的工作,但通常优于其他选项
  • @stryba 感谢您的通知,嗯,所有与 EditorKit 或 HtmlEditorKit 相关的问题都在我们的(JTextComponent 之王 @StanislavL)那里,
  • -1 for 2)(是时候开始寻求反对传播不太正确的建议了 :-) 这不是在应用程序代码中实现视觉单元格装饰的一般方法,而是自定义渲染器。基本规则是:永远不要为应用程序需求扩展 JSomething,它们应该按原样使用。也就是说:使用附加功能扩展核心组件(在此上下文中添加 api 以允许自定义条带化)很好:这允许在所有应用程序中重用扩展组件而无需 进一步 扩展,它们可以根据需要配置自定义组件。
  • 这个答案和上面的评论让我有点困惑。我假设我应该在自定义类中扩展 JTable 并覆盖? prepareRenderer() 方法。我还应该承认,我对 Java Swing 的体验不是很好。
  • 1) 等待@kleopatra 的回复可能会更好,2) 这条评论是关于pass desired value 的,如果你知道的话,请确保她的诚实基本上是真实的,而且不仅仅是有价值的关于 Swing,3)我必须注意到,如果不使用 SSCCE 编辑您的问题,我无法回答您的问题,4)我将此问题仅作为面试,
【解决方案2】:

帮助您的小代码,如何在 JTextPane 上以所需背景突出显示特定文本文字:

import java.awt.*;

import java.awt.event.*;

import javax.swing.*;

import javax.swing.border.*;

import javax.swing.text.AttributeSet;
import javax.swing.text.SimpleAttributeSet;
import javax.swing.text.StyleConstants;
import javax.swing.text.StyleContext;

public class TextPaneTest extends JFrame
{
    private JPanel topPanel;
    private JTextPane tPane;

    public TextPaneTest()
    {
        topPanel = new JPanel();        

        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setLocationRelativeTo(null);            

        EmptyBorder eb = new EmptyBorder(new Insets(10, 10, 10, 10));

        tPane = new JTextPane();                
        tPane.setBorder(eb);
        //tPane.setBorder(BorderFactory.createLineBorder(Color.DARK_GRAY));
        tPane.setMargin(new Insets(5, 5, 5, 5));

        topPanel.add(tPane);

        appendToPane(tPane, "My Name is Too Good.\n", Color.RED, Color.YELLOW);
        appendToPane(tPane, "I wish I could be ONE of THE BEST on ", Color.BLUE, Color.WHITE);
        appendToPane(tPane, "Stack", Color.PINK, Color.WHITE);
        appendToPane(tPane, "Over", Color.YELLOW, Color.RED.brighter());
        appendToPane(tPane, "flow", Color.BLACK, Color.GREEN.darker());

        getContentPane().add(topPanel);

        pack();
        setVisible(true);   
    }

    private void appendToPane(JTextPane tp, String msg, Color c, Color bColor)
    {
        StyleContext sc = StyleContext.getDefaultStyleContext();
        AttributeSet aset = sc.addAttribute(SimpleAttributeSet.EMPTY, StyleConstants.Foreground, c);

        aset = sc.addAttribute(aset, StyleConstants.Background, bColor);
        //  aset = sc.addAttribute(SimpleAttributeSet.EMPTY, StyleConstants.Foreground, c);

        aset = sc.addAttribute(aset, StyleConstants.FontFamily, "Lucida Console");
        aset = sc.addAttribute(aset, StyleConstants.Alignment, StyleConstants.ALIGN_JUSTIFIED);

        int len = tp.getDocument().getLength();
        tp.setCaretPosition(len);
        tp.setCharacterAttributes(aset, false);
        tp.replaceSelection(msg);
    }

    public static void main(String... args)
    {
        SwingUtilities.invokeLater(new Runnable()
            {
                public void run()
                {
                    new TextPaneTest();
                }
            });
    }
}

这是输出:

【讨论】:

  • 感谢您的回答。虽然这解决了我在Calculations Area 中遇到的另一个问题,但它仍然没有解决我在为 JTable 单元格着色时遇到的问题。
  • @Ash : 啊……希望我能在JTable 上帮助你,但我对它们的了解太少了。我对此感到抱歉。但希望这个答案可以帮助你在你的努力中的某个地方,并希望你能很快找到你的答案:-)
猜你喜欢
  • 2013-10-25
  • 1970-01-01
  • 2018-11-06
  • 2012-01-27
  • 1970-01-01
  • 2016-02-15
  • 2011-10-03
  • 2012-08-06
  • 1970-01-01
相关资源
最近更新 更多