I'm making my own script editor (in this case for Arma: Cold War Assault
) because I want to learn and this is challenging enough.
Let me just get this out of the way: please don't tell me that I should do easier things. I want to do this anyway.
So, basically I have the simple GUI for now with a working new/open/save file menu.
I've managed to highlight certain words with different colors (because I want to tackle the hardest part first) but it's not efficient.
I've come up with several ideas for the algorithm (didn't implement them all), but I want to know what you'do, if there's a certain way and what I am doing wrong.
This all happens inside a JTextPane
class.
The arrays containing the reserved words:
Collections.addAll(keywords, "private", "public", "if", "not", "then", "else", "else if");
Collections.addAll(operators, "+", "-", "=", "==", "?", "!","(", ")","{", "}", "_", "-", "^", "<", ">");
ArrayList<String> keywords = new ArrayList<String>();
ArrayList<String> operators = new ArrayList<String>();
Everytime the user makes an update to the document, it get's updated:
@Override
public void insertUpdate(DocumentEvent e) {
update();
}
@Override
public void removeUpdate(DocumentEvent e) {
update();
}
When the user stops typing, it waits 500 ms to update the screen:
Timer t;
/**
* Updates the text when user stops typing
*/
public void update(){
if (t != null) {
if (t.isRunning())
t.stop();
}
t = new Timer(250, new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
long start = System.currentTimeMillis();
String text = getText();
SimpleAttributeSet attrs = new SimpleAttributeSet();
StyleConstants.setForeground(attrs, Color.BLACK);
StyledDocument doc = getStyledDocument();
doc.setCharacterAttributes(0, text.length(), attrs, true);
int index = 0, carriage = 0;
while ((index < text.length())) {
if (text.codePointAt(index) == 10) {
carriage += 1;
}
for (String s : Keywords.listKeywords()) {
if (text.startsWith(s, index)){
changeColor(doc, reserved.get(s), index, carriage, s.length(), false);
index += s.length();
break;
}
}
for (String s : Keywords.listOperators()) {
if (text.startsWith(s, index)){
changeColor(doc, reserved.get(s), index, carriage, s.length(), false);
index += s.length();
break;
}
}
index++;
}
wordCount.setText("word count: " + index);
System.out.println("Iterations took: "
+ (System.currentTimeMillis() - start) + " ms");
t.stop();
}
});
t.start();
}
private void changeColor(StyledDocument doc, Color color, int index, int carriage, int length, boolean replace) {
SimpleAttributeSet attrs = new SimpleAttributeSet();
StyleConstants.setForeground(attrs, color);
doc.setCharacterAttributes(index - carriage, length, attrs, replace);
}
How would I go about doing this more efficiently?
As of right now, with almost 145.000 words i have a delay of about 400 ms with 12 keywords and other words.