/*
* Copyright (c) 2010-2016, Sikuli.org, sikulix.com
* Released under the MIT License.
*
*/
package org.sikuli.ide;
import java.awt.*;
import javax.swing.JTextPane;
import javax.swing.event.CaretEvent;
import javax.swing.event.CaretListener;
import javax.swing.text.*;
import org.sikuli.basics.Debug;
public class EditorCurrentLineHighlighter implements CaretListener {
private static final String me = "EditorCurrentLineHighlighter: ";
static final Color DEFAULT_COLOR = new Color(230, 230, 210);
static final Color ERROR_COLOR = new Color(255, 105, 105);
private Highlighter.HighlightPainter painter;
private Object highlight = null;
public EditorCurrentLineHighlighter(JTextPane textPane) {
this(textPane, null);
}
public EditorCurrentLineHighlighter(JTextPane textPane, Color highlightColor) {
Color c = highlightColor != null ? highlightColor : DEFAULT_COLOR;
MyHighlighter h = new MyHighlighter();
textPane.setHighlighter(h);
painter = new DefaultHighlighter.DefaultHighlightPainter(c);
}
@Override
public void caretUpdate(CaretEvent evt) {
JTextComponent comp = (JTextComponent) evt.getSource();
if (comp != null) {
if (comp.getSelectionStart() != comp.getSelectionEnd()) {
// cancel line highlighting if selection exists
removeLineHighlight(comp);
comp.repaint();
return;
}
int pos = comp.getCaretPosition();
Element elem = Utilities.getParagraphElement(comp, pos);
int start = elem.getStartOffset();
int end = elem.getEndOffset();
Document doc = comp.getDocument();
Element root = doc.getDefaultRootElement();
int line = root.getElementIndex(pos);
Debug.log(5, "LineHighlight: Caret at " + pos + " line " + line + " for " + start + "-" + end);
if (SikuliIDE.getStatusbar() != null) {
SikuliIDE.getStatusbar().setCaretPosition(line + 1, pos - start + 1);
}
removeLineHighlight(comp);
try {
highlight = comp.getHighlighter().addHighlight(start, end, painter);
comp.repaint();
} catch (BadLocationException ex) {
Debug.error(me + "Problem while highlighting line %d\n%s", pos, ex.getMessage());
}
}
}
private void removeLineHighlight(JTextComponent comp) {
if (highlight != null) {
comp.getHighlighter().removeHighlight(highlight);
highlight = null;
}
}
}
//<editor-fold defaultstate="collapsed" desc="class MyHighlighter extends DefaultHighlighter">
class MyHighlighter extends DefaultHighlighter {
private JTextComponent component;
private Rectangle a = null;
@Override
public final void install(final JTextComponent c) {
super.install(c);
this.component = c;
}
@Override
public final void deinstall(final JTextComponent c) {
super.deinstall(c);
this.component = null;
}
@Override
public final void paint(final Graphics g) {
final Highlighter.Highlight[] highlights = getHighlights();
final int len = highlights.length;
if (len == 0) {
return;
}
if (highlights[0].getClass().getName().indexOf("LayeredHighlightInfo") > -1) {
Debug.log(6, "LineHighlight: painting enter for " + len);
a = this.component.getBounds();
final Insets insets = this.component.getInsets();
a.x = insets.left;
Debug.log(6, "LineHighlight: painting 0");
highlights[0].getPainter().paint(g,
highlights[0].getStartOffset(), highlights[0].getEndOffset(), a, this.component);
}
for (int i = 1; i < len; i++) {
if (highlights[i].getClass().getName().indexOf("LayeredHighlightInfo") > -1) {
Debug.log(6, "LineHighlight: painting " + i);
highlights[i].getPainter().paint(g,
highlights[i].getStartOffset(), highlights[i].getEndOffset(), a, this.component);
}
}
}
}
//</editor-fold>