1
2
3
4
5
6
7
8
9
10
11 package com.jsql.view.swing.text;
12
13 import com.jsql.util.LogLevelUtil;
14 import com.jsql.view.swing.popupmenu.JPopupMenuText;
15 import com.jsql.view.swing.text.action.SilentDeleteTextAction;
16 import org.apache.logging.log4j.LogManager;
17 import org.apache.logging.log4j.Logger;
18
19 import javax.swing.*;
20 import javax.swing.text.DefaultEditorKit;
21 import javax.swing.text.JTextComponent;
22 import javax.swing.undo.CannotRedoException;
23 import javax.swing.undo.CannotUndoException;
24 import javax.swing.undo.CompoundEdit;
25 import javax.swing.undo.UndoManager;
26 import java.awt.event.ActionEvent;
27
28
29
30
31
32 public class JPopupTextComponent<T extends JTextComponent> extends JPopupComponent<T> implements DecoratorJComponent<T> {
33
34 private static final Logger LOGGER = LogManager.getRootLogger();
35
36
37
38
39
40 public JPopupTextComponent(final T proxy) {
41 super(proxy);
42
43 this.getProxy().setComponentPopupMenu(new JPopupMenuText(this.getProxy()));
44 this.getProxy().setDragEnabled(true);
45
46 var undoRedoManager = new UndoManager();
47
48
49 final CompoundEdit[] currentEdit = {new CompoundEdit()};
50 Timer commitTimer = new Timer(500, e -> {
51 currentEdit[0].end();
52 undoRedoManager.addEdit(currentEdit[0]);
53 currentEdit[0] = new CompoundEdit();
54 });
55 commitTimer.setRepeats(false);
56
57
58 var doc = this.getProxy().getDocument();
59 doc.addUndoableEditListener(e -> {
60 currentEdit[0].addEdit(e.getEdit());
61 commitTimer.restart();
62 });
63
64 this.initUndo(undoRedoManager);
65 this.initRedo(undoRedoManager);
66 this.makeDeleteSilent();
67 }
68
69 private void initUndo(final UndoManager undo) {
70 final var undoIdentifier = "Undo";
71
72 this.getProxy().getActionMap().put(undoIdentifier, new AbstractAction(undoIdentifier) {
73 @Override
74 public void actionPerformed(ActionEvent evt) {
75
76 try {
77 if (undo.canUndo()) {
78 undo.undo();
79 }
80 } catch (ArrayIndexOutOfBoundsException | CannotUndoException e) {
81 LOGGER.log(LogLevelUtil.CONSOLE_JAVA, e, e);
82 }
83 }
84 });
85
86
87 this.getProxy().getInputMap().put(KeyStroke.getKeyStroke("control Z"), undoIdentifier);
88 }
89
90 private void initRedo(final UndoManager undo) {
91 final var redoIdentifier = "Redo";
92
93 this.getProxy().getActionMap().put(redoIdentifier, new AbstractAction(redoIdentifier) {
94 @Override
95 public void actionPerformed(ActionEvent evt) {
96 try {
97 if (undo.canRedo()) {
98 undo.redo();
99 }
100 } catch (CannotRedoException e) {
101 LOGGER.log(LogLevelUtil.CONSOLE_JAVA, e, e);
102 }
103 }
104 });
105
106
107 this.getProxy().getInputMap().put(KeyStroke.getKeyStroke("control Y"), redoIdentifier);
108 }
109
110 private void makeDeleteSilent() {
111 var actionMap = this.getProxy().getActionMap();
112
113 String key = DefaultEditorKit.deletePrevCharAction;
114 actionMap.put(key, new SilentDeleteTextAction(key, actionMap.get(key)));
115
116 key = DefaultEditorKit.deleteNextCharAction;
117 actionMap.put(key, new SilentDeleteTextAction(key, actionMap.get(key)));
118 }
119 }