JPopupTextComponent.java

1
/*******************************************************************************
2
 * Copyhacked (H) 2012-2020.
3
 * This program and the accompanying materials
4
 * are made available under no term at all, use it like
5
 * you want, but share and discuss about it
6
 * every time possible with every body.
7
 *
8
 * Contributors:
9
 *      ron190 at ymail dot com - initial implementation
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.UndoManager;
25
import java.awt.event.ActionEvent;
26
27
/**
28
 * A swing JTextComponent with Undo/Redo functionality.
29
 * @param <T> Component like JTextField or JTextArea to decorate
30
 */
31
public class JPopupTextComponent<T extends JTextComponent> extends JPopupComponent<T> implements DecoratorJComponent<T> {
32
    
33
    /**
34
     * Log4j logger sent to view.
35
     */
36
    private static final Logger LOGGER = LogManager.getRootLogger();
37
38
    /**
39
     * Save the component to decorate, add the Undo/Redo.
40
     * @param proxy Swing component to decorate
41
     */
42
    public JPopupTextComponent(final T proxy) {
43
        
44
        super(proxy);
45
46 1 1. <init> : removed call to javax/swing/text/JTextComponent::setComponentPopupMenu → NO_COVERAGE
        this.getProxy().setComponentPopupMenu(new JPopupMenuText(this.getProxy()));
47 1 1. <init> : removed call to javax/swing/text/JTextComponent::setDragEnabled → NO_COVERAGE
        this.getProxy().setDragEnabled(true);
48
49
        var undoRedoManager = new UndoManager();
50
        var doc = this.getProxy().getDocument();
51
52
        // Listen for undo and redo events
53 1 1. <init> : removed call to javax/swing/text/Document::addUndoableEditListener → NO_COVERAGE
        doc.addUndoableEditListener(undoableEditEvent -> undoRedoManager.addEdit(undoableEditEvent.getEdit()));
54
55 1 1. <init> : removed call to com/jsql/view/swing/text/JPopupTextComponent::initializeUndo → NO_COVERAGE
        this.initializeUndo(undoRedoManager);
56 1 1. <init> : removed call to com/jsql/view/swing/text/JPopupTextComponent::initializeRedo → NO_COVERAGE
        this.initializeRedo(undoRedoManager);
57 1 1. <init> : removed call to com/jsql/view/swing/text/JPopupTextComponent::makeDeleteSilent → NO_COVERAGE
        this.makeDeleteSilent();
58
    }
59
60
    private void initializeUndo(final UndoManager undo) {
61
        
62
        final var undoIdentifier = "Undo";  // Create an undo action and add it to the text component
63
        
64 1 1. initializeUndo : removed call to javax/swing/ActionMap::put → NO_COVERAGE
        this.getProxy().getActionMap().put(undoIdentifier, new AbstractAction(undoIdentifier) {
65
            @Override
66
            public void actionPerformed(ActionEvent evt) {
67
                // Unhandled ArrayIndexOutOfBoundsException #92146 on undo()
68
                try {
69 1 1. actionPerformed : negated conditional → NO_COVERAGE
                    if (undo.canUndo()) {
70 1 1. actionPerformed : removed call to javax/swing/undo/UndoManager::undo → NO_COVERAGE
                        undo.undo();
71
                    }
72
                } catch (ArrayIndexOutOfBoundsException | CannotUndoException e) {
73
                    LOGGER.log(LogLevelUtil.CONSOLE_JAVA, e, e);
74
                }
75
            }
76
       });
77
78
        // Bind the undo action to ctl-Z
79 1 1. initializeUndo : removed call to javax/swing/InputMap::put → NO_COVERAGE
        this.getProxy().getInputMap().put(KeyStroke.getKeyStroke("control Z"), undoIdentifier);
80
    }
81
82
    private void initializeRedo(final UndoManager undo) {
83
        
84
        final var redoIdentifier = "Redo";  // Create a redo action and add it to the text component
85
        
86 1 1. initializeRedo : removed call to javax/swing/ActionMap::put → NO_COVERAGE
        this.getProxy().getActionMap().put(redoIdentifier, new AbstractAction(redoIdentifier) {
87
            @Override
88
            public void actionPerformed(ActionEvent evt) {
89
                try {
90 1 1. actionPerformed : negated conditional → NO_COVERAGE
                    if (undo.canRedo()) {
91 1 1. actionPerformed : removed call to javax/swing/undo/UndoManager::redo → NO_COVERAGE
                        undo.redo();
92
                    }
93
                } catch (CannotRedoException e) {
94
                    LOGGER.log(LogLevelUtil.CONSOLE_JAVA, e, e);
95
                }
96
            }
97
        });
98
99
        // Bind the redo action to ctl-Y
100 1 1. initializeRedo : removed call to javax/swing/InputMap::put → NO_COVERAGE
        this.getProxy().getInputMap().put(KeyStroke.getKeyStroke("control Y"), redoIdentifier);
101
    }
102
103
    private void makeDeleteSilent() {
104
        
105
        var actionMap = this.getProxy().getActionMap();  // Silent delete
106
107
        String key = DefaultEditorKit.deletePrevCharAction;
108 1 1. makeDeleteSilent : removed call to javax/swing/ActionMap::put → NO_COVERAGE
        actionMap.put(key, new SilentDeleteTextAction(key, actionMap.get(key)));
109
110
        key = DefaultEditorKit.deleteNextCharAction;
111 1 1. makeDeleteSilent : removed call to javax/swing/ActionMap::put → NO_COVERAGE
        actionMap.put(key, new SilentDeleteTextAction(key, actionMap.get(key)));
112
    }
113
}

Mutations

46

1.1
Location : <init>
Killed by : none
removed call to javax/swing/text/JTextComponent::setComponentPopupMenu → NO_COVERAGE

47

1.1
Location : <init>
Killed by : none
removed call to javax/swing/text/JTextComponent::setDragEnabled → NO_COVERAGE

53

1.1
Location : <init>
Killed by : none
removed call to javax/swing/text/Document::addUndoableEditListener → NO_COVERAGE

55

1.1
Location : <init>
Killed by : none
removed call to com/jsql/view/swing/text/JPopupTextComponent::initializeUndo → NO_COVERAGE

56

1.1
Location : <init>
Killed by : none
removed call to com/jsql/view/swing/text/JPopupTextComponent::initializeRedo → NO_COVERAGE

57

1.1
Location : <init>
Killed by : none
removed call to com/jsql/view/swing/text/JPopupTextComponent::makeDeleteSilent → NO_COVERAGE

64

1.1
Location : initializeUndo
Killed by : none
removed call to javax/swing/ActionMap::put → NO_COVERAGE

69

1.1
Location : actionPerformed
Killed by : none
negated conditional → NO_COVERAGE

70

1.1
Location : actionPerformed
Killed by : none
removed call to javax/swing/undo/UndoManager::undo → NO_COVERAGE

79

1.1
Location : initializeUndo
Killed by : none
removed call to javax/swing/InputMap::put → NO_COVERAGE

86

1.1
Location : initializeRedo
Killed by : none
removed call to javax/swing/ActionMap::put → NO_COVERAGE

90

1.1
Location : actionPerformed
Killed by : none
negated conditional → NO_COVERAGE

91

1.1
Location : actionPerformed
Killed by : none
removed call to javax/swing/undo/UndoManager::redo → NO_COVERAGE

100

1.1
Location : initializeRedo
Killed by : none
removed call to javax/swing/InputMap::put → NO_COVERAGE

108

1.1
Location : makeDeleteSilent
Killed by : none
removed call to javax/swing/ActionMap::put → NO_COVERAGE

111

1.1
Location : makeDeleteSilent
Killed by : none
removed call to javax/swing/ActionMap::put → NO_COVERAGE

Active mutators

Tests examined


Report generated by PIT 1.16.1