首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何使用alternation匹配正则表达式中的最长匹配?

如何使用alternation匹配正则表达式中的最长匹配?
EN

Stack Overflow用户
提问于 2016-02-02 18:36:34
回答 2查看 173关注 0票数 0

我是用Java语言开发的,我正在努力寻找一种智能的解决方案,以便即使在使用JLabel的多行文本时也能正确地将前景色设置为html。

我知道Swing在将前景设置为html文本时遇到了问题。我想使用正则表达式来发现label的文本是否为html格式,如果是,则向其添加一个font标签。问题是为了让它正常工作,我必须在方法的末尾调用setText()。为了避免StackOverflowException,必须采取一些措施。这就是我想要的正则表达式:<html>(<font [^>]*>)?((.*)(<\\/font><\\/html>)|(.*)<\\/html>)

因此,在覆盖JLabel的类中,我覆盖了JLabel.getText()方法:

代码语言:javascript
复制
@Override
public String getText()
  {
  String superText = super.getText();
  if (superText == null)
    return superText;
  Matcher m = pattern.matcher(superText);
  if (m.matches())
    {
    String text = "<html><font color=\""+retrieveHexColor()+"\">"+TempUtils.nvl(m.group(5), m.group(3))+"</font></html>";
    if (superText.equals(text))
      return superText;
    superText = text;
    }
  setText(superText);
  return superText;
  }

那么TempUtils.nvl就只是

代码语言:javascript
复制
public static <T> T nvl(T value, T defaultValue)
  {
  return value == null ? defaultValue : value;
  }

我不太喜欢这个解决方案。你能帮帮我吗?我想,如果我能在(<\\/font><\\/html>)(.*)<\\/html>)之间找到最长的匹配,我就可以很容易地解决我的问题。

编辑:我被要求编写一些代码来测试我所说的话:

代码语言:javascript
复制
public static void main(String[] args)
    {
    final JPanel panel = new JPanel(new BorderLayout());

    JLabel overriddenLabel = new JLabel("<html>aBc<br>deEEEF</html>", JLabel.CENTER) {

    Color foreground = Color.cyan;
        {
        addMouseListener(new MouseAdapter() {
            @Override
            public void mouseEntered(MouseEvent e)
            {
            foreground = Color.black;
            repaint();
            }
            @Override
            public void mouseExited(MouseEvent e)
            {
            foreground = Color.cyan;
            repaint();
            }
        });
        }
    @Override
        public Color getForeground()
            {
            return foreground;
            }

        };
    JFrame frame = new JFrame("AD");
    panel.add(overriddenLabel);
    frame.setContentPane(panel);
    frame.setVisible(true);
    frame.setSize(new Dimension(300,300));
    }

正如您所看到的,设置非html文本可以使其正常工作。

EDIT2:吃完午饭回来了。我的解决方案与此类似。它能工作,但我不喜欢它。

代码语言:javascript
复制
public static void main(String[] args)
    {
    final JPanel panel = new JPanel(new BorderLayout());

    JLabel overriddenLabel = new JLabel("<html>aBc<br>deEEEF</html>", JLabel.CENTER) {

        Color foreground = Color.cyan;
            {
            addMouseListener(new MouseAdapter() {
                @Override
                public void mouseEntered(MouseEvent e)
                {
                foreground = Color.black;
                repaint();
                }
                @Override
                public void mouseExited(MouseEvent e)
                {
                foreground = Color.cyan;
                repaint();
                }
            });
            }
        @Override
        public Color getForeground()
            {
            return foreground;
            }


        public String colorToHex(Color color)
            {
            if (color == null)
                return null;
            String hexColor = Integer.toHexString(color.getRGB() & 0xffffff);
            if (hexColor.length() < 6)
                hexColor = "000000".substring(0, 6 - hexColor.length()) + hexColor;
            return "#"+hexColor;
            }

        @Override
        public String getText()
            {
            Pattern pattern = Pattern.compile("<html>(<font [^>]*>)?((.*)(<\\/font><\\/html>)|(.*)<\\/html>)");
            String superText = super.getText();
            if (superText == null)
                return superText;
            Matcher m = pattern.matcher(superText);
            if (m.matches())
                {
                String text = "<html><font color=\""+colorToHex(foreground)+"\">"+(m.group(5) == null ? m.group(3) : m.group(5))+"</font></html>";
                if (superText.equals(text))
                    return superText;
                superText = text;
                }
            setText(superText);
            return superText;
            }

        };
    JFrame frame = new JFrame("AD");
    panel.add(overriddenLabel);
    frame.setContentPane(panel);
    frame.setVisible(true);
    frame.setSize(new Dimension(300,300));
    }
EN

回答 2

Stack Overflow用户

发布于 2016-02-03 04:33:52

可行的解决方案,无需使用regexp。

代码语言:javascript
复制
public static void main(String[] args) {
    final JPanel panel = new JPanel(new BorderLayout());

    JLabel overriddenLabel = new JLabel("<html>aBc<br>deEEEF</html>", JLabel.CENTER) {

        Color foreground = Color.cyan;

        {
            addMouseListener(new MouseAdapter() {
                @Override
                public void mouseEntered(MouseEvent e) {
                    setForeground(Color.black);
                    repaint();
                }

                @Override
                public void mouseExited(MouseEvent e) {
                    setForeground(Color.cyan);
                    repaint();
                }
            });
        }
    };
    overriddenLabel.setForeground(Color.cyan);
    JFrame frame = new JFrame("AD");
    panel.add(overriddenLabel);
    frame.setContentPane(panel);
    frame.setVisible(true);
    frame.setSize(new Dimension(300, 300));
}

我不知道您为什么要覆盖getForeground,您并没有对它做任何特殊的事情

票数 1
EN

Stack Overflow用户

发布于 2016-02-03 00:57:21

我终于为我的问题找到了正确的正则表达式。如果有人需要它,它就在这里:

<html>(<[^>]*>)*(([^<]*)(<\/?br\/?>)?[^<]*)(<\/[^>]*>)*<\/html>

谢谢。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35151080

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档