This code highlights all instances of keywords in a JTextPane. I don't think it is very CPU efficient (it has three loops per LINE) It splits all the lines, creates a Matcher for each keyword, and iterates through those, which consequently means slow execution with larger files. The thread is called every time a key is released. This is the code:

private final Thread highlighter = new Thread() {

		@Override
		public void run() {
			final String text = editor.getText();
			final StyledDocument doc = editor.getStyledDocument();
			final String[] lines = text.split("\n");
			int offset = 0;
			doc.setCharacterAttributes(0, text.length(),
					Constants.getDefaultStyle(), true);
			for (final String line : lines) {
				for (final String keyword : Tools.KEYWORDS) {
					final int length = keyword.length();
					final Matcher m = Pattern.compile(keyword).matcher(line);
					while (m.find()) {
						doc.setCharacterAttributes(offset + m.start(), length,
								Constants.getKeywordsStyle(), true);
					}
				}
				offset += line.length();
			}
		}

	};

I was thinking of getting the line only that the caret is on, and do the above code only for when the user pastes text. Would that be a more efficient way?

P.S: When the user types a keyword, presses the delete (look below), the default style is the same as the keyword style, and I can't seem to stop this.

keyword |

**Backspace**

keyword|

**Starts typing again**

keyword non|

until the user presses space, then the statement of

doc.setCharacterAttributes(0, text.length(),
					Constants.getDefaultStyle(), true);

clears it.

It does sound inefficient. If I'm typing in the entire text of Huck Finn and my keywords are "Huck" and "Jim" and I'm already on page 200 and I press a key, it doesn't make sense to parse 200 pages of text that I've already parsed (let's see 80 characters per line, 50 lines per page, 200 pages = 800,000. Anyone want to check my arithmetic?) 800,000 times. I've already found all the keywords on page 123 already.


>> I was thinking of getting the line only that the caret is on, and do the above code only for when the user pastes text. Would that be a more efficient way?

Sounds like a good idea to me! However, consider the fact that I still want all my keywords highlighted, I just don't want to bother having to parse them again, so make sure that when you start typing on a new line that all the old highlighted keywords don't disappear. I'm not assuming that they will or won't, just check to make sure.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.