├── .project
├── ChangeRecorder
├── .classpath
├── .gitignore
├── .project
├── .settings
│ └── org.eclipse.jdt.core.prefs
├── META-INF
│ └── MANIFEST.MF
├── build.properties
├── icons
│ └── jcu_obj.gif
├── lib
│ └── commons-io-2.4.jar
├── plugin.xml
└── src
│ └── org
│ └── jtool
│ └── changerecorder
│ ├── Activator.java
│ ├── diff
│ ├── CodeDelta.java
│ ├── DiffOperationGenerator.java
│ └── diff_match_patch.java
│ ├── editor
│ ├── ConsoleOperationListener.java
│ ├── HistoryManager.java
│ └── JCompilationUnitEditor.java
│ ├── event
│ ├── OperationEvent.java
│ ├── OperationEventListener.java
│ └── OperationEventSource.java
│ ├── history
│ ├── CodeRestorer.java
│ ├── Operation2Xml.java
│ ├── OperationHistory.java
│ ├── Xml2Operation.java
│ └── XmlConstantStrings.java
│ ├── operation
│ ├── AbstractOperation.java
│ ├── CompoundOperation.java
│ ├── CopyOperation.java
│ ├── FileOperation.java
│ ├── IOperation.java
│ ├── MenuOperation.java
│ ├── NormalOperation.java
│ ├── NullOperation.java
│ ├── ResourceOperation.java
│ └── TextOperation.java
│ └── util
│ ├── FileStream.java
│ ├── StringComparator.java
│ ├── Time.java
│ ├── Whoami.java
│ └── XmlFileStream.java
├── LICENSE
├── MacroRecorder
├── .classpath
├── .gitignore
├── .project
├── .settings
│ └── org.eclipse.jdt.core.prefs
├── META-INF
│ └── MANIFEST.MF
├── build.properties
└── src
│ └── org
│ └── jtool
│ └── macrorecorder
│ ├── Activator.java
│ ├── internal
│ ├── diff
│ │ ├── CodeDelta.java
│ │ ├── DiffMacroGenerator.java
│ │ └── diff_match_patch.java
│ └── recorder
│ │ ├── CommandExecutionManager.java
│ │ ├── DocMacroRecorder.java
│ │ ├── DocMacroRecorderOffEdit.java
│ │ ├── DocMacroRecorderOnEdit.java
│ │ ├── DocumentManager.java
│ │ ├── MenuMacroRecorder.java
│ │ ├── RefactoringExecutionManager.java
│ │ ├── ResourceChangedManager.java
│ │ └── Time.java
│ ├── macro
│ ├── CancelMacro.java
│ ├── CompoundMacro.java
│ ├── CopyMacro.java
│ ├── DiffMacro.java
│ ├── DocumentMacro.java
│ ├── ExecutionMacro.java
│ ├── Macro.java
│ ├── ResourceMacro.java
│ └── TriggerMacro.java
│ ├── recorder
│ ├── MacroCompressor.java
│ ├── MacroEvent.java
│ ├── MacroListener.java
│ └── Recorder.java
│ └── util
│ ├── EditorUtilities.java
│ └── WorkspaceUtilities.java
├── README.md
├── RemoteSystemsTempFiles
└── .project
├── compare.png
├── jp.ac.ritsumei.cs.fse.contentassist
├── .classpath
├── .project
├── .settings
│ └── org.eclipse.jdt.core.prefs
├── META-INF
│ └── MANIFEST.MF
├── bin
│ ├── .gitignore
│ └── jp
│ │ └── ac
│ │ └── ritsumei
│ │ └── cs
│ │ └── fse
│ │ └── contentassist
│ │ ├── Activator.class
│ │ ├── DataAnalyser
│ │ ├── ConsoleOperationListener2.class
│ │ ├── DataManager.class
│ │ ├── HistoryRecorder.class
│ │ └── getProposalResult.class
│ │ ├── View
│ │ └── JavaCompletionProposalComputer1.class
│ │ └── entity
│ │ └── ApplyOperation.class
├── build.properties
├── plugin.xml
└── src
│ └── jp
│ └── ac
│ └── ritsumei
│ └── cs
│ └── fse
│ └── contentassist
│ ├── Activator.java
│ ├── DataAnalyser
│ ├── ConsoleOperationListener2.java
│ ├── DataManager.java
│ ├── HistoryRecorder.java
│ └── getProposalResult.java
│ ├── View
│ └── JavaCompletionProposalComputer1.java
│ └── entity
│ └── ApplyOperation.java
├── structure.png
└── 編集履歴から算出した開発者の関心度に基づくコード補完.pdf
/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | ContentAssist
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/ChangeRecorder/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/ChangeRecorder/.gitignore:
--------------------------------------------------------------------------------
1 | /bin
2 |
--------------------------------------------------------------------------------
/ChangeRecorder/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | ChangeRecorder
4 |
5 |
6 |
7 |
8 |
9 | org.eclipse.jdt.core.javabuilder
10 |
11 |
12 |
13 |
14 | org.eclipse.pde.ManifestBuilder
15 |
16 |
17 |
18 |
19 | org.eclipse.pde.SchemaBuilder
20 |
21 |
22 |
23 |
24 |
25 | org.eclipse.pde.PluginNature
26 | org.eclipse.jdt.core.javanature
27 |
28 |
29 |
--------------------------------------------------------------------------------
/ChangeRecorder/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
4 | org.eclipse.jdt.core.compiler.compliance=1.7
5 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
6 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
7 | org.eclipse.jdt.core.compiler.source=1.7
8 |
--------------------------------------------------------------------------------
/ChangeRecorder/META-INF/MANIFEST.MF:
--------------------------------------------------------------------------------
1 | Manifest-Version: 1.0
2 | Bundle-ManifestVersion: 2
3 | Bundle-Name: ChangeRecorder
4 | Bundle-SymbolicName: ChangeRecorder;singleton:=true
5 | Bundle-Version: 1.0.0.qualifier
6 | Bundle-Activator: org.jtool.changerecorder.Activator
7 | Require-Bundle: org.eclipse.ui;bundle-version="3.106.0",
8 | org.eclipse.core.runtime;bundle-version="3.10.0",
9 | org.eclipse.core.resources;bundle-version="3.9.1",
10 | org.eclipse.ui.ide;bundle-version="3.10.1",
11 | org.eclipse.ui.editors;bundle-version="3.8.200",
12 | org.eclipse.jface.text;bundle-version="3.9.1",
13 | org.eclipse.jdt.ui;bundle-version="3.10.1",
14 | org.eclipse.jdt.core;bundle-version="3.10.0",
15 | org.eclipse.ltk.core.refactoring;bundle-version="3.6.101",
16 | MacroRecorder;bundle-version="1.0.0"
17 | Bundle-RequiredExecutionEnvironment: JavaSE-1.8
18 | Bundle-ActivationPolicy: lazy
19 | Bundle-ClassPath: .,
20 | lib/commons-io-2.4.jar
21 | Export-Package: org.jtool.changerecorder.diff,
22 | org.jtool.changerecorder.editor,
23 | org.jtool.changerecorder.event,
24 | org.jtool.changerecorder.history,
25 | org.jtool.changerecorder.operation,
26 | org.jtool.changerecorder.util
27 |
--------------------------------------------------------------------------------
/ChangeRecorder/build.properties:
--------------------------------------------------------------------------------
1 | output.. = bin/
2 | bin.includes = META-INF/,\
3 | plugin.xml,\
4 | .,\
5 | lib/commons-io-2.4.jar
6 | source.. = src/
7 | jre.compilation.profile = JavaSE-1.7
8 |
9 |
--------------------------------------------------------------------------------
/ChangeRecorder/icons/jcu_obj.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/ChangeRecorder/icons/jcu_obj.gif
--------------------------------------------------------------------------------
/ChangeRecorder/lib/commons-io-2.4.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/ChangeRecorder/lib/commons-io-2.4.jar
--------------------------------------------------------------------------------
/ChangeRecorder/plugin.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
6 |
8 |
9 |
10 |
12 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/Activator.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder;
8 |
9 | import org.jtool.changerecorder.editor.HistoryManager;
10 | import org.eclipse.core.resources.IWorkspace;
11 | import org.eclipse.core.resources.IWorkspaceRoot;
12 | import org.eclipse.core.resources.ResourcesPlugin;
13 | import org.eclipse.core.runtime.IPath;
14 | import org.eclipse.ui.IStartup;
15 | import org.eclipse.ui.plugin.AbstractUIPlugin;
16 | import org.osgi.framework.BundleContext;
17 |
18 | import java.io.File;
19 |
20 | /**
21 | * The activator class that manages plug-in information.
22 | * @author Katsuhisa Maruyama
23 | */
24 | public class Activator extends AbstractUIPlugin implements IStartup {
25 |
26 | /**
27 | * The plug-in ID.
28 | */
29 | public static final String PLUGIN_ID = "ChangeRecorder";
30 |
31 | /**
32 | * The plug-in instance.
33 | */
34 | private static Activator plugin;
35 |
36 | /**
37 | * The top directory that stores history files.
38 | */
39 | public static String DEFAULT_HISTORY_TOPDIR = File.separator + "#history";
40 |
41 | /**
42 | * Creates a plug-in instance.
43 | */
44 | public Activator() {
45 |
46 | }
47 |
48 | /**
49 | * Performs actions when the plug-in is activated.
50 | * @param context the bundle context for this plug-in
51 | * @throws Exception if this plug-in did not start up properly
52 | */
53 | @Override
54 | public void start(BundleContext context) throws Exception {
55 | super.start(context);
56 | plugin = this;
57 |
58 | HistoryManager.getInstance().start();
59 |
60 | System.out.println(PLUGIN_ID + " activated.");
61 | }
62 |
63 | /**
64 | * Performs actions when when the plug-in is shut down.
65 | * @param context the bundle context for this plug-in
66 | * @throws Exception if this this plug-in fails to stop
67 | */
68 | @Override
69 | public void stop(BundleContext context) throws Exception {
70 | HistoryManager.getInstance().stop();
71 |
72 | super.stop(context);
73 | plugin = null;
74 | }
75 |
76 | /**
77 | * Will be called in a separate thread after the workbench initializes.
78 | */
79 | @Override
80 | public void earlyStartup() {
81 | }
82 |
83 | /**
84 | * Returns the default plug-in instance.
85 | * @return the default plug-in instance
86 | */
87 | public static Activator getPlugin() {
88 | return plugin;
89 | }
90 |
91 | /**
92 | * Obtains the workspace.
93 | * @return the workspace information
94 | */
95 | public IWorkspace getWorkspace() {
96 | return ResourcesPlugin.getWorkspace();
97 | }
98 |
99 | /**
100 | * Returns the directory path of the plug-in's workspace, which contains operation history.
101 | * @return the the directory into which the operation history is stored
102 | */
103 | public String getOperationHistoryDirPath() {
104 | IWorkspaceRoot workspaceRoot = ResourcesPlugin.getWorkspace().getRoot();
105 | IPath workspaceDir = workspaceRoot.getLocation();
106 | return workspaceDir.append(Activator.DEFAULT_HISTORY_TOPDIR).toString();
107 | }
108 | }
109 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/diff/CodeDelta.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.diff;
8 |
9 | /**
10 | * Manages the delta of code (the difference between two source files).
11 | * @author Katsuhisa Maruyama
12 | */
13 | class CodeDelta {
14 |
15 | /**
16 | * The type of code change operation.
17 | */
18 | enum Type {
19 | DELETE, INSERT, NULL
20 | }
21 |
22 | /**
23 | * The offset value of the text that contains this code delta.
24 | */
25 | private int offset;
26 |
27 | /**
28 | * The type of this code delta.
29 | */
30 | private Type type;
31 |
32 | /**
33 | * The text of the code delta.
34 | */
35 | private String text;
36 |
37 | /**
38 | * Creates an instance that stores information on change.
39 | * @param offset the offset value of the location where the change was applied
40 | * @param type the type of the change
41 | * @param text
42 | */
43 | CodeDelta(int offset, Type type, String text) {
44 | this.offset = offset;
45 | this.type = type;
46 | this.text = text;
47 | }
48 |
49 | /**
50 | * Returns the offset value of the text that indicates the start point of the change.
51 | * @return the offset value for the change
52 | */
53 | int getOffset() {
54 | return offset;
55 | }
56 |
57 | /**
58 | * Returns the type of the change.
59 | * @return the code change type
60 | */
61 | Type getType() {
62 | return type;
63 | }
64 |
65 | /**
66 | * Returns the text that was inserted or deleted by the change.
67 | * @return the changed text
68 | */
69 | String getText() {
70 | return text;
71 | }
72 |
73 | /**
74 | * Returns the string for printing
75 | * @return the string information
76 | */
77 | public String toString() {
78 | return "-- Delta [" + String.valueOf(offset) + "] "+ type + " (" + text + ")";
79 | }
80 | }
81 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/diff/DiffOperationGenerator.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.diff;
8 |
9 | import org.jtool.changerecorder.diff.diff_match_patch.Diff;
10 | import org.jtool.changerecorder.diff.diff_match_patch.Operation;
11 | import org.jtool.changerecorder.operation.NormalOperation;
12 | import java.util.ArrayList;
13 | import java.util.List;
14 | import java.util.LinkedList;
15 | import java.util.ListIterator;
16 |
17 | /**
18 | * Generates diff operations from differences between the contents of two the source files.
19 | * @author Katsuhisa Maruyama
20 | */
21 | public class DiffOperationGenerator {
22 |
23 | /**
24 | * The cost of an empty edit operation in terms of edit characters.
25 | */
26 | private static short editCost = 4;
27 |
28 | /**
29 | * Sets the edit costs for finding difference.
30 | * @param cost the edit cost to be set
31 | */
32 | public static void setEditCost(short cost) {
33 | editCost = cost;
34 | }
35 |
36 | /**
37 | * Generates diff operations from the differences between two textual contents.
38 | * @param time the time when this operation was inserted
39 | * @param path the name of the file path on which this operation was performed
40 | * @param otext the old contents of the file
41 | * @param ntext the new contents of the file
42 | * @return the collection of the generated diff operations
43 | */
44 | public static List generate(long time, String path, String otext, String ntext) {
45 | List ops = new ArrayList();
46 | List deltas = findDiff(otext, ntext);
47 |
48 | int offsetGap = 0;
49 | for (int idx = 0; idx < deltas.size(); idx++) {
50 | CodeDelta delta = deltas.get(idx);
51 |
52 | String itext = "";
53 | String dtext = "";
54 | if (delta.getType() == CodeDelta.Type.DELETE) {
55 | dtext = delta.getText();
56 |
57 | } else if (delta.getType() == CodeDelta.Type.INSERT) {
58 | itext = delta.getText();
59 | }
60 |
61 | int start = delta.getOffset() + offsetGap;
62 | NormalOperation op = new NormalOperation(time, idx, path, start, itext, dtext, NormalOperation.Type.DIFF);
63 | offsetGap = offsetGap - dtext.length();
64 |
65 | ops.add(op);
66 | }
67 |
68 | return ops;
69 | }
70 |
71 | /**
72 | * Finds differences between the contents of two the source code files.
73 | * @param otext the contents of the source code file to be diffed
74 | * @param ntext the contents of the source code file to be diffed
75 | * @return the collection of the code deltas
76 | */
77 | private static List findDiff(String otext, String ntext) {
78 | diff_match_patch dmp = new diff_match_patch();
79 | dmp.Diff_EditCost = editCost;
80 |
81 | LinkedList diffs = dmp.diff_main(otext, ntext);
82 | dmp.diff_cleanupEfficiency(diffs);
83 | List deltas = getDeltas(diffs);
84 |
85 | return deltas;
86 | }
87 |
88 | /**
89 | * Obtains the deltas from a given difference information.
90 | * @param diffs the collection of difference information of the diff utility.
91 | * @return the collection of the code deltas
92 | */
93 | private static List getDeltas(LinkedList diffs) {
94 | ArrayList deltas = new ArrayList();
95 | int offset = 0;
96 |
97 | for (ListIterator pointer = diffs.listIterator(); pointer.hasNext(); ) {
98 | Diff diff = pointer.next();
99 |
100 | if (diff.operation == Operation.INSERT) {
101 | deltas.add(new CodeDelta(offset, CodeDelta.Type.INSERT, diff.text));
102 |
103 | } else if (diff.operation == Operation.DELETE) {
104 | deltas.add(new CodeDelta(offset, CodeDelta.Type.DELETE, diff.text));
105 | }
106 |
107 | offset = offset + diff.text.length();
108 | }
109 |
110 | return deltas;
111 | }
112 | }
113 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/editor/ConsoleOperationListener.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.editor;
8 |
9 | import org.jtool.changerecorder.event.OperationEvent;
10 | import org.jtool.changerecorder.event.OperationEventListener;
11 |
12 | /**
13 | * Displays operations recorded on editors.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class ConsoleOperationListener implements OperationEventListener {
17 |
18 | /**
19 | * Receives an operation event when operation history was updated.
20 | * @param evt the received event
21 | */
22 | @Override
23 | public void historyNotification(OperationEvent evt) {
24 | System.out.println(evt.getOperation().toString());
25 | }
26 |
27 | }
28 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/editor/JCompilationUnitEditor.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.editor;
8 |
9 | import org.jtool.changerecorder.operation.FileOperation;
10 | import org.jtool.changerecorder.operation.IOperation;
11 | import org.jtool.macrorecorder.recorder.MacroEvent;
12 | import org.jtool.macrorecorder.util.EditorUtilities;
13 | import org.eclipse.core.resources.IFile;
14 | import org.eclipse.core.runtime.CoreException;
15 | import org.eclipse.core.runtime.IProgressMonitor;
16 | import org.eclipse.jdt.internal.ui.javaeditor.CompilationUnitEditor;
17 | import org.eclipse.jface.text.IDocument;
18 | import org.eclipse.ui.IEditorInput;
19 | import org.eclipse.ui.IEditorSite;
20 | import org.eclipse.ui.PartInitException;
21 |
22 | /**
23 | * Provides a Java-specific text editor on which editing operations are recorded.
24 | */
25 | @SuppressWarnings("restriction")
26 | public class JCompilationUnitEditor extends CompilationUnitEditor {
27 |
28 | /**
29 | * A manager that manages the operation history.
30 | */
31 | private HistoryManager historyManager = null;
32 |
33 | /**
34 | * Creates an instance of this editor.
35 | */
36 | public JCompilationUnitEditor() {
37 | super();
38 | }
39 |
40 | /**
41 | * Records the file open operation when the editor is instantiated.
42 | * @param site the editor site
43 | * @param input the editor input
44 | * @exception PartInitException if this editor was not initialized successfully
45 | */
46 | @Override
47 | public void init(IEditorSite site, IEditorInput input) throws PartInitException {
48 | super.init(site, input);
49 |
50 | if (historyManager == null) {
51 | historyManager = HistoryManager.getInstance();
52 | historyManager.start(this);
53 |
54 | historyManager.recordFileOpenOperation(getInputFile(), getSourceCode());
55 | }
56 | }
57 |
58 | /**
59 | * Records the file activation operation when the editor is activated.
60 | */
61 | @Override
62 | public void setFocus() {
63 | super.setFocus();
64 |
65 | if (historyManager != null) {
66 | IOperation op = historyManager.getLastOperation();
67 | if (op != null && op.getOperationType() == IOperation.Type.FILE) {
68 | FileOperation fop = (FileOperation)op;
69 | if (fop.getActionType() == FileOperation.Type.ACT && fop.getFilePath().compareTo(getInputFilePath()) == 0) {
70 | return;
71 | }
72 | }
73 |
74 | historyManager.recordFileOperation(getInputFile(), getSourceCode(), FileOperation.Type.ACT, false);
75 | }
76 | }
77 |
78 | /**
79 | * Records the file save operation and stores the operation history into the output file when the contents of the editor is saved.
80 | * @param progressMonitor the progress monitor for communicating result state, or null
if not needed
81 | */
82 | @Override
83 | public void doSave(IProgressMonitor progressMonitor) {
84 | super.doSave(progressMonitor);
85 |
86 | if (historyManager != null) {
87 | historyManager.recordFileOperation(getInputFile(), getSourceCode(), FileOperation.Type.SAVE, true);
88 | historyManager.writeHistory(getInputFile());
89 | }
90 | }
91 |
92 | /**
93 | * Stores the operation history into the output file when the setting of the editor input is changed.
94 | * @param input the changed editor input
95 | */
96 | @Override
97 | protected void doSetInput(IEditorInput input) throws CoreException {
98 | super.doSetInput(input);
99 | }
100 |
101 | /**
102 | * Records the file close operation and stores the operation history into the output file when the editor is closed.
103 | */
104 | @Override
105 | public void dispose() {
106 | if (historyManager != null) {
107 | historyManager.stop(this);
108 |
109 | historyManager.recordFileCloseOperation(getInputFile(), getSourceCode());
110 | historyManager.writeHistory(getInputFile());
111 | historyManager = null;
112 | }
113 |
114 | super.dispose();
115 | }
116 |
117 | /**
118 | * Returns the path of a file existing on this editor.
119 | * @return the file path, which is relative to the path of the path of the workspace
120 | */
121 | public String getInputFilePath() {
122 | return EditorUtilities.getInputFilePath(this);
123 | }
124 |
125 | /**
126 | * Returns a file existing on this editor.
127 | * @return the IFile
instance corresponding to the file, or null
if none
128 | */
129 | public IFile getInputFile() {
130 | return EditorUtilities.getInputFile(this);
131 | }
132 |
133 | /**
134 | * Obtains a document related to this editor.
135 | * @return the related document, or null
if none
136 | */
137 | public IDocument getDocument() {
138 | return EditorUtilities.getDocument(this);
139 | }
140 |
141 | /**
142 | * Obtains the contents of source code related to this editor.
143 | * @return the contents of the source code, or null
if the source code is not valid
144 | */
145 | public String getSourceCode() {
146 | return EditorUtilities.getSourceCode(this);
147 | }
148 |
149 | /**
150 | * Receives a macro event when a new macro is added.
151 | * @param evt the macro event
152 | */
153 | public void macroAdded(MacroEvent evt) {
154 | /*
155 | Macro macro = evt.getMacro();
156 | System.out.println(macro.toString());
157 | if (macro instanceof CompoundMacro) {
158 | CompoundMacro cmacro = (CompoundMacro)macro;
159 | for (Macro m : cmacro.getMacros()) {
160 | System.out.println(" " + m.toString());
161 | }
162 | }
163 | */
164 | }
165 |
166 | /**
167 | * Receives a macro event when a document is changed.
168 | * @param evt the raw macro event
169 | */
170 | public void documentChanged(MacroEvent evt) {
171 | // System.out.println("!MACRO: " + evt.getMacro());
172 | }
173 | }
174 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/event/OperationEvent.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.event;
8 |
9 | import org.jtool.changerecorder.operation.IOperation;
10 |
11 | /**
12 | * Manages an event indicating that the operation has performed.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public class OperationEvent {
16 |
17 | /**
18 | * Defines the type of this event.
19 | */
20 | public enum Type {
21 | OPERATION_ADDED, DEFAULT;
22 | }
23 |
24 | /**
25 | * The type of this event.
26 | */
27 | private OperationEvent.Type type = OperationEvent.Type.DEFAULT;
28 |
29 | /**
30 | * The operation sent by this operation event.
31 | */
32 | private IOperation operation;
33 |
34 | /**
35 | * Creates an instance containing information on this operation event.
36 | * @param type the type of this operation event
37 | * @param operation the operation sent by this operation event
38 | */
39 | public OperationEvent(OperationEvent.Type type, IOperation operation) {
40 | this.type = type;
41 | this.operation = operation;
42 | }
43 |
44 | /**
45 | * Creates an instance containing information on this operation event.
46 | * @param operation the operation sent by this operation event
47 | */
48 | public OperationEvent(IOperation operation) {
49 | this.operation = operation;
50 | }
51 |
52 | /**
53 | * Returns the type of this operation event.
54 | * @return the event type
55 | */
56 | public OperationEvent.Type getType() {
57 | return type;
58 | }
59 |
60 | /**
61 | * Returns the operation sent by this operation event.
62 | * @return the operation related to this operation event
63 | */
64 | public IOperation getOperation() {
65 | return operation;
66 | }
67 | }
68 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/event/OperationEventListener.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.event;
8 |
9 | /**
10 | * Defines the listener interface for receiving an operation event.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public interface OperationEventListener {
14 |
15 | /**
16 | * Receives an operation event when operation history was updated.
17 | * @param evt the received event
18 | */
19 | public void historyNotification(OperationEvent evt);
20 | }
21 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/event/OperationEventSource.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.event;
8 |
9 | import org.jtool.changerecorder.operation.IOperation;
10 | import java.util.List;
11 | import java.util.ArrayList;
12 |
13 | /**
14 | * Manages a source that send an operation event.
15 | * @author Katsuhisa Maruyama
16 | */
17 | public class OperationEventSource {
18 |
19 | /**
20 | * The collection of listeners that receives operation events.
21 | */
22 | private List listeners = new ArrayList();
23 |
24 | /**
25 | * Creates an object that performs as an event source.
26 | */
27 | public OperationEventSource() {
28 | }
29 |
30 | /**
31 | * Adds a listener in order to receive an operation event from this source.
32 | * @param listener the event listener to be added
33 | */
34 | public void addOperationEventListener(OperationEventListener listener) {
35 | listeners.add(listener);
36 | }
37 |
38 | /**
39 | * Removes a listener which no longer receives an operation event from this source.
40 | * @param listener the event listener to be removed
41 | */
42 | public void removeOperationEventListener(OperationEventListener listener) {
43 | listeners.remove(listener);
44 | }
45 |
46 | /**
47 | * Sends an operation event to all the listeners.
48 | * @param evt the operation event.
49 | */
50 | protected void notify(IOperation op) {
51 | OperationEvent evt = new OperationEvent(OperationEvent.Type.OPERATION_ADDED, op);
52 | for (OperationEventListener listener : listeners) {
53 | listener.historyNotification(evt);
54 | }
55 | }
56 | }
57 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/history/CodeRestorer.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.history;
8 |
9 | import org.jtool.changerecorder.operation.CompoundOperation;
10 | import org.jtool.changerecorder.operation.IOperation;
11 | import org.jtool.changerecorder.operation.NormalOperation;
12 |
13 | /**
14 | * Applies an operation into code.
15 | * @author Katsuhisa Maruyama
16 | */
17 | public class CodeRestorer {
18 |
19 | /**
20 | * Obtains the code after the application of a given operation into given code.
21 | * @param preCode the code before the application
22 | * @param op the operation to be applied
23 | * @return the resulting code after the application
24 | */
25 | public static String applyOperation(String preCode, IOperation op) {
26 | if (op instanceof NormalOperation) {
27 | return applyOperation(preCode, (NormalOperation)op);
28 |
29 | } else if (op instanceof CompoundOperation) {
30 | return applyOperation(preCode, (CompoundOperation)op);
31 | }
32 | return preCode;
33 | }
34 |
35 | /**
36 | * Applies a specified normal operation into given code.
37 | * @param preCode the code before the application
38 | * @param op the operation to be applied
39 | * @return the resulting code after the application
40 | */
41 | public static String applyOperation(String preCode, NormalOperation op) {
42 | StringBuilder postCode = new StringBuilder(preCode);
43 |
44 | if (hasDeletionMismatch(postCode, op)) {
45 | return null;
46 | }
47 |
48 | int start = op.getStart();
49 | int end = start + op.getDeletedText().length();
50 | String itext = op.getInsertedText();
51 | postCode.replace(start, end, itext);
52 | return postCode.toString();
53 | }
54 |
55 | /**
56 | * Applies a given compound operation into given code.
57 | * @param preCode the code before the application
58 | * @param cop the operation to be applied
59 | * @return the resulting code after the application
60 | */
61 | public static String applyOperation(String preCode, CompoundOperation cop) {
62 | String postCode = null;
63 |
64 | for (IOperation op : cop.getLeaves()) {
65 | if (op instanceof CompoundOperation) {
66 | applyOperation(preCode, (CompoundOperation)op);
67 |
68 | } else if (op instanceof NormalOperation) {
69 | postCode = applyOperation(preCode, (NormalOperation)op);
70 | if (postCode == null) {
71 | return null;
72 | }
73 | preCode = postCode;
74 | }
75 | }
76 | return postCode;
77 | }
78 |
79 | /**
80 | * Obtains the code after the application of a given operation into given code reversely.
81 | * @param preCode the code before the application
82 | * @param op the operation to be applied
83 | * @return the resulting code after the application
84 | */
85 | public static String applyOperationReversely(String preCode, IOperation op) {
86 | if (op instanceof NormalOperation) {
87 | return applyOperationReversely(preCode, (NormalOperation)op);
88 |
89 | } else if (op instanceof CompoundOperation) {
90 | return applyOperationReversely(preCode, (CompoundOperation)op);
91 |
92 | }
93 | return preCode;
94 | }
95 |
96 | /**
97 | * Applies a specified normal operation into given code reversely.
98 | * @param preCode the code before the application
99 | * @param op the operation to be applied
100 | * @return the resulting code after the application
101 | */
102 | public static String applyOperationReversely(String preCode, NormalOperation op) {
103 | StringBuilder postCode = new StringBuilder(preCode);
104 |
105 | if (hasInsertionMismatch(postCode, op)) {
106 | return null;
107 | }
108 |
109 | int start = op.getStart();
110 | int end = start + op.getDeletedText().length();
111 | String dtext = op.getDeletedText();
112 | postCode.replace(start, end, dtext);
113 | return postCode.toString();
114 | }
115 |
116 | /**
117 | * Applies a given compound operation into given code reversely.
118 | * @param preCode the code before the application
119 | * @param cop the operation to be applied
120 | * @return the resulting code after the application
121 | */
122 | public static String applyOperationReversely(String preCode, CompoundOperation cop) {
123 | String postCode = null;
124 |
125 | for (IOperation op : cop.getLeaves()) {
126 | if (op instanceof CompoundOperation) {
127 | applyOperationReversely(preCode, (CompoundOperation)op);
128 |
129 | } else if (op instanceof NormalOperation) {
130 | postCode = applyOperationReversely(preCode, (NormalOperation)op);
131 | if (postCode == null) {
132 | return null;
133 | }
134 | preCode = postCode;
135 | }
136 | }
137 | return postCode;
138 | }
139 |
140 | /**
141 | * Tests if the deletion derives any mismatch.
142 | * @param code the code before the application
143 | * @param op the operation to be applied
144 | * @return true
if a mismatch exists, otherwise false
145 | */
146 | private static boolean hasDeletionMismatch(StringBuilder code, NormalOperation op) {
147 | String dtext = op.getDeletedText();
148 | int start = op.getStart();
149 | int end = start + dtext.length();
150 |
151 | if (dtext.length() > 0) {
152 | String rtext = code.substring(start, end);
153 | if (rtext != null && rtext.compareTo(dtext) != 0) {
154 |
155 | for (int i = 0; i < rtext.length(); i++) {
156 | if (rtext.charAt(i) == dtext.charAt(i)) {
157 | System.out.println(((int)rtext.charAt(i)) + " == " + ((int)dtext.charAt(i)));
158 | } else {
159 | System.out.println(((int)rtext.charAt(i)) + " != " + ((int)dtext.charAt(i)));
160 | }
161 | }
162 | return true;
163 | }
164 | }
165 | return false;
166 | }
167 |
168 | /**
169 | * Tests if the deletion derives any mismatch.
170 | * @param code the code before the application
171 | * @param op the operation to be applied
172 | * @return true
if a mismatch exists, otherwise false
173 | */
174 | private static boolean hasInsertionMismatch(StringBuilder code, NormalOperation op) {
175 | String itext = op.getDeletedText();
176 | int start = op.getStart();
177 | int end = start + itext.length();
178 |
179 | if (itext.length() > 0) {
180 | String rtext = code.substring(start, end);
181 | if (rtext != null && rtext.compareTo(itext) != 0) {
182 |
183 | for (int i = 0; i < rtext.length(); i++) {
184 | if (rtext.charAt(i) == itext.charAt(i)) {
185 | System.out.println(((int)rtext.charAt(i)) + " == " + ((int)itext.charAt(i)));
186 | } else {
187 | System.out.println(((int)rtext.charAt(i)) + " != " + ((int)itext.charAt(i)));
188 | }
189 | }
190 | return true;
191 | }
192 | }
193 | return false;
194 | }
195 | }
196 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/history/XmlConstantStrings.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.history;
8 |
9 | /**
10 | * The elements, attributes, and values of the attributes appearing in XML documents
11 | * that store information on the operation history.
12 | * @author Katsuhisa Maruyama
13 | */
14 | public interface XmlConstantStrings {
15 |
16 | static final String OperationHistoryElem = "OperationHistory";
17 | static final String OperationHistoryVersion = "1.0a";
18 | static final String OperationsElem = "operations";
19 |
20 | static final String NormalOperationElem = "normalOperation";
21 | static final String CompoundOperationElem = "compoundOperation";
22 | static final String CopyOperationElem = "copyOperation";
23 | static final String FileOperationElem = "fileOperation";
24 | static final String MenuOperationElem = "menuOperation";
25 | static final String ResourceOperationElem = "resourceOperation";
26 |
27 | static final String InsertedElem = "inserted";
28 | static final String DeletedElem = "deleted";
29 | static final String CopiedElem = "copied";
30 | static final String CodeElem = "code";
31 |
32 | static final String VersionAttr = "version";
33 | static final String TimeAttr = "time";
34 | static final String SeqAttr = "seq";
35 | static final String OffsetAttr = "offset";
36 | static final String FileAttr = "file";
37 | static final String ActionAttr = "action";
38 | static final String LabelAttr = "label";
39 | static final String AuthorAttr = "author";
40 |
41 | static final String TargetAttr = "target";
42 | static final String APathAttr = "apath";
43 |
44 | static final String Yes = "yes";
45 | static final String No = "no";
46 | static final String None = "None";
47 | }
48 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/AbstractOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Whoami;
11 |
12 | /**
13 | * Defines the abstract class used for accessing information on the all kinds of operations.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public abstract class AbstractOperation implements IOperation {
17 |
18 | /**
19 | * The time when this operation was performed.
20 | */
21 | protected long time;
22 |
23 | /**
24 | * The sequence number that indicates the order of change operations in the same time.
25 | */
26 | private int sequenceNumber = 0;
27 |
28 | /**
29 | * The path name of the file on which this operation was performed.
30 | */
31 | protected String path;
32 |
33 | /**
34 | * The name of a developer who performed this operation.
35 | */
36 | protected String author;
37 |
38 | /**
39 | * Creates an instance storing information on this operation.
40 | * @param time the time when this operation was performed
41 | * @param seq the sequence number of this operation
42 | * @param path the name of the file on which this operation was performed
43 | * @param author the author's name
44 | */
45 | protected AbstractOperation(long time, int seq, String path, String author) {
46 | this.time = time;
47 | this.sequenceNumber = seq;
48 | this.path = path;
49 | this.author = author;
50 | }
51 |
52 | /**
53 | * Creates an instance storing information on this operation.
54 | * @param time the time when this operation was performed
55 | * @param seq the sequence number of this operation
56 | * @param path the name of the file on which this operation was performed
57 | */
58 | protected AbstractOperation(long time, int seq, String path) {
59 | this(time, seq, path, getUserName());
60 | }
61 |
62 | /**
63 | * Creates an instance storing information on this operation.
64 | * @param time the time when this operation was performed
65 | * @param path the name of the file on which this operation was performed
66 | * @param author the author's name
67 | */
68 | protected AbstractOperation(long time, String path, String author) {
69 | this(time, 0, path, author);
70 | }
71 |
72 | /**
73 | * Creates an instance storing information on this operation.
74 | * @param time the time when this operation was performed
75 | * @param path the name of the file on which this operation was performed
76 | */
77 | protected AbstractOperation(long time, String path) {
78 | this(time, 0, path);
79 | }
80 |
81 | /**
82 | * Obtains the user name by executing whoami
true if the operation is a text edit operation
135 | */
136 | public boolean isTextEditOperation() {
137 | IOperation.Type type = getOperationType();
138 | return type == IOperation.Type.NORMAL || type == IOperation.Type.COMPOUND || type == IOperation.Type.COPY;
139 | }
140 |
141 | /**
142 | * Tests if a given operation changes any text.
143 | * @return true
if the operation is a text change operation
144 | */
145 | public boolean isTextChangedOperation() {
146 | IOperation.Type type = getOperationType();
147 | return type == IOperation.Type.NORMAL || type == IOperation.Type.COMPOUND;
148 | }
149 |
150 | /**
151 | * Converts a text into its pretty one.
152 | * @param text the original text
153 | * @return the text consists of the first four characters not including the new line
154 | */
155 | public String getText(String text) {
156 | final int LESS_LEN = 9;
157 |
158 | String text2;
159 | if (text.length() < LESS_LEN + 1) {
160 | text2 = text;
161 | } else {
162 | text2 = text.substring(0, LESS_LEN + 1) + "...";
163 | }
164 |
165 | return text2.replace('\n', '~');
166 | }
167 |
168 | /**
169 | * Tests if this operation is the same as a given one.
170 | * @param op the given operation
171 | * @return true
if the two operations are the same, otherwise false
172 | */
173 | public boolean equals(IOperation op) {
174 | if (!(op instanceof AbstractOperation)) {
175 | return false;
176 | }
177 |
178 | return time == op.getTime() && sequenceNumber == getSequenceNumber() &&
179 | StringComparator.isSame(path, op.getFilePath()) &&
180 | StringComparator.isSame(author, op.getAuthor());
181 | }
182 | }
183 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/CompoundOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Time;
11 | import java.util.List;
12 | import java.util.ArrayList;
13 |
14 | /**
15 | * Stores information on a compound operation enclosing multiple operations.
16 | * @author Katsuhisa Maruyama
17 | */
18 | public class CompoundOperation extends AbstractOperation {
19 |
20 | /**
21 | * The array list of operations contained in this operation.
22 | */
23 | private List extends IOperation> operations = new ArrayList();
24 |
25 | /**
26 | * The label indicating the name of this operation.
27 | */
28 | protected String label;
29 |
30 | /**
31 | * Creates an instance storing information on this compound operation.
32 | * @param time the time when this operation was performed
33 | * @param author the author's name
34 | * @param ops the operations contained in this operation
35 | * @param label the label indicating the name of the undo operation
36 | */
37 | public CompoundOperation(long time, String author, List extends IOperation> ops, String label) {
38 | super(time, "", author);
39 | this.operations = ops;
40 | this.label = label;
41 | }
42 |
43 | /**
44 | * Creates an instance storing information on this compound operation.
45 | * @param time the time when this operation was performed
46 | * @param ops the operations contained in this operation
47 | * @param label the label indicating the name of the undo operation
48 | */
49 | public CompoundOperation(long time, List extends IOperation> ops, String label) {
50 | this(time, AbstractOperation.getUserName(), ops, label);
51 | }
52 |
53 | /**
54 | * Returns the array of operations contained in this operation.
55 | * @return the contained operations
56 | */
57 | public List extends IOperation> getOperations() {
58 | return operations;
59 | }
60 |
61 | /**
62 | * Returns the label indicating the name of the undo operation.
63 | * @return the label string
64 | */
65 | public String getLabel() {
66 | return label;
67 | }
68 |
69 | /**
70 | * Returns the array list of operations dangling on this operation.
71 | * @return the dangling editing operations
72 | */
73 | public List extends IOperation> getLeaves() {
74 | List leaves = new ArrayList();
75 | for (IOperation op : operations) {
76 | if (op.getOperationType() == IOperation.Type.COMPOUND) {
77 | CompoundOperation cop = (CompoundOperation)op;
78 | leaves.addAll(cop.getLeaves());
79 | } else {
80 | leaves.add(op);
81 | }
82 | }
83 | return leaves;
84 | }
85 |
86 | /**
87 | * Returns the sort of this operation.
88 | * @return the string indicating the operation sort
89 | */
90 | @Override
91 | public IOperation.Type getOperationType() {
92 | return IOperation.Type.COMPOUND;
93 | }
94 |
95 | /**
96 | * Tests if this operation is the same as a given one.
97 | * @param op the given operation
98 | * @return true
if the two operations are the same, otherwise false
99 | */
100 | @Override
101 | public boolean equals(IOperation op) {
102 | if (!(op instanceof CompoundOperation)) {
103 | return false;
104 | }
105 |
106 | CompoundOperation cop = (CompoundOperation)op;
107 | if (!super.equals(cop) || !StringComparator.isSame(label, cop.getLabel()) ||
108 | operations.size() != cop.getOperations().size()) {
109 | return false;
110 | }
111 |
112 | for (int idx = 0; idx < operations.size(); idx++) {
113 | if (!operations.get(idx).equals(cop.getOperations().get(idx))) {
114 | return false;
115 | }
116 | }
117 |
118 | return true;
119 | }
120 |
121 | /**
122 | * Returns the string for printing, which does not contain a new line character at its end.
123 | * @return the string for printing
124 | */
125 | @Override
126 | public String toString() {
127 | StringBuilder buf = new StringBuilder();
128 | buf.append("{");
129 | buf.append(Time.toUsefulFormat(time));
130 | buf.append(" label=[" + label + "]\n");
131 |
132 | for (IOperation op : operations) {
133 | buf.append(" " + op.toString());
134 | buf.append("\n");
135 | }
136 | buf.append("}");
137 |
138 | return buf.toString();
139 | }
140 | }
141 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/CopyOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Time;
11 |
12 | /**
13 | * Stores information on a copy operation.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class CopyOperation extends AbstractOperation {
17 |
18 | /**
19 | * The leftmost offset of the text modified by this editing operation.
20 | */
21 | protected int start;
22 |
23 | /**
24 | * The content of the text copied by this editing operation.
25 | */
26 | protected String copiedText;
27 |
28 | /**
29 | * Creates an instance storing information on this copy operation.
30 | * @param time the time when this operation was performed
31 | * @param path the name of the file path on which this operation was performed
32 | * @param author the author's name
33 | * @param start the leftmost offset of the text modified by this operation
34 | * @param ctext the content of the text copied by this operation
35 | */
36 | public CopyOperation(long time, String path, String author, int start, String ctext) {
37 | super(time, path, author);
38 | this.start = start;
39 | this.copiedText = ctext;
40 | }
41 |
42 | /**
43 | * Creates an instance storing information on this copy operation.
44 | * @param time the time when this operation was performed
45 | * @param path the name of the file path on which this operation was performed
46 | * @param start the leftmost offset of the text modified by this operation
47 | * @param ctext the content of the text copied by this operation
48 | */
49 | public CopyOperation(long time, String path, int start, String ctext) {
50 | this(time, path, AbstractOperation.getUserName(), start, ctext);
51 | }
52 |
53 | /**
54 | * Returns the leftmost offset of the text copied by this operation.
55 | * @return the leftmost offset value of the modified text
56 | */
57 | public int getStart() {
58 | return start;
59 | }
60 |
61 | /**
62 | * Returns the content of the text copied by this operation.
63 | * @return the content of the copied text, or the empty string
64 | */
65 | public String getCopiedText() {
66 | return copiedText;
67 | }
68 |
69 | /**
70 | * Returns the sort of this operation.
71 | * @return the string indicating the operation sort
72 | */
73 | @Override
74 | public IOperation.Type getOperationType() {
75 | return IOperation.Type.COPY;
76 | }
77 |
78 | /**
79 | * Tests if this operation is the same as a given one.
80 | * @param op the given operation
81 | * @return true
if the two operations are the same, otherwise false
82 | */
83 | @Override
84 | public boolean equals(IOperation op) {
85 | if (!(op instanceof CopyOperation)) {
86 | return false;
87 | }
88 |
89 | CopyOperation cop = (CopyOperation)op;
90 | return super.equals(cop) &&
91 | start == cop.getStart() && StringComparator.isSame(copiedText, cop.getCopiedText());
92 | }
93 |
94 | /**
95 | * Returns the string for printing, which does not contain a new line character at its end.
96 | * @return the string for printing
97 | */
98 | @Override
99 | public String toString() {
100 | StringBuilder buf = new StringBuilder();
101 | buf.append(Time.toUsefulFormat(time));
102 | buf.append(" author=[" + author + "]");
103 | buf.append(" path=" + path + "]");
104 | buf.append(" offset=" + start);
105 | buf.append(" copied=[" + getText(copiedText) + "]\n");
106 |
107 | return buf.toString();
108 | }
109 | }
110 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/FileOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Time;
11 |
12 | /**
13 | * Stores information on a file operation.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class FileOperation extends AbstractOperation {
17 |
18 | /**
19 | * Defines the type of a file action.
20 | */
21 | public enum Type {
22 | NEW, OPEN, CLOSE, SAVE, DELETE, ACT, INSTANT, NONE;
23 |
24 | /**
25 | * Checks the type of the file action
26 | * @param str the string indicating the action
27 | * @return the type of the file action, or NONE
if none
28 | */
29 | public static Type parseType(String str) {
30 | if (StringComparator.isSameIgnoreCase(str, "new")) {
31 | return NEW;
32 | } else if (StringComparator.isSameIgnoreCase(str, "open")) {
33 | return OPEN;
34 | } else if (StringComparator.isSameIgnoreCase(str, "close")) {
35 | return CLOSE;
36 | } else if (StringComparator.isSameIgnoreCase(str, "save")) {
37 | return SAVE;
38 | } else if (StringComparator.isSameIgnoreCase(str, "delete")) {
39 | return DELETE;
40 | } else if (StringComparator.isSameIgnoreCase(str, "act")) {
41 | return ACT;
42 | } else if (StringComparator.isSameIgnoreCase(str, "instant")) {
43 | return INSTANT;
44 | }
45 | return NONE;
46 | }
47 | }
48 |
49 | /**
50 | * The sort of the file action for this operation.
51 | */
52 | protected Type actionType;
53 |
54 | /**
55 | * The contents of the source code when this file operation was performed.
56 | */
57 | protected String code;
58 |
59 | /**
60 | * Creates an instance storing information on this file operation.
61 | * @param time the time when this operation was performed
62 | * @param path the path name of the file on which this operation was performed
63 | * @param author the author's name
64 | * @param atype the type of the operation
65 | * @param code the contents of the source code when this file operation was performed
66 | */
67 | public FileOperation(long time, String path, String author, Type atype, String code) {
68 | super(time, path, author);
69 | this.actionType = atype;
70 | this.code = code;
71 | }
72 |
73 | /**
74 | * Creates an instance storing information on this file operation.
75 | * @param time the time when this operation was performed
76 | * @param path the path name of the file on which this operation was performed
77 | * @param atype the type of the operation
78 | * @param code the contents of the source code when this file operation was performed
79 | */
80 | public FileOperation(long time, String path, Type atype, String code) {
81 | this(time, path, AbstractOperation.getUserName(), atype, code);
82 | }
83 |
84 | /**
85 | * Returns the sort of the file action for this operation.
86 | * @return the sort of the file action for this operation
87 | */
88 | public Type getActionType() {
89 | return actionType;
90 | }
91 |
92 | /**
93 | * Returns the contents of the source code when this file operation was performed
94 | * @return the contents of the source code
95 | */
96 | public String getCode() {
97 | return code;
98 | }
99 |
100 | /**
101 | * Sets the contents of the source code when this file operation was performed
102 | * @param code the contents of the source code
103 | */
104 | public void setCode(String code) {
105 | this.code = code;
106 | }
107 |
108 | /**
109 | * Returns the sort of this operation.
110 | * @return the string indicating the operation sort
111 | */
112 | @Override
113 | public IOperation.Type getOperationType() {
114 | return IOperation.Type.FILE;
115 | }
116 |
117 | /**
118 | * Tests if this operation is the same as a given one.
119 | * @param op the given operation
120 | * @return true
if the two operations are the same, otherwise false
121 | */
122 | @Override
123 | public boolean equals(IOperation op) {
124 | if (!(op instanceof FileOperation)) {
125 | return false;
126 | }
127 |
128 | FileOperation fop = (FileOperation)op;
129 | return super.equals(fop) &&
130 | actionType == fop.getActionType() && StringComparator.isSame(code, fop.getCode());
131 | }
132 |
133 | /**
134 | * Returns the string for printing, which does not contain a new line character at its end.
135 | * @return the string for printing
136 | */
137 | @Override
138 | public String toString() {
139 | StringBuilder buf = new StringBuilder();
140 | buf.append(Time.toUsefulFormat(time));
141 | buf.append(" " + actionType.toString());
142 | buf.append(" author=[" + author + "]");
143 | buf.append(" path=" + path);
144 | if (code != null) {
145 | buf.append(" code=[" + getText(code) + "]");
146 | }
147 |
148 | return buf.toString();
149 | }
150 | }
151 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/IOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | /**
10 | * Defines the interface used for accessing information on the all kinds of operations.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public interface IOperation {
14 |
15 | /**
16 | * Defines the type of an operation.
17 | */
18 | public enum Type {
19 |
20 | /**
21 | * The string indicating if this is a normal operation.
22 | */
23 | NORMAL,
24 |
25 | /**
26 | * The string indicating if this is a compounded operation.
27 | */
28 | COMPOUND,
29 |
30 | /**
31 | * The string indicating if this is a copy operation.
32 | */
33 | COPY,
34 |
35 | /**
36 | * The string indicating if this is a file operation.
37 | */
38 | FILE,
39 |
40 | /**
41 | * The string indicating if this is a menu operation.
42 | */
43 | MENU,
44 |
45 | /**
46 | * The string indicating if this is a resource change operation.
47 | */
48 | RESOURCE,
49 |
50 | /**
51 | * The string indicating if this is a null operation.
52 | */
53 | NULL;
54 | }
55 |
56 | /**
57 | * Returns the time when this operation was performed.
58 | * @return the time of the operation
59 | */
60 | public long getTime();
61 |
62 | /**
63 | * Returns the sequence number indicating the order of operations whose times are the same.
64 | * @return the sequence number of this operation
65 | */
66 | public int getSequenceNumber();
67 |
68 | /**
69 | * Returns the path name of the file on which this operation was performed.
70 | * @return the path name of the file
71 | */
72 | public String getFilePath();
73 |
74 | /**
75 | * Returns the name of a author who performs this operation.
76 | * @return the suthor's name
77 | */
78 | public String getAuthor();
79 |
80 | /**
81 | * Returns the sort of this operation.
82 | * @return the string indicating the operation sort
83 | */
84 | public IOperation.Type getOperationType();
85 |
86 | /**
87 | * Tests if a given operation edits any text.
88 | * @return true
if the operation is a text edit operation
89 | */
90 | public boolean isTextEditOperation();
91 |
92 | /**
93 | * Tests if a given operation changes any text.
94 | * @return true
if the operation is a text change operation
95 | */
96 | public boolean isTextChangedOperation();
97 |
98 | /**
99 | * Tests if this operation is the same as a given one.
100 | * @param op the given operation
101 | * @return true
if the two operations are the same, otherwise false
102 | */
103 | public boolean equals(IOperation op);
104 |
105 | /**
106 | * Returns the string for printing, which does not contain a new line character at its end.
107 | * @return the string for printing
108 | */
109 | public String toString();
110 | }
111 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/MenuOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Time;
11 |
12 | /**
13 | * Stores information on a menu operation.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class MenuOperation extends AbstractOperation {
17 |
18 | /**
19 | * The label indicating the contents of this operation.
20 | */
21 | protected String label;
22 |
23 | /**
24 | * Provides the constructor for creating an instance storing information on this operation.
25 | * @param time the time when this operation was performed
26 | * @param path the name of the file on which this operation was performed
27 | * @param author the author's name
28 | * @param the label indicating the name of the menu operation
29 | */
30 | public MenuOperation(long time, String path, String author, String label) {
31 | super(time, path, author);
32 | this.label = label;
33 | }
34 |
35 | /**
36 | * Provides the constructor for creating an instance storing information on this operation.
37 | * @param time the time when this operation was performed
38 | * @param path the name of the file on which this operation was performed
39 | * @param the label indicating the name of the menu operation
40 | */
41 | public MenuOperation(long time, String path, String label) {
42 | this(time, path, AbstractOperation.getUserName(), label);
43 | }
44 |
45 | /**
46 | * Returns the label indicating the name of the menu operation.
47 | * @return the label string
48 | */
49 | public String getLabel() {
50 | return label;
51 | }
52 |
53 | /**
54 | * Returns the sort of this operation.
55 | * @return the string indicating the operation sort
56 | */
57 | @Override
58 | public IOperation.Type getOperationType() {
59 | return IOperation.Type.MENU;
60 | }
61 |
62 | /**
63 | * Tests if this operation is the same as a given one.
64 | * @param op the given operation
65 | * @return true
if the two operations are the same, otherwise false
66 | */
67 | @Override
68 | public boolean equals(IOperation op) {
69 | if (!(op instanceof MenuOperation)) {
70 | return false;
71 | }
72 |
73 | MenuOperation mop = (MenuOperation)op;
74 | return super.equals(mop) && StringComparator.isSame(label, mop.getLabel());
75 | }
76 |
77 | /**
78 | * Returns the string for printing, which does not contain a new line character at its end.
79 | * @return the string for printing
80 | */
81 | @Override
82 | public String toString() {
83 | StringBuilder buf = new StringBuilder();
84 | buf.append(Time.toUsefulFormat(time));
85 | buf.append(" MENU ");
86 | buf.append(" label=[" + label + "]");
87 | buf.append(" autor=[" + author + "]");
88 | buf.append(" path=" + path);
89 |
90 | return buf.toString();
91 | }
92 | }
93 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/NullOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | /**
10 | * Stores information on a null operation.
11 | * This operation does not usually appear.
12 | * @author Katsuhisa Maruyama
13 | */
14 | public class NullOperation extends AbstractOperation {
15 |
16 | /**
17 | * The cache that stores the original operation.
18 | */
19 | private IOperation originalOperation = null;
20 |
21 | /**
22 | * Creates an instance storing information on this null operation.
23 | */
24 | public NullOperation() {
25 | super(-1, null, null);
26 | }
27 |
28 | /**
29 | * Creates an instance storing information on this null operation.
30 | * @param original the original operation to be stored
31 | */
32 | public NullOperation(IOperation original) {
33 | super(-1, null, null);
34 | originalOperation = original;
35 | }
36 |
37 | /**
38 | * Returns the stored original operation
39 | * @return the original operation
40 | */
41 | public IOperation getOriginalOperation() {
42 | return originalOperation;
43 | }
44 |
45 | /**
46 | * Returns the sort of this operation.
47 | * @return the string indicating the operation sort
48 | */
49 | @Override
50 | public IOperation.Type getOperationType() {
51 | return IOperation.Type.NULL;
52 | }
53 |
54 | /**
55 | * Tests if this operation is the same as a given one.
56 | * @param op the given operation
57 | * @return always false
58 | */
59 | @Override
60 | public boolean equals(IOperation op) {
61 | return false;
62 | }
63 |
64 | /**
65 | * Returns the string for printing, which does not contain a new line character at its end.
66 | * @return the string for printing
67 | */
68 | @Override
69 | public String toString() {
70 | return "NULL";
71 | }
72 | }
73 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/ResourceOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 | import org.jtool.changerecorder.util.Time;
11 |
12 | /**
13 | * Stores information on an operation related to the resource (project and package) changes.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class ResourceOperation extends AbstractOperation {
17 |
18 | /**
19 | * Defines the type of a resource change.
20 | */
21 | public enum Type {
22 |
23 | /**
24 | * The type of the resource change performed by this operation.
25 | */
26 | ADDED, REMOVED, MOVED_FROM, MOVED_TO, RENAMED_FROM, RENAMED_TO, OTHERS;
27 |
28 | /**
29 | * Obtains the type of the resource change performed by this operation.
30 | * @param str the type string indicating the resource change
31 | * @return the type of the resource change
32 | */
33 | public static ResourceOperation.Type parseType(String str) {
34 | if (StringComparator.isSameIgnoreCase(str, "added")) {
35 | return ADDED;
36 | } else if (StringComparator.isSameIgnoreCase(str, "removed")) {
37 | return REMOVED;
38 | } else if (StringComparator.isSameIgnoreCase(str, "moved_from")) {
39 | return MOVED_FROM;
40 | } else if (StringComparator.isSameIgnoreCase(str, "moved_to")) {
41 | return MOVED_TO;
42 | } else if (StringComparator.isSameIgnoreCase(str, "renamed_from")) {
43 | return RENAMED_FROM;
44 | } else if (StringComparator.isSameIgnoreCase(str, "renamed_to")) {
45 | return RENAMED_TO;
46 | }
47 |
48 | return OTHERS;
49 | }
50 | }
51 |
52 | /**
53 | * Defines the target of a resource change.
54 | */
55 | public enum Target {
56 |
57 | /**
58 | * The target of the resource change performed by this operation.
59 | */
60 | JPROJECT, JPACKAGE, JFILE, OTHERS;
61 |
62 | /**
63 | * Obtains the target of the resource change performed by this operation.
64 | * @param str the target string indicating the resource change
65 | * @return the target of the resource change
66 | */
67 | public static ResourceOperation.Target parseType(String str) {
68 | if (StringComparator.isSameIgnoreCase(str, "jproject")) {
69 | return JPROJECT;
70 | } else if (StringComparator.isSameIgnoreCase(str, "jpackage")) {
71 | return JPACKAGE;
72 | } else if (StringComparator.isSameIgnoreCase(str, "jfile")) {
73 | return JFILE;
74 | }
75 |
76 | return OTHERS;
77 | }
78 | }
79 |
80 | /**
81 | * The type of the resource change performed by this operation.
82 | */
83 | protected Type actionType;
84 |
85 | /**
86 | * The target of the resource change performed by this operation.
87 | */
88 | protected Target target;
89 |
90 | /**
91 | * The path of a resource identical to the resource changed by this macro.
92 | */
93 | private String ipath;
94 |
95 | /**
96 | * Creates an instance that stores an operation related to resource change.
97 | * @param time the time when the operation was performed
98 | * @param path the file related to the changed resource
99 | * @param author the author's name
100 | * @param atype the type of the resource change
101 | * @param target the target of the resource change
102 | * @param ipath the path of a resource identical to the changed resource
103 | */
104 | public ResourceOperation(long time, String path, String author, Type atype, Target target, String ipath) {
105 | super(time, path, author);
106 | this.actionType = atype;
107 | this.target = target;
108 | this.ipath = ipath;
109 | }
110 |
111 | /**
112 | * Creates an instance that stores an operation related to resource change.
113 | * @param time the time when the operation was performed
114 | * @param path the file related to the changed resource, which is usually null
115 | * @param ctype the type of the resource change
116 | * @param target the target of the resource change
117 | * @param ipath the path of a resource identical to the changed resource
118 | */
119 | public ResourceOperation(long time, String path, Type ctype, Target target, String ipath) {
120 | this(time, path, AbstractOperation.getUserName(), ctype, target, ipath);
121 | }
122 |
123 | /**
124 | * Returns the type of the resource change performed by this operation
125 | * @return the type of the resource change
126 | */
127 | public Type getActionType() {
128 | return actionType;
129 | }
130 |
131 | /**
132 | * Returns the target of the resource change performed by this operation
133 | * @return the target of the resource change
134 | */
135 | public Target getTarget() {
136 | return target;
137 | }
138 |
139 | /**
140 | * Returns the path of a resource moved/renamed from or to.
141 | * @return the path of the identical resource
142 | */
143 | public String getIdenticalPath() {
144 | return ipath;
145 | }
146 |
147 | /**
148 | * Returns the sort of this operation.
149 | * @return the string indicating the operation sort
150 | */
151 | @Override
152 | public IOperation.Type getOperationType() {
153 | return IOperation.Type.RESOURCE;
154 | }
155 |
156 | /**
157 | * Tests if this operation is the same as a given one.
158 | * @param op the given operation
159 | * @return true
if the two operations are the same, otherwise false
160 | */
161 | @Override
162 | public boolean equals(IOperation op) {
163 | if (!(op instanceof ResourceOperation)) {
164 | return false;
165 | }
166 |
167 | ResourceOperation rop = (ResourceOperation)op;
168 | return super.equals(rop) &&
169 | actionType == rop.getActionType() && target == rop.getTarget() &&
170 | StringComparator.isSame(ipath, rop.getIdenticalPath());
171 | }
172 |
173 | /**
174 | * Obtains information on this operation.
175 | * @return the string storing the information on this operation
176 | */
177 | @Override
178 | public String toString() {
179 | StringBuilder buf = new StringBuilder();
180 | buf.append(Time.toUsefulFormat(time));
181 | buf.append(" " + actionType.name());
182 | buf.append(" author=[" + author + "]");
183 | buf.append(" target=" + target.name());
184 | buf.append(" path=" + path);
185 | buf.append(" ipath=" + ipath);
186 |
187 | return buf.toString();
188 | }
189 | }
190 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/operation/TextOperation.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.operation;
8 |
9 | import org.jtool.changerecorder.util.StringComparator;
10 |
11 | /**
12 | * Stores information on a text operation.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public abstract class TextOperation extends AbstractOperation {
16 |
17 | /**
18 | * The leftmost offset of the text modified by this operation.
19 | */
20 | protected int start;
21 |
22 | /**
23 | * The contents of the text inserted by this operation.
24 | */
25 | protected String insertedText = "";
26 |
27 | /**
28 | * The contents of the text deleted by this operation.
29 | */
30 | protected String deletedText = "";
31 |
32 | /**
33 | * Creates an instance storing information on this operation.
34 | * @param time the time when this operation was performed
35 | * @param seq the sequence number of this operation
36 | * @param path the name of the file path on which this operation was performed
37 | * @param author the author's name
38 | * @param start the leftmost offset of the text modified by this operation
39 | * @param itext the contents of the text inserted by this operation
40 | * @param dtext the contents of the text deleted by this operation
41 | */
42 | public TextOperation(long time, int seq, String path, String author, int start, String itext, String dtext) {
43 | super(time, seq, path, author);
44 | this.start = start;
45 | if (itext != null) {
46 | this.insertedText = itext;
47 | }
48 | if (dtext != null) {
49 | this.deletedText = dtext;
50 | }
51 | }
52 |
53 | /**
54 | * Creates an instance storing information on this operation.
55 | * @param time the time when this operation was performed
56 | * @param seq the sequence number of this operation
57 | * @param path the name of the file path on which this operation was performed
58 | * @param start the leftmost offset of the text modified by this operation
59 | * @param itext the contents of the text inserted by this operation
60 | * @param dtext the contents of the text deleted by this operation
61 | */
62 | public TextOperation(long time, int seq, String path, int start, String itext, String dtext) {
63 | this(time, seq, path, AbstractOperation.getUserName(), start, itext, dtext);
64 | }
65 |
66 | /**
67 | * Creates an instance storing information on this editing operation.
68 | * This constructor is called when the instance is created from the undo history of Eclipse.
69 | * @param time the time when this operation was performed
70 | * @param path the name of the file path on which this operation was performed
71 | * @param author the author's name
72 | * @param start the leftmost offset of the text modified by this operation
73 | * @param itext the contents of the text inserted by this operation
74 | * @param dtext the contents of the text deleted by this operation
75 | */
76 | public TextOperation(long time, String path, String author, int start, String itext, String dtext) {
77 | this(time, 0, path, author, start, itext, dtext);
78 | }
79 |
80 | /**
81 | * Creates an instance storing information on this editing operation.
82 | * This constructor is called when the instance is created from the undo history of Eclipse.
83 | * @param time the time when this operation was performed
84 | * @param path the name of the file path on which this operation was performed
85 | * @param start the leftmost offset of the text modified by this operation
86 | * @param itext the contents of the text inserted by this operation
87 | * @param dtext the contents of the text deleted by this operation
88 | */
89 | public TextOperation(long time, String path, int start, String itext, String dtext) {
90 | this(time, path, AbstractOperation.getUserName(), start, itext, dtext);
91 | }
92 |
93 | /**
94 | * Returns the leftmost offset of the text modified by this operation.
95 | * @return the leftmost offset value of the modified text
96 | */
97 | public int getStart() {
98 | return start;
99 | }
100 |
101 | /**
102 | * Returns the contents of the text inserted by this operation.
103 | * @return the contents of the inserted text, or the empty string
104 | */
105 | public String getInsertedText() {
106 | return insertedText;
107 | }
108 |
109 | /**
110 | * Sets the contents of the text inserted by this operation.
111 | * @param text the contents of the inserted text
112 | */
113 | public void setInsertedText(String text) {
114 | insertedText = text;
115 | }
116 |
117 | /**
118 | * Returns the content of the text deleted by this operation.
119 | * @return the contents of the deleted text, or the empty string
120 | */
121 | public String getDeletedText() {
122 | return deletedText;
123 | }
124 |
125 | /**
126 | * Sets the contents of the text deleted by this operation.
127 | * @param text the contents of the deleted text
128 | */
129 | public void setDeletedText(String text) {
130 | deletedText = text;
131 | }
132 |
133 | /**
134 | * Tests if this operation did not any change of the text.
135 | * @return true
if both the inserted and deleted texts are empty, otherwise false
136 | */
137 | public boolean isEmpty() {
138 | return insertedText.length() == 0 && deletedText.length() == 0;
139 | }
140 |
141 | /**
142 | * Tests if this operation inserted any text.
143 | * @return true
if the inserted text is not empty but the deleted text is empty, otherwise false
144 | */
145 | public boolean isInsertion() {
146 | return insertedText.length() != 0 && deletedText.length() == 0;
147 | }
148 |
149 | /**
150 | * Tests if this operation inserted any text.
151 | * @return true
if the deleted text is not empty but the inserted text is empty, otherwise false
152 | */
153 | public boolean isDeletion() {
154 | return insertedText.length() == 0 && deletedText.length() != 0;
155 | }
156 |
157 | /**
158 | * Tests if this operation inserted any text.
159 | * @return true
if the inserted and deleted texts are not empty, otherwise false
160 | */
161 | public boolean isReplace() {
162 | return insertedText.length() != 0 && deletedText.length() != 0;
163 | }
164 |
165 | /**
166 | * Tests if this operation is the same as a given one.
167 | * @param op the given operation
168 | * @return true
if the two operations are the same, otherwise false
169 | */
170 | @Override
171 | public boolean equals(IOperation op) {
172 | if (!(op instanceof TextOperation)) {
173 | return false;
174 | }
175 |
176 | TextOperation top = (TextOperation)op;
177 | return super.equals(top) && start == top.getStart() &&
178 | StringComparator.isSame(insertedText, top.getInsertedText()) &&
179 | StringComparator.isSame(deletedText, top.getDeletedText());
180 | }
181 | }
182 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/util/FileStream.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.util;
8 |
9 | import org.apache.commons.io.FileUtils;
10 | import java.io.File;
11 | import java.io.IOException;
12 |
13 | /**
14 | * Manages the file stream.
15 | * @author Katsuhisa Maruyama
16 | */
17 | public class FileStream {
18 |
19 | /**
20 | * Reads and returns the contents of a file.
21 | * @param path the full path indicating the file to be read
22 | * @return the contents of the file
23 | */
24 | public static String read(String path) {
25 | File file = new File(path);
26 | try {
27 | return FileUtils.readFileToString(file);
28 | } catch (IOException e) {
29 | System.err.println(e.getMessage());
30 | }
31 | return "";
32 | }
33 |
34 | /**
35 | * Writes the content into a file.
36 | * @param path the full path indicating the file which the contents are written into
37 | * @param contents the contents to be written
38 | */
39 | public static void write(String path, String contents) {
40 | makeDir(path);
41 |
42 | File file = new File(path);
43 | try {
44 | FileUtils.writeStringToFile(file, contents);
45 | } catch (final IOException e) {
46 | System.err.println(e.getMessage());
47 | }
48 | }
49 |
50 | /**
51 | * Creates a directory containing a file.
52 | * @param path the path name of the file
53 | */
54 | public static void makeDir(String path) {
55 | try {
56 | FileUtils.forceMkdir(new File(path).getParentFile());
57 | } catch (final IOException e) {
58 | System.err.println(e.getMessage());
59 | }
60 | }
61 | }
62 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/util/StringComparator.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.util;
8 |
9 | /**
10 | * Compares two strings.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class StringComparator {
14 |
15 | /**
16 | * Tests if two texts are the same.
17 | * @param text1 the first text to be compared to the second text
18 | * @param text2 the second text to be compare to the first text
19 | * @return true
if both the texts are the same, otherwise false
20 | */
21 | public static boolean isSame(String text1, String text2) {
22 | if (text1 == null && text2 == null) {
23 | return true;
24 | }
25 |
26 | if (text1 == null || text2 == null) {
27 | return false;
28 | }
29 |
30 | return text1.compareTo(text2) == 0;
31 | }
32 |
33 | /**
34 | * Tests if two texts are the same, ignoring case differences.
35 | * @param text1 the first text to be compared to the second text
36 | * @param text2 the second text to be compare to the first text
37 | * @return true
if the texts are the same, otherwise false
38 | */
39 | public static boolean isSameIgnoreCase(String text1, String text2) {
40 | if (text1 == null && text2 == null) {
41 | return true;
42 | }
43 |
44 | if (text1 == null || text2 == null) {
45 | return false;
46 | }
47 |
48 | return text1.compareToIgnoreCase(text2) == 0;
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/util/Time.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.util;
8 |
9 | import java.util.Calendar;
10 |
11 | /**
12 | * Manages and formats time information.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public class Time {
16 |
17 | /**
18 | * Obtains the current time.
19 | * @return the current time
20 | */
21 | public static long getCurrentTime() {
22 | Calendar cal = Calendar.getInstance();
23 | return cal.getTimeInMillis();
24 | }
25 |
26 | /**
27 | * Obtains the formated time information.
28 | * @param time the time information
29 | * @return the formatted string of the time
30 | */
31 | public static String toUsefulFormat(long time) {
32 | Calendar cal = Calendar.getInstance();
33 | cal.setTimeInMillis(time);
34 |
35 | return String.format("%1$tY/%1$tm/%1$td %1$tT", cal);
36 | }
37 |
38 | /**
39 | * Obtains time from the string format.
40 | * @param str the string representing the time
41 | * @return the time
42 | */
43 | public static long parseTime(String str) {
44 | str = str.trim();
45 | str = str.replace('/', ' ');
46 | str = str.replace(':', ' ');
47 | String[] strs = str.split(" ");
48 | if (strs.length < 3 || 6 < strs.length) {
49 | return -1;
50 | }
51 |
52 | int year, month, day, hour, min, sec;
53 | try {
54 | year = Integer.parseInt(strs[0]);
55 | month = Integer.parseInt(strs[1]);
56 | day = Integer.parseInt(strs[2]);
57 | hour = Integer.parseInt(strs[3]);
58 | min = Integer.parseInt(strs[4]);
59 | sec = Integer.parseInt(strs[5]);
60 | } catch (Exception e) {
61 | return -1;
62 | }
63 |
64 | Calendar cal = Calendar.getInstance();
65 | cal.set(year, month - 1, day, hour, min, sec);
66 | return cal.getTimeInMillis();
67 | }
68 |
69 | /**
70 | * Obtains the year information.
71 | * @param time the time information
72 | * @return the year information
73 | */
74 | public static int getYear(long time) {
75 | Calendar cal = Calendar.getInstance();
76 | cal.setTimeInMillis(time);
77 | return cal.get(Calendar.YEAR);
78 | }
79 |
80 | /**
81 | * Obtains the month information.
82 | * @param time the time information
83 | * @return the month information
84 | */
85 | public static int getMonth(long time) {
86 | Calendar cal = Calendar.getInstance();
87 | cal.setTimeInMillis(time);
88 | return cal.get(Calendar.MONTH) + 1;
89 | }
90 |
91 | /**
92 | * Obtains the day information.
93 | * @param time the time information
94 | * @return the day information
95 | */
96 | public static int getDay(long time) {
97 | Calendar cal = Calendar.getInstance();
98 | cal.setTimeInMillis(time);
99 | return cal.get(Calendar.DAY_OF_MONTH);
100 | }
101 |
102 | /**
103 | * Obtains time information with the YYYYMMDD format.
104 | * @param time the time information
105 | * @return the formated string of the time
106 | */
107 | public static String YYYYMMDD(long time) {
108 | return String.format("%04d%02d%02d", getYear(time), getMonth(time), getDay(time));
109 | }
110 |
111 | /**
112 | * Tests if the time information is valid.
113 | * @param time the time information
114 | * @return true
if the time information is valid, otherwise false
115 | */
116 | public static boolean isValid(long time) {
117 | return 0 <= time && time <= Long.MAX_VALUE;
118 | }
119 | }
120 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/util/Whoami.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Software Science and Technology Lab.
3 | * Department of Computer Science, Ritsumeikan University
4 | */
5 |
6 | package org.jtool.changerecorder.util;
7 |
8 | import java.io.BufferedReader;
9 | import java.io.IOException;
10 | import java.io.InputStreamReader;
11 |
12 | /**
13 | * Obtains the name of a user editing source code.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class Whoami {
17 |
18 | /**
19 | * The name of a command for obtaining developer's name.
20 | */
21 | private static final String whoamiCmd = "whoami";
22 |
23 | /**
24 | * The user name.
25 | */
26 | private static String userName = null;
27 |
28 | /**
29 | * Obtains the user name by using the whoami
command.
30 | * @return the user name
31 | */
32 | public static String getUserName() {
33 | if (userName != null) {
34 | return userName;
35 | }
36 |
37 | userName = "Unknown";
38 |
39 | BufferedReader reader = null;
40 | Process process = null;
41 | try {
42 | Runtime runtime = Runtime.getRuntime();
43 | process = runtime.exec(whoamiCmd);
44 | reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
45 |
46 | userName = reader.readLine();
47 | if (userName.indexOf("\\") >= 0) { // for Windows format (host_name + "\" + user_name)
48 | userName = userName.substring(userName.indexOf("\\") + 1);
49 | }
50 | } catch (IOException e) {
51 | /* empty */
52 | } finally {
53 | if (process != null) {
54 | process.destroy();
55 | }
56 | if (reader != null) {
57 | try {
58 | reader.close();
59 | } catch (IOException e) {
60 | /* empty */
61 | }
62 | }
63 | }
64 |
65 | return userName;
66 | }
67 | }
68 |
--------------------------------------------------------------------------------
/ChangeRecorder/src/org/jtool/changerecorder/util/XmlFileStream.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.changerecorder.util;
8 |
9 | import org.eclipse.core.resources.IFile;
10 | import org.eclipse.core.runtime.CoreException;
11 | import org.xml.sax.ErrorHandler;
12 | import org.xml.sax.SAXException;
13 | import org.xml.sax.SAXParseException;
14 | import org.w3c.dom.Document;
15 | import javax.xml.parsers.DocumentBuilder;
16 | import javax.xml.parsers.DocumentBuilderFactory;
17 | import javax.xml.transform.OutputKeys;
18 | import javax.xml.transform.Transformer;
19 | import javax.xml.transform.TransformerException;
20 | import javax.xml.transform.TransformerFactory;
21 | import javax.xml.transform.dom.DOMSource;
22 | import javax.xml.transform.stream.StreamResult;
23 | import java.io.File;
24 | import java.io.StringWriter;
25 | import java.nio.charset.Charset;
26 |
27 | /**
28 | * Manages the XML file stream.
29 | * @author Katsuhisa Maruyama
30 | */
31 | public class XmlFileStream {
32 |
33 | /**
34 | * Reads and returns the DOM instance created from the contents of an XML file.
35 | * @param path the full path indicating the XML file to be read
36 | * @return the DOM instance
37 | */
38 | public static Document read(final String path) {
39 | try {
40 | DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
41 | factory.setIgnoringElementContentWhitespace(true);
42 | DocumentBuilder builder = factory.newDocumentBuilder();
43 |
44 | builder.setErrorHandler(new ErrorHandler() {
45 |
46 | public void error(SAXParseException e) throws SAXException {
47 | printException(path, e);
48 | }
49 |
50 | public void fatalError(SAXParseException e) throws SAXException {
51 | printException(path, e);
52 | }
53 |
54 | public void warning(SAXParseException e) throws SAXException {
55 | printException(path, e);
56 | }
57 | });
58 |
59 | File file = new File(path);
60 | return builder.parse(file);
61 |
62 | } catch (Exception e) {
63 | System.err.println("DOM: Parse error occurred: " + e.getMessage() + ".");
64 | }
65 | return null;
66 | }
67 |
68 | /**
69 | * Prints errors during paring the contents of the XML file.
70 | * @param path the full path indicating the XML file to be read
71 | * @param e the occurred exception
72 | */
73 | private static void printException(String path, SAXParseException e) {
74 | System.err.println("[FATAL]file:" + path + "line:" + e.getLineNumber() + ", " +
75 | "column:" + e.getColumnNumber() + ", " + e.getMessage());
76 | }
77 |
78 | /**
79 | *
80 | * Writes the content of the DOM instance into an XML file.
81 | * @param doc the content of the DOM instance to be written
82 | * @param path the full path indicating the file which the contents are written into
83 | * @param file the input file
84 | */
85 | public static void write(Document doc, String path, IFile file) {
86 | try {
87 | String encoding;
88 | if (file == null) {
89 | encoding = Charset.defaultCharset().name();
90 | } else {
91 | encoding = file.getCharset();
92 | }
93 |
94 | write(doc, path, encoding);
95 | } catch (CoreException e) {
96 | e.printStackTrace();
97 | }
98 | }
99 |
100 | /**
101 | *
102 | * Writes the content of the DOM instance into an XML file.
103 | * @param doc the content of the DOM instance to be written
104 | * @param path the full path indicating the file which the contents are written into
105 | * @param the encoding of texts in the DOM instance
106 | */
107 | public static void write(Document doc, String path, String encoding) {
108 | path.replace('/', File.separatorChar);
109 |
110 | try {
111 | TransformerFactory factory = TransformerFactory.newInstance();
112 | Transformer transformer = factory.newTransformer();
113 | transformer.setOutputProperty(OutputKeys.ENCODING, encoding);
114 | // transformer.setOutputProperty(OutputKeys.ENCODING, "Shift_JIS");
115 | // transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
116 | transformer.setOutputProperty(OutputKeys.INDENT, "yes");
117 | DOMSource src = new DOMSource(doc);
118 |
119 | StringWriter writer = new StringWriter();
120 | transformer.transform(src, new StreamResult(writer));
121 |
122 | FileStream.write(path, writer.toString());
123 | } catch (TransformerException e) {
124 | System.out.println("DOM: Write error occurred: " + e.getMessage() + ".");
125 | }
126 | }
127 | }
128 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 Ziyang Liao
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/MacroRecorder/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/MacroRecorder/.gitignore:
--------------------------------------------------------------------------------
1 | /bin
2 |
--------------------------------------------------------------------------------
/MacroRecorder/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | MacroRecorder
4 |
5 |
6 |
7 |
8 |
9 | org.eclipse.jdt.core.javabuilder
10 |
11 |
12 |
13 |
14 | org.eclipse.pde.ManifestBuilder
15 |
16 |
17 |
18 |
19 | org.eclipse.pde.SchemaBuilder
20 |
21 |
22 |
23 |
24 |
25 | org.eclipse.pde.PluginNature
26 | org.eclipse.jdt.core.javanature
27 |
28 |
29 |
--------------------------------------------------------------------------------
/MacroRecorder/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
4 | org.eclipse.jdt.core.compiler.compliance=1.7
5 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
6 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
7 | org.eclipse.jdt.core.compiler.source=1.7
8 |
--------------------------------------------------------------------------------
/MacroRecorder/META-INF/MANIFEST.MF:
--------------------------------------------------------------------------------
1 | Manifest-Version: 1.0
2 | Bundle-ManifestVersion: 2
3 | Bundle-Name: MacroRecorder
4 | Bundle-SymbolicName: MacroRecorder;singleton:=true
5 | Bundle-Version: 1.0.0.qualifier
6 | Bundle-Activator: org.jtool.macrorecorder.Activator
7 | Require-Bundle: org.eclipse.ui;bundle-version="3.106.0",
8 | org.eclipse.core.runtime;bundle-version="3.10.0",
9 | org.eclipse.core.resources;bundle-version="3.9.1",
10 | org.eclipse.ui.ide;bundle-version="3.10.1",
11 | org.eclipse.ui.editors;bundle-version="3.8.200",
12 | org.eclipse.jface.text;bundle-version="3.9.1",
13 | org.eclipse.jdt.ui;bundle-version="3.10.1",
14 | org.eclipse.jdt.core;bundle-version="3.10.0",
15 | org.eclipse.ltk.core.refactoring;bundle-version="3.6.101"
16 | Bundle-RequiredExecutionEnvironment: JavaSE-1.8
17 | Bundle-ActivationPolicy: lazy
18 | Export-Package: org.jtool.macrorecorder.macro,
19 | org.jtool.macrorecorder.recorder,
20 | org.jtool.macrorecorder.util
21 |
--------------------------------------------------------------------------------
/MacroRecorder/build.properties:
--------------------------------------------------------------------------------
1 | source.. = src/
2 | output.. = bin/
3 | bin.includes = .,\
4 | META-INF/
5 | jre.compilation.profile = JavaSE-1.7
6 |
7 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/Activator.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder;
8 |
9 | import org.eclipse.ui.plugin.AbstractUIPlugin;
10 | import org.osgi.framework.BundleContext;
11 | import org.eclipse.ui.IWorkbenchWindow;
12 | import org.eclipse.ui.PlatformUI;
13 | import org.jtool.macrorecorder.recorder.Recorder;
14 |
15 | /**
16 | * The activator class controls the plug-in life cycle.
17 | * @author Katsuhisa Maruyama
18 | */
19 | public class Activator extends AbstractUIPlugin {
20 |
21 | /**
22 | * The plug-in ID.
23 | */
24 | public static final String PLUGIN_ID = "MacroRecorder";
25 |
26 | /**
27 | * The plug-in instance.
28 | */
29 | private static Activator plugin;
30 |
31 | /**
32 | * Creates a plug-in instance.
33 | */
34 | public Activator() {
35 | }
36 |
37 | /**
38 | * Performs actions when the plug-in is activated.
39 | * @param context the bundle context for this plug-in
40 | * @throws Exception if this plug-in did not start up properly
41 | */
42 | @Override
43 | public void start(BundleContext context) throws Exception {
44 | super.start(context);
45 | plugin = this;
46 |
47 | Recorder.getInstance().start();
48 |
49 | System.out.println(PLUGIN_ID + " activated.");
50 | }
51 |
52 | /**
53 | * Performs actions when when the plug-in is shut down.
54 | * @param context the bundle context for this plug-in
55 | * @throws Exception if this this plug-in fails to stop
56 | */
57 | @Override
58 | public void stop(BundleContext context) throws Exception {
59 | Recorder.getInstance().stop();
60 |
61 | super.stop(context);
62 |
63 | plugin = null;
64 | }
65 |
66 | /**
67 | * Returns the default plug-in instance.
68 | * @return the default plug-in instance
69 | */
70 | public static Activator getPlugin() {
71 | return plugin;
72 | }
73 |
74 | /**
75 | * Obtains the workbench window.
76 | * @return the workbench window
77 | */
78 | public static IWorkbenchWindow getWorkbenchWindow() {
79 | return PlatformUI.getWorkbench().getActiveWorkbenchWindow();
80 | }
81 | }
82 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/diff/CodeDelta.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.diff;
8 |
9 | /**
10 | * Manages the delta of code (the difference between two source files).
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class CodeDelta {
14 |
15 | /**
16 | * The type of code change operation.
17 | */
18 | enum Type {
19 | DELETE, INSERT, NULL
20 | }
21 |
22 | /**
23 | * The offset value of the text that contains this code delta.
24 | */
25 | private int offset;
26 |
27 | /**
28 | * The type of this code delta.
29 | */
30 | private Type type;
31 |
32 | /**
33 | * The text of the code delta.
34 | */
35 | private String text;
36 |
37 | /**
38 | * Creates an instance that stores information on change.
39 | * @param offset the offset value of the location where the change was applied
40 | * @param type the type of the change
41 | * @param text
42 | */
43 | public CodeDelta(int offset, Type type, String text) {
44 | this.offset = offset;
45 | this.type = type;
46 | this.text = text;
47 | }
48 |
49 | /**
50 | * Returns the offset value of the text that indicates the start point of the change.
51 | * @return the offset value for the change
52 | */
53 | int getOffset() {
54 | return offset;
55 | }
56 |
57 | /**
58 | * Returns the type of the change.
59 | * @return the code change type
60 | */
61 | Type getType() {
62 | return type;
63 | }
64 |
65 | /**
66 | * Returns the text that was inserted or deleted by the change.
67 | * @return the changed text
68 | */
69 | String getText() {
70 | return text;
71 | }
72 |
73 | /**
74 | * Returns the string for printing
75 | * @return the string information
76 | */
77 | public String toString() {
78 | return "-- Delta [" + String.valueOf(offset) + "] "+ type + " (" + text + ")";
79 | }
80 | }
81 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/diff/DiffMacroGenerator.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.diff;
8 |
9 | import org.jtool.macrorecorder.internal.diff.diff_match_patch.Diff;
10 | import org.jtool.macrorecorder.internal.diff.diff_match_patch.Operation;
11 | import org.jtool.macrorecorder.macro.DiffMacro;
12 | import java.util.ArrayList;
13 | import java.util.List;
14 | import java.util.LinkedList;
15 | import java.util.ListIterator;
16 |
17 | /**
18 | * Generates diff macros from differences between the contents of two the source files.
19 | * @author Katsuhisa Maruyama
20 | */
21 | public class DiffMacroGenerator {
22 |
23 | /**
24 | * The cost of an empty edit operation in terms of edit characters.
25 | */
26 | private static short editCost = 4;
27 |
28 | /**
29 | * Sets the edit costs for finding difference.
30 | * @param cost the edit cost to be set
31 | */
32 | public static void setEditCost(short cost) {
33 | editCost = cost;
34 | }
35 |
36 | /**
37 | * Generates diff macros from the differences between two textual contents.
38 | * @param time the time when this operation was inserted
39 | * @param path the name of the file path on which this operation was performed
40 | * @param otext the old contents of the file
41 | * @param ntext the new contents of the file
42 | * @return the collection of the generated diff macros
43 | */
44 | public static List generate(long time, String path, String otext, String ntext) {
45 | List macros = new ArrayList();
46 | List deltas = findDiff(otext, ntext);
47 |
48 | int offsetGap = 0;
49 | for (int idx = 0; idx < deltas.size(); idx++) {
50 | CodeDelta delta = deltas.get(idx);
51 |
52 | String itext = "";
53 | String dtext = "";
54 | if (delta.getType() == CodeDelta.Type.DELETE) {
55 | dtext = delta.getText();
56 |
57 | } else if (delta.getType() == CodeDelta.Type.INSERT) {
58 | itext = delta.getText();
59 | }
60 |
61 | int start = delta.getOffset() + offsetGap;
62 | DiffMacro macro = new DiffMacro(time, "Diff", path, start, itext, dtext);
63 | offsetGap = offsetGap - dtext.length();
64 |
65 | macros.add(macro);
66 | }
67 |
68 | return macros;
69 | }
70 |
71 | /**
72 | * Finds differences between the contents of two the source code files.
73 | * @param otext the contents of the source code file to be diffed
74 | * @param ntext the contents of the source code file to be diffed
75 | * @return the collection of the code deltas
76 | */
77 | private static List findDiff(String otext, String ntext) {
78 | diff_match_patch dmp = new diff_match_patch();
79 | dmp.Diff_EditCost = editCost;
80 |
81 | LinkedList diffs = dmp.diff_main(otext, ntext);
82 | dmp.diff_cleanupEfficiency(diffs);
83 | List deltas = getDeltas(diffs);
84 |
85 | return deltas;
86 | }
87 |
88 | /**
89 | * Obtains the deltas from a given difference information.
90 | * @param diffs the collection of difference information of the diff utility.
91 | * @return the collection of the code deltas
92 | */
93 | private static List getDeltas(LinkedList diffs) {
94 | ArrayList deltas = new ArrayList();
95 | int offset = 0;
96 |
97 | for (ListIterator pointer = diffs.listIterator(); pointer.hasNext(); ) {
98 | Diff diff = pointer.next();
99 |
100 | if (diff.operation == Operation.INSERT) {
101 | deltas.add(new CodeDelta(offset, CodeDelta.Type.INSERT, diff.text));
102 |
103 | } else if (diff.operation == Operation.DELETE) {
104 | deltas.add(new CodeDelta(offset, CodeDelta.Type.DELETE, diff.text));
105 | }
106 |
107 | offset = offset + diff.text.length();
108 | }
109 |
110 | return deltas;
111 | }
112 | }
113 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/CommandExecutionManager.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.jtool.macrorecorder.macro.ExecutionMacro;
10 | import org.jtool.macrorecorder.macro.TriggerMacro;
11 | import org.eclipse.core.commands.ExecutionEvent;
12 | import org.eclipse.core.commands.ExecutionException;
13 | import org.eclipse.core.commands.IExecutionListener;
14 | import org.eclipse.core.commands.NotHandledException;
15 | import org.eclipse.core.commands.common.NotDefinedException;
16 | import org.eclipse.ui.commands.ICommandService;
17 | import org.eclipse.ui.PlatformUI;
18 |
19 | /**
20 | * Manages command events (menu etc.).
21 | * @author Katsuhisa Maruyama
22 | */
23 | public class CommandExecutionManager implements IExecutionListener {
24 |
25 | /**
26 | * A recorder that records menu actions.
27 | */
28 | private MenuMacroRecorder recorder;
29 |
30 | /**
31 | * Creates an object that records command execution events.
32 | * @param recorder a recorder that records menu actions
33 | */
34 | public CommandExecutionManager(MenuMacroRecorder recorder) {
35 | this.recorder = recorder;
36 | }
37 |
38 | /**
39 | * Registers a command manager with the command service of the workbench.
40 | * @param cm the command manager
41 | */
42 | public static void register(CommandExecutionManager cm) {
43 | ICommandService cs = (ICommandService)PlatformUI.getWorkbench().getService(ICommandService.class);
44 | if (cs != null) {
45 | cs.addExecutionListener(cm);
46 | }
47 | }
48 |
49 | /**
50 | * Unregisters a command manager with the command service of the workbench.
51 | * @param cm the command manager
52 | */
53 | public static void unregister(CommandExecutionManager cm) {
54 | ICommandService cs = (ICommandService)PlatformUI.getWorkbench().getService(ICommandService.class);
55 | if (cs != null) {
56 | cs.removeExecutionListener(cm);
57 | }
58 | }
59 |
60 | /**
61 | * Receives a command that is about to execute.
62 | * @param commandId the identifier of the command that is about to execute
63 | * @param event the event that will be passed to the execute
method
64 | */
65 | @Override
66 | public void preExecute(String commandId, ExecutionEvent event) {
67 | long time = Time.getCurrentTime();
68 | String path = recorder.getActiveInputFilePath();
69 |
70 | ExecutionMacro macro = new ExecutionMacro(time, "Exec", path, commandId);
71 | recorder.recordExecutionMacro(macro);
72 |
73 | try {
74 | String id = event.getCommand().getCategory().getId();
75 | if (id.endsWith("category.refactoring")) {
76 | recorder.setParentMacro(macro);
77 |
78 | TriggerMacro trigger = new TriggerMacro(time, "Refactoring", path, TriggerMacro.Kind.BEGIN);
79 | recorder.recordTriggerMacro(trigger);
80 | }
81 | } catch (NotDefinedException e) {
82 | e.printStackTrace();
83 | }
84 | }
85 |
86 | /**
87 | * Receives a command that has failed to complete execution.
88 | * @param commandId the identifier of the command that has executed
89 | * @param returnValue the return value from the command; may be null
.
90 | */
91 | @Override
92 | public void postExecuteSuccess(String commandId, Object returnValue) {
93 | }
94 |
95 | /**
96 | * Receives a command with no handler.
97 | * @param commandId the identifier of command that is not handled
98 | * @param exception the exception that occurred
99 | */
100 | @Override
101 | public void notHandled(String commandId, NotHandledException exception) {
102 | }
103 |
104 | /**
105 | * Receives a command that has completed execution successfully.
106 | * @param commandId the identifier of the command that has executed
107 | * @param returnValue the return value from the command
108 | */
109 | @Override
110 | public void postExecuteFailure(String commandId, ExecutionException exception) {
111 | }
112 | }
113 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/DocMacroRecorderOffEdit.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.jtool.macrorecorder.recorder.Recorder;
10 | import org.jtool.macrorecorder.util.EditorUtilities;
11 | import org.jtool.macrorecorder.macro.DocumentMacro;
12 | import org.jtool.macrorecorder.macro.ExecutionMacro;
13 | import org.jtool.macrorecorder.macro.TriggerMacro;
14 | import org.jtool.macrorecorder.macro.ResourceMacro;
15 | import org.eclipse.core.resources.IFile;
16 | import org.eclipse.jface.text.IDocument;
17 |
18 | /**
19 | * Records document macros related to a file.
20 | * @author Katsuhisa Maruyama
21 | */
22 | public class DocMacroRecorderOffEdit extends DocMacroRecorder {
23 |
24 | /**
25 | * A file related to recorded macros.
26 | */
27 | private IFile file;
28 |
29 | /**
30 | * The document of a file.
31 | */
32 | private IDocument doc;
33 |
34 | /**
35 | * Creates an object that records document macros related to a file.
36 | * @param file the file
37 | * @param recorder a recorder that sends macro events
38 | */
39 | public DocMacroRecorderOffEdit(IFile file, Recorder recorder) {
40 | super(EditorUtilities.getInputFilePath(file), recorder);
41 |
42 | this.file = file;
43 | this.doc = EditorUtilities.getDocument(file);
44 | }
45 |
46 | /**
47 | * Starts the recording of document macros.
48 | */
49 | public void start() {
50 | if (file == null) {
51 | return;
52 | }
53 |
54 | DocumentManager.register(doc, null, documentManager);
55 |
56 | preCode = doc.get();
57 |
58 | super.start();
59 | }
60 |
61 | /**
62 | * Stops the recording of macros.
63 | */
64 | public void stop() {
65 | if (file == null) {
66 | return;
67 | }
68 |
69 | DocumentManager.unregister(doc, null, documentManager);
70 |
71 | super.stop();
72 | }
73 |
74 | /**
75 | * Records a document macro and its compressed macro.
76 | * @param macro the document macro
77 | */
78 | protected void recordDocumentMacro(DocumentMacro macro) {
79 | super.recordDocumentMacro(macro);
80 | }
81 |
82 | /**
83 | * Records a command execution macro.
84 | * @param macro the command execution macro
85 | */
86 | protected void recordExecutionMacro(ExecutionMacro macro) {
87 | super.recordExecutionMacro(macro);
88 | recordRawMacro(macro);
89 | }
90 |
91 | /**
92 | * Records a trigger macro.
93 | * @param macro the trigger macro
94 | */
95 | protected void recordTriggerMacro(TriggerMacro macro) {
96 | super.recordTriggerMacro(macro);
97 | }
98 |
99 | /**
100 | * Records a resource change macro.
101 | * @param macro the resource change macro
102 | */
103 | protected void recordResourceMacro(ResourceMacro macro) {
104 | super.recordResourceMacro(macro);
105 | }
106 |
107 | /**
108 | * Records a compressed macro into the operation history and its original one in .
109 | * @param macro a document macro
110 | */
111 | protected void recordUndoRedoMacro(DocumentMacro macro) {
112 | super.recordUndoRedoMacro(macro);
113 | }
114 |
115 | /**
116 | * Obtains the current contents of a file under recording.
117 | * @return the contents of source code, or null
if source code does not exist
118 | */
119 | protected String getCurrentCode() {
120 | IDocument doc = EditorUtilities.getDocument(file);
121 | if (doc != null) {
122 | return doc.get();
123 | }
124 | return null;
125 | }
126 | }
127 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/DocMacroRecorderOnEdit.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.jtool.macrorecorder.recorder.MacroCompressor;
10 | import org.jtool.macrorecorder.recorder.Recorder;
11 | import org.jtool.macrorecorder.util.EditorUtilities;
12 | import org.jtool.macrorecorder.macro.DocumentMacro;
13 | import org.jtool.macrorecorder.macro.ExecutionMacro;
14 | import org.jtool.macrorecorder.macro.TriggerMacro;
15 | import org.jtool.macrorecorder.macro.ResourceMacro;
16 | import org.jtool.macrorecorder.macro.CopyMacro;
17 | import org.eclipse.swt.custom.StyledText;
18 | import org.eclipse.ui.IEditorPart;
19 | import org.eclipse.jface.text.IDocument;
20 |
21 | /**
22 | * Records document macros performed on the editor.
23 | * @author Katsuhisa Maruyama
24 | */
25 | public class DocMacroRecorderOnEdit extends DocMacroRecorder {
26 |
27 | /**
28 | * An editor on which document macros are recorded.
29 | */
30 | private IEditorPart editor;
31 |
32 | /**
33 | * The document of a file.
34 | */
35 | private IDocument doc;
36 |
37 | /**
38 | * A compressor that compresses macros.
39 | */
40 | private MacroCompressor compressor;
41 |
42 | /**
43 | * The styled text of an editor.
44 | */
45 | private StyledText styledText;
46 |
47 | /**
48 | * Creates an object that records document macros performed on an editor.
49 | * @param editor the editor
50 | * @param recorder a recorder that sends macro events
51 | * @param compressor a compressor that compresses macros
52 | */
53 | public DocMacroRecorderOnEdit(IEditorPart editor, Recorder recorder, MacroCompressor compressor) {
54 | super(EditorUtilities.getInputFilePath(editor), recorder);
55 |
56 | this.editor = editor;
57 | this.doc = EditorUtilities.getDocument(editor);
58 | this.compressor = compressor;
59 | this.styledText = EditorUtilities.getStyledText(editor);
60 | }
61 |
62 | /**
63 | * Starts the recording of document macros.
64 | */
65 | public void start() {
66 | if (editor == null) {
67 | return;
68 | }
69 |
70 | DocumentManager.register(doc, styledText, documentManager);
71 |
72 | preCode = doc.get();
73 |
74 | super.start();
75 | }
76 |
77 | /**
78 | * Stops the recording of macros.
79 | */
80 | public void stop() {
81 | if (editor == null) {
82 | return;
83 | }
84 |
85 | DocumentManager.unregister(doc, styledText, documentManager);
86 |
87 | super.stop();
88 | }
89 |
90 | /**
91 | * Records a document macro and its compressed macro.
92 | * @param macro the document macro
93 | */
94 | protected void recordDocumentMacro(DocumentMacro macro) {
95 | boolean isCutPaste = setCutPasteMacro(macro);
96 | recordRawMacro(macro);
97 | // System.out.println("MACRO = " + macro);
98 |
99 | if (isCutPaste) {
100 | dumpMacros(macro);
101 | return;
102 | }
103 |
104 | if (compressor.canCombine(macro)) {
105 | DocumentMacro newMacro = compressor.combine(lastDocumentMacro, macro);
106 | if (newMacro != null) {
107 | lastDocumentMacro = newMacro;
108 | } else {
109 | dumpLastDocumentMacro();
110 | lastDocumentMacro = macro;
111 | }
112 | } else {
113 | dumpMacros(macro);
114 | }
115 | }
116 |
117 | /**
118 | * Tests if a macro indicates the cut or paste and sets its type according to its result.
119 | * @param macro a macro that might be a cut or paste one
120 | * @return true
if a macro indicates the cut or paste, otherwise false
121 | */
122 | boolean setCutPasteMacro(DocumentMacro macro) {
123 | if (lastRawMacro == null) {
124 | return false;
125 | }
126 |
127 | if (lastRawMacro instanceof ExecutionMacro) {
128 | ExecutionMacro emacro = (ExecutionMacro)lastRawMacro;
129 | if (emacro.getCommandId().compareTo("org.eclipse.ui.edit.cut") == 0) {
130 | macro.setType("Cut");
131 | return true;
132 | } else if (emacro.getCommandId().compareTo("org.eclipse.ui.edit.paste") == 0) {
133 | macro.setType("Paste");
134 | return true;
135 | }
136 | }
137 | return false;
138 | }
139 |
140 | /**
141 | * Records a command execution macro.
142 | * @param macro the command execution macro
143 | */
144 | protected void recordExecutionMacro(ExecutionMacro macro) {
145 | super.recordExecutionMacro(macro);
146 |
147 | if (styledText == null) {
148 | return;
149 | }
150 |
151 | if (macro.getCommandId().compareTo("org.eclipse.ui.edit.copy") == 0 ||
152 | macro.getCommandId().compareTo("org.eclipse.jdt.ui.edit.text.java.copy.qualified.name") == 0) {
153 | int offset = styledText.getSelectionRange().x;
154 | String text = styledText.getSelectionText();
155 |
156 | long time = Time.getCurrentTime();
157 | CopyMacro cmacro = new CopyMacro(time, "Copy", macro.getPath(), offset, text);
158 |
159 | recordRawMacro(cmacro);
160 | dumpMacros(cmacro);
161 |
162 | } else if (macro.getCommandId().compareTo("org.eclipse.ui.edit.delete") == 0) {
163 | macro.setType("Delete");
164 | }
165 | }
166 |
167 | /**
168 | * Records a trigger macro.
169 | * @param macro the trigger macro
170 | */
171 | protected void recordTriggerMacro(TriggerMacro macro) {
172 | super.recordTriggerMacro(macro);
173 | }
174 |
175 | /**
176 | * Records a resource change macro.
177 | * @param macro the resource change macro
178 | */
179 | protected void recordResourceMacro(ResourceMacro macro) {
180 | super.recordResourceMacro(macro);
181 | }
182 |
183 | /**
184 | * Records a compressed macro into the operation history and its original one in .
185 | * @param macro a document macro
186 | */
187 | protected void recordUndoRedoMacro(DocumentMacro macro) {
188 | super.recordUndoRedoMacro(macro);
189 | }
190 |
191 | /**
192 | * Obtains the current contents of a file under recording.
193 | * @return the contents of source code, or null
if source code does not exist
194 | */
195 | protected String getCurrentCode() {
196 | IDocument doc = EditorUtilities.getDocument(editor);
197 | if (doc != null) {
198 | return doc.get();
199 | }
200 | return null;
201 | }
202 | }
203 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/MenuMacroRecorder.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.jtool.macrorecorder.Activator;
10 | import org.jtool.macrorecorder.recorder.Recorder;
11 | import org.jtool.macrorecorder.util.EditorUtilities;
12 | import org.jtool.macrorecorder.macro.CompoundMacro;
13 | import org.jtool.macrorecorder.macro.Macro;
14 | import org.jtool.macrorecorder.macro.ExecutionMacro;
15 | import org.jtool.macrorecorder.macro.TriggerMacro;
16 | import org.jtool.macrorecorder.macro.ResourceMacro;
17 | import org.eclipse.ui.IWorkbenchWindow;
18 | import org.eclipse.jface.viewers.ISelection;
19 | import org.eclipse.jface.text.ITextSelection;
20 |
21 | import java.util.ArrayList;
22 | import java.util.List;
23 |
24 | /**
25 | * Records macros performed on the editor.
26 | * @author Katsuhisa Maruyama
27 | */
28 | public class MenuMacroRecorder {
29 |
30 | /**
31 | * A recorder that sends all kinds of macro events.
32 | */
33 | private Recorder recorder;
34 |
35 | /**
36 | * The collection of raw macros that were recorded.
37 | */
38 | private List rawMacros = new ArrayList();
39 |
40 | /**
41 | * A compound macro that contains macros.
42 | */
43 | private CompoundMacro compoundMacro;
44 |
45 | /**
46 | * A manger that manages command execution events.
47 | */
48 | private CommandExecutionManager commandManager;
49 |
50 | /**
51 | * A manger that manages refactoring execution events.
52 | */
53 | private RefactoringExecutionManager refactoringManager;
54 |
55 | /**
56 | * A manager that records operations related to resource changes in the Java model.
57 | */
58 | private ResourceChangedManager resourceChangeManager;
59 |
60 | /**
61 | * A parent macro on which the current recorded macro dangles
62 | */
63 | private Macro parentMacro;
64 |
65 | /**
66 | * The single instance of this menu recorder
67 | */
68 | private static MenuMacroRecorder instance = new MenuMacroRecorder();
69 |
70 | /**
71 | * Creates an empty object.
72 | */
73 | private MenuMacroRecorder() {
74 | commandManager = new CommandExecutionManager(this);
75 | refactoringManager = new RefactoringExecutionManager(this);
76 | resourceChangeManager = new ResourceChangedManager(this);
77 | }
78 |
79 | /**
80 | * Sets the recorder that sends all kinds of macro events.
81 | * @param recorder the recorder.
82 | */
83 | public void setRecorder(Recorder recorder) {
84 | this.recorder = recorder;
85 | }
86 |
87 | /**
88 | * Returns the single instance of this menu recorder.
89 | * @return the single instance
90 | */
91 | public static MenuMacroRecorder getInstance() {
92 | return instance;
93 | }
94 |
95 | /**
96 | * Starts the recording of menu actions.
97 | */
98 | public void start() {
99 | CommandExecutionManager.register(commandManager);
100 | RefactoringExecutionManager.register(refactoringManager);
101 | ResourceChangedManager.register(resourceChangeManager);
102 |
103 | rawMacros.clear();
104 | compoundMacro = null;
105 | parentMacro = null;
106 | }
107 |
108 | /**
109 | * Stops the recording of menu actions.
110 | */
111 | public void stop() {
112 | CommandExecutionManager.unregister(commandManager);
113 | RefactoringExecutionManager.unregister(refactoringManager);
114 | ResourceChangedManager.unregister(resourceChangeManager);
115 |
116 | rawMacros.clear();
117 | }
118 |
119 | /**
120 | * Sets a parent macro related to a file.
121 | * @param parent the parent macro, or null
if no parent exists
122 | */
123 | void setParentMacro(Macro parent) {
124 | parentMacro = parent;
125 | }
126 |
127 | /**
128 | * Returns the parent macro.
129 | * @return the parent macro
130 | */
131 | Macro getParentMacro() {
132 | return parentMacro;
133 | }
134 |
135 | /**
136 | * Records a command execution macro.
137 | * @param macro the command execution macro
138 | */
139 | protected void recordExecutionMacro(ExecutionMacro macro) {
140 | breakMacro();
141 |
142 | String path = macro.getPath();
143 | DocMacroRecorder docMacroRecorder = getDocMacroRecorder(path);
144 | if (docMacroRecorder != null) {
145 | docMacroRecorder.recordExecutionMacro(macro);
146 |
147 | } else {
148 | recordRawMacro(macro);
149 | recordMacro(macro);
150 | }
151 | }
152 |
153 | /**
154 | * Records a trigger macro.
155 | * @param macro the trigger macro
156 | */
157 | protected void recordTriggerMacro(TriggerMacro macro) {
158 | breakMacro();
159 |
160 | String path = macro.getPath();
161 | DocMacroRecorder docMacroRecorder = getDocMacroRecorder(path);
162 | if (docMacroRecorder != null) {
163 | docMacroRecorder.recordTriggerMacro(macro);
164 |
165 | } else {
166 | recordRawMacro(macro);
167 | recordMacro(macro);
168 | }
169 | }
170 |
171 | /**
172 | * Records a resource change macro.
173 | * @param macro the resource change macro
174 | */
175 | protected void recordResourceMacro(ResourceMacro macro) {
176 | breakMacro();
177 |
178 | String path = macro.getPath();
179 | DocMacroRecorder docMacroRecorder = getDocMacroRecorder(path);
180 |
181 | if (docMacroRecorder != null) {
182 | macro.setOnEdit(true);
183 | docMacroRecorder.recordResourceMacro(macro);
184 |
185 | } else {
186 | macro.setOnEdit(false);
187 | recordRawMacro(macro);
188 | recordMacro(macro);
189 | }
190 | }
191 |
192 | /**
193 | * Records a raw macro.
194 | * @param macro the raw macro to be recored
195 | */
196 | private void recordRawMacro(Macro macro) {
197 | rawMacros.add(macro);
198 | recorder.notifyRawMacro(macro);
199 | }
200 |
201 | /**
202 | * Records a macro.
203 | * @param macro the macro to be recorded
204 | */
205 | private void recordMacro(Macro macro) {
206 | if (macro instanceof TriggerMacro) {
207 | TriggerMacro tmacro = (TriggerMacro)macro;
208 | if (compoundMacro == null && tmacro.isBegin()) {
209 | compoundMacro = new CompoundMacro(tmacro.getStartTime(), tmacro.getType(), macro.getPath());
210 |
211 | } else if (tmacro.isEnd() || tmacro.isCursorChange()) {
212 | if (compoundMacro != null) {
213 | compoundMacro.setRawMacros(new ArrayList(rawMacros));
214 | compoundMacro.setTimes();
215 | rawMacros.clear();
216 |
217 | recorder.notifyMacro(compoundMacro);
218 | }
219 | compoundMacro = null;
220 | }
221 |
222 | } else {
223 | if (compoundMacro != null) {
224 | compoundMacro.addMacro(macro);
225 | } else {
226 | macro.setRawMacros(new ArrayList(rawMacros));
227 | rawMacros.clear();
228 |
229 | recorder.notifyMacro(macro);
230 | }
231 | }
232 | }
233 |
234 | /**
235 | * Returns the a recorder that records macros related to a file
236 | * @param path the path of the file
237 | * @return the recorder
238 | */
239 | protected DocMacroRecorder getDocMacroRecorder(String path) {
240 | if (path == null) {
241 | return null;
242 | }
243 |
244 | return Recorder.getDocRecorder(path);
245 | }
246 |
247 | /**
248 | * Break the current macro.
249 | */
250 | public void breakMacro() {
251 | for (DocMacroRecorder docRecorder : Recorder.getDocRecorders()) {
252 | docRecorder.dumpLastDocumentMacro();
253 | docRecorder.needDiff();
254 | }
255 | }
256 |
257 | /**
258 | * Obtains the path of a active file existing on an editor.
259 | * @return @return the path of the file, or null
if none
260 | */
261 | protected String getActiveInputFilePath() {
262 | IWorkbenchWindow window = Activator.getPlugin().getWorkbench().getActiveWorkbenchWindow();
263 | if (window != null) {
264 | ISelection selection = window.getSelectionService().getSelection();
265 | if (selection instanceof ITextSelection) {
266 | return EditorUtilities.getActiveInputFilePath();
267 | }
268 | }
269 | return null;
270 | }
271 | }
272 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/RefactoringExecutionManager.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.jtool.macrorecorder.macro.Macro;
10 | import org.jtool.macrorecorder.macro.TriggerMacro;
11 | import org.eclipse.ltk.core.refactoring.RefactoringCore;
12 | import org.eclipse.ltk.core.refactoring.history.IRefactoringExecutionListener;
13 | import org.eclipse.ltk.core.refactoring.history.RefactoringExecutionEvent;
14 | import org.eclipse.ltk.core.refactoring.history.IRefactoringHistoryListener;
15 | import org.eclipse.ltk.core.refactoring.history.RefactoringHistoryEvent;
16 | import org.eclipse.ltk.core.refactoring.history.IRefactoringHistoryService;
17 |
18 | /**
19 | * Manages refactoring events.
20 | * @author Katsuhisa Maruyama
21 | */
22 | public class RefactoringExecutionManager implements IRefactoringExecutionListener, IRefactoringHistoryListener {
23 |
24 | /**
25 | * A recorder that records menu actions.
26 | */
27 | private MenuMacroRecorder recorder;
28 |
29 | /**
30 | * Creates an object that records refectoring execution events.
31 | * @param recorder a recorder that records menu actions
32 | */
33 | public RefactoringExecutionManager(MenuMacroRecorder recorder) {
34 | this.recorder = recorder;
35 | }
36 |
37 | /**
38 | * Registers a refactoring execution manager with the refactoring history service.
39 | * @param rm the refactoring execution manager
40 | */
41 | public static void register(RefactoringExecutionManager rm) {
42 | IRefactoringHistoryService rs = RefactoringCore.getHistoryService();
43 | if (rs != null) {
44 | rs.addExecutionListener(rm);
45 | // rs.addHistoryListener(rm);
46 | }
47 | }
48 |
49 | /**
50 | * Unregisters a refactoring execution manager with the refactoring history service.
51 | * @param rm the refactoring execution manager
52 | */
53 | public static void unregister(RefactoringExecutionManager rm) {
54 | IRefactoringHistoryService rs = RefactoringCore.getHistoryService();
55 | if (rs != null) {
56 | rs.removeExecutionListener(rm);
57 | // rs.removeHistoryListener(rm);
58 | }
59 | }
60 |
61 | /**
62 | * Receives an event when a refactoring execution event happened.
63 | * @param event the refactoring execution event
64 | */
65 | @Override
66 | public void executionNotification(RefactoringExecutionEvent event) {
67 | long time = Time.getCurrentTime();
68 | Macro macro = recorder.getParentMacro();
69 | String path = null;
70 | if (macro != null) {
71 | path = macro.getPath();
72 | }
73 |
74 | String commandId = event.getDescriptor().getDescription();
75 | if (event.getEventType() == RefactoringExecutionEvent.ABOUT_TO_PERFORM) {
76 | TriggerMacro trigger = new TriggerMacro(time, commandId, path, TriggerMacro.Kind.BEGIN);
77 | recorder.recordTriggerMacro(trigger);
78 |
79 | } else if (event.getEventType() == RefactoringExecutionEvent.PERFORMED) {
80 | TriggerMacro trigger = new TriggerMacro(time, commandId, path, TriggerMacro.Kind.END);
81 | path = null;
82 | recorder.recordTriggerMacro(trigger);
83 |
84 | recorder.setParentMacro(null);
85 | }
86 | }
87 |
88 | /**
89 | * Receives an event when a refactoring history event happened.
90 | * @param event the refactoring history event
91 | */
92 | @Override
93 | public void historyNotification(RefactoringHistoryEvent event) {
94 | }
95 | }
96 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/ResourceChangedManager.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import org.eclipse.jdt.core.IElementChangedListener;
10 | import org.eclipse.jdt.core.ElementChangedEvent;
11 | import org.eclipse.jdt.core.IJavaElementDelta;
12 | import org.eclipse.jdt.core.IJavaElement;
13 | import org.eclipse.jdt.core.JavaCore;
14 | import org.jtool.macrorecorder.macro.ResourceMacro;
15 | import java.util.List;
16 | import java.util.ArrayList;
17 |
18 | /**
19 | * Manages operations related to element changes.
20 | * @author Katsuhisa Maruyama
21 | */
22 | public class ResourceChangedManager implements IElementChangedListener {
23 |
24 | /**
25 | * A recorder that records menu actions.
26 | */
27 | private MenuMacroRecorder recorder;
28 |
29 | /**
30 | * Creates an object that records resource change events.
31 | * @param recorder a recorder that records menu actions
32 | */
33 | public ResourceChangedManager(MenuMacroRecorder recorder) {
34 | this.recorder = recorder;
35 | }
36 |
37 | /**
38 | * Registers an element change manager with the Java model.
39 | * @param em the element change manager
40 | */
41 | public static void register(ResourceChangedManager em) {
42 | JavaCore.addElementChangedListener(em);
43 | }
44 |
45 | /**
46 | * Unregisters an element change manager with the Java model.
47 | * @param em the element change manager
48 | */
49 | public static void unregister(ResourceChangedManager em) {
50 | JavaCore.removeElementChangedListener(em);
51 | }
52 |
53 | /**
54 | * Receives an event when one or more Java elements have changed.
55 | * @param event the change event
56 | */
57 | @Override
58 | public void elementChanged(ElementChangedEvent event) {
59 | long time = Time.getCurrentTime();
60 | ChangeCollector collector = new ChangeCollector(event.getDelta());
61 |
62 | for (IJavaElementDelta delta : collector.deltas) {
63 | if (delta.getKind() == IJavaElementDelta.REMOVED) {
64 | ResourceMacro macro = createResourceRemovedMacro(time, delta);
65 | if (macro != null) {
66 | recorder.recordResourceMacro(macro);
67 | }
68 | }
69 | }
70 |
71 | for (IJavaElementDelta delta : collector.deltas) {
72 | if (delta.getKind() == IJavaElementDelta.ADDED) {
73 | ResourceMacro macro = createResourceAddedMacro(time, delta);
74 | if (macro != null) {
75 | recorder.recordResourceMacro(macro);
76 | }
77 | }
78 | }
79 |
80 | for (IJavaElementDelta delta : collector.deltas) {
81 | if (delta.getKind() == IJavaElementDelta.CHANGED) {
82 | ResourceMacro macro = createResourceChangedMacro(time, delta);
83 | if (macro != null) {
84 | recorder.recordResourceMacro(macro);
85 | }
86 | }
87 | }
88 | }
89 |
90 | /**
91 | * Creates a macro corresponding to the removed delta of the change.
92 | * @param time the time when the change occurred
93 | * @param delta the removed delta of the change
94 | * @return the created resource macro
95 | */
96 | private ResourceMacro createResourceRemovedMacro(long time, IJavaElementDelta delta) {
97 | IJavaElement elem = delta.getElement();
98 | String path = elem.getPath().toString();
99 | if (path == null) {
100 | return null;
101 | }
102 |
103 | String type = "Removed";
104 | if ((delta.getFlags() & IJavaElementDelta.F_MOVED_TO) != 0) {
105 | if (isRenamed(delta.getElement(), delta.getMovedToElement())) {
106 | type = "RenamedTo";
107 | } else {
108 | type = "MovedTo";
109 | }
110 | }
111 |
112 | return new ResourceMacro(time, type, path, elem);
113 | }
114 |
115 | /**
116 | * Creates a macro corresponding to the added delta of the change.
117 | * @param time the time when the change occurred
118 | * @param delta the added delta of the change
119 | * @return the created resource macro
120 | */
121 | private ResourceMacro createResourceAddedMacro(long time, IJavaElementDelta delta) {
122 | IJavaElement elem = delta.getElement();
123 | String path = elem.getPath().toString();
124 | if (path == null) {
125 | return null;
126 | }
127 |
128 | String type = "Added";
129 | if ((delta.getFlags() & IJavaElementDelta.F_MOVED_FROM) != 0) {
130 | if (isRenamed(delta.getElement(), delta.getMovedFromElement())) {
131 | type = "RenamedFrom";
132 | } else {
133 | type = "MovedFrom";
134 | }
135 | }
136 |
137 | return new ResourceMacro(time, type, path, elem);
138 | }
139 |
140 | /**
141 | * Creates a macro corresponding to the changed delta of the change.
142 | * @param time the time when the change occurred
143 | * @param delta the changed delta of the change
144 | * @return the created resource macro
145 | */
146 | private ResourceMacro createResourceChangedMacro(long time, IJavaElementDelta delta) {
147 | IJavaElement elem = delta.getElement();
148 | String path = elem.getPath().toString();
149 | if (path == null) {
150 | return null;
151 | }
152 |
153 | if ((delta.getFlags() & IJavaElementDelta.F_CONTENT) != 0) {
154 | // System.out.println("CONTENT CHANGED" + path);
155 | return null;
156 | }
157 |
158 | return new ResourceMacro(time, "Changed", path, elem);
159 | }
160 |
161 | /**
162 | * Tests if the element was renamed by the change.
163 | * @param before the element before the change
164 | * @param after the element after the change
165 | * @return true
if renaming was applied, otherwise false
166 | */
167 | private boolean isRenamed(IJavaElement before, IJavaElement after) {
168 | if (before == null || after == null) {
169 | return true;
170 | }
171 |
172 | String beforen = ResourceMacro.getName(before);
173 | String aftern = ResourceMacro.getName(after);
174 | if (beforen.compareTo(aftern) != 0) {
175 | return true;
176 | }
177 | return false;
178 | }
179 |
180 | /**
181 | * Collects change deltas.
182 | */
183 | class ChangeCollector {
184 |
185 | /**
186 | * The collection of change deltas
187 | */
188 | List deltas = new ArrayList();
189 |
190 | /**
191 | * Creates an object that collects the deltas of element changes.
192 | * @param delta the root delta of the change
193 | */
194 | ChangeCollector(IJavaElementDelta delta) {
195 | collectDeltas(delta);
196 | }
197 |
198 | /**
199 | * Collects all the deltas of the changes.
200 | * @param delta the root delta of the change
201 | * @param deltas the collection of the deltas to be collected
202 | */
203 | private void collectDeltas(IJavaElementDelta delta) {
204 | if (delta.getKind() == IJavaElementDelta.ADDED ||
205 | delta.getKind() == IJavaElementDelta.REMOVED) {
206 | if (!contain(delta)) {
207 | deltas.add(delta);
208 | }
209 | } else if (delta.getKind() == IJavaElementDelta.CHANGED &&
210 | ((delta.getFlags() & IJavaElementDelta.F_CONTENT) != 0)) {
211 | if (!contain(delta)) {
212 | deltas.add(delta);
213 | }
214 | }
215 |
216 | for (IJavaElementDelta d : delta.getAffectedChildren()) {
217 | collectDeltas(d);
218 | }
219 | }
220 |
221 | /**
222 | * Tests if a given change delta was already contained in the change collection.
223 | * @param delta the change delta
224 | * @return true
if the change delta was contained in the change collection, otherwise false
225 | */
226 | private boolean contain(IJavaElementDelta delta) {
227 | String path = delta.getElement().getPath().toString();
228 | for (IJavaElementDelta d : deltas) {
229 | String p = d.getElement().getPath().toString();
230 | if (p.compareTo(path) == 0 && d.getKind() == delta.getKind()) {
231 | return true;
232 | }
233 | }
234 | return false;
235 | }
236 | }
237 | }
238 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/internal/recorder/Time.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.internal.recorder;
8 |
9 | import java.util.Calendar;
10 |
11 | /**
12 | * Obtains time information.
13 | * @author Katsuhisa Maruyama
14 | */
15 | class Time {
16 |
17 | /**
18 | * Obtains the current time.
19 | * @return the current time
20 | */
21 | static long getCurrentTime() {
22 | Calendar cal = Calendar.getInstance();
23 | return cal.getTimeInMillis();
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/CancelMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores a cancel macro that cancels another macro.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class CancelMacro extends DocumentMacro {
14 |
15 | /**
16 | * Creates an object storing information on a cancel macro.
17 | * @param time the time when the macro started and ended
18 | * @param type the type of the macro
19 | * @param path the path of a file or a package this macro was performed
20 | * @param start the leftmost offset of the document changed by this macro
21 | * @param itext the contents of the document inserted by the macro
22 | * @param dtext the contents of the document deleted by the macro
23 | */
24 | public CancelMacro(long time, String type, String path, int start, String itext, String dtext) {
25 | super(time, time, type, path, start, itext, dtext);
26 | }
27 |
28 | /**
29 | * Returns the string for printing, which does not contain a new line character at its end.
30 | * @return the string for printing
31 | */
32 | public String toString() {
33 | return "CANCEL = " + getStartTime() + "-" + getEndTime() + ": " +
34 | getPath() + " " + getStart() + " " + "[" + getInsertedText() + "][" + getDeletedText() + "]";
35 | }
36 | }
37 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/CompoundMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | import java.util.ArrayList;
10 | import java.util.List;
11 |
12 | /**
13 | * Stores a compound macro that contains macros.
14 | * @author Katsuhisa Maruyama
15 | */
16 | public class CompoundMacro extends Macro {
17 |
18 | /**
19 | * The collection of macros contained in this compound macro.
20 | */
21 | private List macros = new ArrayList();
22 |
23 | /**
24 | * Creates an object storing information on a compound macro.
25 | * @param stime the time when the macro started
26 | * @param the type of the macro
27 | * @param path the path of a file or a package this macro was performed
28 | */
29 | public CompoundMacro(long stime, String type, String path) {
30 | super(stime, stime, type, path);
31 | }
32 |
33 | /**
34 | * Adds a macro into this compound macro.
35 | * @param macro the macro to be added
36 | */
37 | public void addMacro(Macro macro) {
38 | macros.add(macro);
39 | }
40 |
41 | /**
42 | * Removes a macro from this compound macro.
43 | * @param the index number of the macro to be removed
44 | */
45 | public void removeMacro(int index) {
46 | macros.remove(index);
47 | }
48 |
49 | /**
50 | * Removes a macro that will be canceled by a given macro.
51 | * @param macro the macro that cancels the macro stored in this compound macro
52 | * @return true
if the cancellation succeeded, otherwise false
53 | */
54 | public boolean cancelMacro(DocumentMacro macro) {
55 | int index = getIndexOfCorrespondingMacro(macro);
56 | if (index < 0) {
57 | return false;
58 | }
59 |
60 | macros.remove(index);
61 | return true;
62 | }
63 |
64 | /**
65 | * Returns the collection of macros contained in this compound macro.
66 | * @return the the collection of the contained macros
67 | */
68 | public List getMacros() {
69 | return macros;
70 | }
71 |
72 | /**
73 | * Sets the starting and ending times.
74 | */
75 | public void setTimes() {
76 | for (Macro m : macros) {
77 | if (m.getStartTime() < startTime) {
78 | startTime = m.getStartTime();
79 | }
80 | if (m.getEndTime() > endTime) {
81 | endTime = m.getEndTime();
82 | }
83 | }
84 | }
85 |
86 | /**
87 | * Obtains the index number of the macro corresponding to a given macro.
88 | * @param macro the given macro
89 | * @return the index number of the corresponding macro
90 | */
91 | private int getIndexOfCorrespondingMacro(DocumentMacro macro) {
92 | for (int i = 0; i < macros.size(); i++) {
93 | Macro m = macros.get(i);
94 | if (m instanceof DocumentMacro) {
95 | DocumentMacro dm = (DocumentMacro)m;
96 | if (dm.getStart() == macro.getStart() &&
97 | dm.getInsertedText().compareTo(macro.getDeletedText()) == 0 &&
98 | dm.getDeletedText().compareTo(macro.getInsertedText()) == 0) {
99 | return i;
100 | }
101 | }
102 | }
103 | return -1;
104 | }
105 |
106 | /**
107 | * Returns the string for printing, which does not contain a new line character at its end.
108 | * @return the string for printing
109 | */
110 | public String toString() {
111 | return "COMP(" + getType() + ") = " + getPath() + " " +
112 | getStartTime() + "-" + getEndTime();
113 | }
114 | }
115 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/CopyMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores a macro occurring copy.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class CopyMacro extends Macro {
14 |
15 | /**
16 | * The leftmost offset of the document copied by this macro.
17 | */
18 | private int start;
19 |
20 | /**
21 | * The contents of the document copied by this macro.
22 | */
23 | private String copiedText;
24 |
25 | /**
26 | * Creates an object storing information on a copy macro.
27 | * @param time the time when the macro started and ended
28 | * @param type the type of the macro
29 | * @param path the path of a file or a package this macro was performed
30 | * @param start the leftmost offset of the document changed by this macro
31 | * @param text the contents of the document copied by the macro
32 | */
33 | public CopyMacro(long time, String type, String path, int start, String text) {
34 | super(time, time, type, path);
35 | this.start = start;
36 | this.copiedText = text;
37 | }
38 |
39 | /**
40 | * Returns the leftmost offset of the document changed by this macro.
41 | * @return the leftmost offset of the document
42 | */
43 | public int getStart() {
44 | return start;
45 | }
46 |
47 | /**
48 | * Returns the contents of the document copied by this macro.
49 | * @return the copied contents of the document
50 | */
51 | public String getCopiedText() {
52 | return copiedText;
53 | }
54 |
55 | /**
56 | * Returns the string for printing, which does not contain a new line character at its end.
57 | * @return the string for printing
58 | */
59 | public String toString() {
60 | return "COPY = " + getStartTime() + "-" + getEndTime() + ": " +
61 | getPath() + " " + getStart() + " " + "[" + getCopiedText() + "]";
62 | }
63 | }
64 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/DiffMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores a macro that represents difference between two versions of source code.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class DiffMacro extends DocumentMacro {
14 |
15 | /**
16 | * Creates an object storing information on a difference macro.
17 | * @param time the time when the macro started and ended
18 | * @param type the type of the macro
19 | * @param path the path of a file or a package this macro was performed
20 | * @param start the leftmost offset of the document changed by this macro
21 | * @param itext the contents of the document inserted by the macro
22 | * @param dtext the contents of the document deleted by the macro
23 | */
24 | public DiffMacro(long time, String type, String path, int start, String itext, String dtext) {
25 | super(time, time, type, path, start, itext, dtext);
26 | }
27 |
28 | /**
29 | * Returns the string for printing, which does not contain a new line character at its end.
30 | * @return the string for printing
31 | */
32 | public String toString() {
33 | return "DIFF = " + getStartTime() + "-" + getEndTime() + ": " +
34 | getPath() + " " + getStart() + " " + "[" + getInsertedText() + "][" + getDeletedText() + "]";
35 | }
36 | }
37 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/DocumentMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores a macro occurring a document change.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class DocumentMacro extends Macro {
14 |
15 | /**
16 | * The leftmost offset of the document changed by this macro.
17 | */
18 | private int start;
19 |
20 | /**
21 | * The contents of the document inserted by this macro.
22 | */
23 | private String insertedText;
24 |
25 | /**
26 | * The contents of the document deleted by this macro.
27 | */
28 | private String deletedText;
29 |
30 | /**
31 | * Creates an object storing information on a document macro.
32 | * @param stime the time when the macro started
33 | * @param etime the time when the macro ended
34 | * @param type the type of the macro
35 | * @param path the path of a file or a package this macro was performed
36 | * @param start the leftmost offset of the document changed by this macro
37 | * @param itext the contents of the document inserted by the macro
38 | * @param dtext the contents of the document deleted by the macro
39 | */
40 | public DocumentMacro(long stime, long etime, String type, String path, int start, String itext, String dtext) {
41 | super(stime, etime, type, path);
42 | this.start = start;
43 | this.insertedText = itext;
44 | this.deletedText = dtext;
45 | }
46 |
47 | /**
48 | * Creates an object storing information on a document macro.
49 | * @param time the time when the macro started and ended
50 | * @param type the type of the macro
51 | * @param path the path of a file or a package this macro was performed
52 | * @param start the leftmost offset of the document changed by this macro
53 | * @param itext the contents of the document inserted by the macro
54 | * @param dtext the contents of the document deleted by the macro
55 | */
56 | public DocumentMacro(long time, String type, String path, int start, String itext, String dtext) {
57 | this(time, time, type, path, start, itext, dtext);
58 | }
59 |
60 | /**
61 | * Returns the leftmost offset of the document changed by this macro.
62 | * @return the leftmost offset of the document
63 | */
64 | public int getStart() {
65 | return start;
66 | }
67 |
68 | /**
69 | * Returns the contents of the document inserted by this macro.
70 | * @return the inserted contents of the document
71 | */
72 | public String getInsertedText() {
73 | return insertedText;
74 | }
75 |
76 | /**
77 | * Returns the contents of the document deleted by this macro.
78 | * @return the deleted contents of the document
79 | */
80 | public String getDeletedText() {
81 | return deletedText;
82 | }
83 |
84 | /**
85 | * Tests if this macro inserts any text and deletes no text.
86 | * @return true
if this macro performs insertion, otherwise false>
87 | */
88 | public boolean isInsert() {
89 | return insertedText.length() != 0 && deletedText.length() == 0;
90 | }
91 |
92 | /**
93 | * Tests if this macro inserts no text and deletes any text.
94 | * @return true
if this macro performs deletion, otherwise false>
95 | */
96 | public boolean isDelete() {
97 | return insertedText.length() == 0 && deletedText.length() != 0;
98 | }
99 |
100 | /**
101 | * Tests if this macro inserts any text and deletes any text.
102 | * @return true
if this macro performs replacement, otherwise false>
103 | */
104 | public boolean isReplace() {
105 | return insertedText.length() != 0 && deletedText.length() != 0;
106 | }
107 |
108 | /**
109 | * Returns the string for printing, which does not contain a new line character at its end.
110 | * @return the string for printing
111 | */
112 | public String toString() {
113 | return "DOC(" + getType() + ") = " + getStartTime() + "-" + getEndTime() + ": " +
114 | getPath() + " " + getStart() + " " + "[" + getInsertedText() + "][" + getDeletedText() + "]";
115 | }
116 | }
117 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/ExecutionMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores an execution macro.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class ExecutionMacro extends Macro {
14 |
15 | /**
16 | * The string representing the contents of this macro.
17 | */
18 | private String commandId;
19 |
20 | /**
21 | * Creates an object storing information on an execution macro.
22 | * @param time the time when the macro started
23 | * @param type the type of the macro
24 | * @param path the path of a file or a package this macro was performed
25 | * @param commandId the string representing the contents of the macro
26 | */
27 | public ExecutionMacro(long time, String type, String path, String commandId) {
28 | super(time, time, type, path);
29 | this.commandId = commandId;
30 | }
31 |
32 | /**
33 | * Returns the string representing the contents of this macro.
34 | * @return the information on this macro
35 | */
36 | public String getCommandId() {
37 | return commandId;
38 | }
39 |
40 | /**
41 | * Returns the string for printing, which does not contain a new line character at its end.
42 | * @return the string for printing
43 | */
44 | public String toString() {
45 | return "EXEC = " + getStartTime() + "-" + getEndTime() + ": " +
46 | getPath() + " " + getCommandId();
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/Macro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | import java.util.List;
10 |
11 | /**
12 | * Stores a macro.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public class Macro {
16 |
17 | /**
18 | * The time when this macro started.
19 | */
20 | protected long startTime;
21 |
22 | /**
23 | * The time when this macro ended.
24 | */
25 | protected long endTime;
26 |
27 | /**
28 | * The type of this macro.
29 | */
30 | protected String type;
31 |
32 | /**
33 | * The path of a file or a package this macro was performed.
34 | */
35 | private String path;
36 |
37 | /**
38 | * The collection of raw macros that were recorded.
39 | */
40 | private List rawMacros;
41 |
42 | /**
43 | * Creates an object storing information on a macro.
44 | * @param stime the time when the macro started
45 | * @param etime the time when the macro ended
46 | * @param type the type of the macro
47 | * @param path the path of a file or a package this macro was performed
48 | */
49 | public Macro(long stime, long etime, String type, String path) {
50 | this.startTime = stime;
51 | this.endTime = etime;
52 | this.type = type;
53 | this.path = path;
54 | }
55 |
56 | /**
57 | * Creates an object storing information on a macro.
58 | * @param time the time when the macro started and ended
59 | * @param type the type of the macro
60 | * @param path the path of a file or a package this macro was performed
61 | */
62 | public Macro(long time, String type, String path) {
63 | this(time, time, type, path);
64 | }
65 |
66 | /**
67 | * Returns the time when this command started
68 | * @return the starting time of this macro
69 | */
70 | public long getStartTime() {
71 | return startTime;
72 | }
73 |
74 | /**
75 | * Returns the time when this macro ended
76 | * @return the ending time of this macro
77 | */
78 | public long getEndTime() {
79 | return endTime;
80 | }
81 |
82 | /**
83 | * Sets the type of this macro
84 | * @param type the type of the macro
85 | */
86 | public void setType(String type) {
87 | this.type = type;
88 | }
89 |
90 | /**
91 | * Returns the type of this macro
92 | * @return the type of the macro
93 | */
94 | public String getType() {
95 | return type;
96 | }
97 |
98 | /**
99 | * Returns the path of a file or a package this macro was performed
100 | * @return the path string
101 | */
102 | public String getPath() {
103 | return path;
104 | }
105 |
106 | /**
107 | * Sets the collection of raw macros that were recorded.
108 | * @param macros the raw macros to be stored
109 | */
110 | public void setRawMacros(List macros) {
111 | rawMacros = macros;
112 | }
113 |
114 | /**
115 | * Returns the collection of raw macros that were recorded.
116 | * @return raw macros
117 | */
118 | public List getRawMacros() {
119 | return rawMacros;
120 | }
121 | }
122 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/ResourceMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | import org.eclipse.core.resources.IResource;
10 | import org.eclipse.core.resources.IFile;
11 | import org.eclipse.core.runtime.CoreException;
12 | import org.eclipse.jdt.core.ICompilationUnit;
13 | import org.eclipse.jdt.core.IJavaElement;
14 | import org.eclipse.jdt.core.IPackageFragment;
15 | import org.eclipse.jdt.core.JavaCore;
16 | import org.eclipse.jdt.core.JavaModelException;
17 |
18 | /**
19 | * Stores a resource change macro.
20 | * @author Katsuhisa Maruyama
21 | */
22 | public class ResourceMacro extends Macro {
23 |
24 | /**
25 | * The target of this resource change.
26 | */
27 | private String target;
28 |
29 | /**
30 | * The path of a resource identical to the changed resource.
31 | */
32 | private String identicalPath;
33 |
34 | /**
35 | * The contents of source code after the resource change.
36 | */
37 | private String code;
38 |
39 | /**
40 | * The encoding of the changed source code.
41 | */
42 | private String encoding;
43 |
44 | /**
45 | * A flag that indicates if the changed resource is currently edited.
46 | */
47 | private boolean onEdit = false;
48 |
49 | /**
50 | * Creates an object storing information on an resource change macro.
51 | * @param time the time when the macro started
52 | * @param type the type of the change
53 | * @param path the path of the changed resource
54 | * @param elem the changed resource
55 | */
56 | public ResourceMacro(long time, String type, String path, IJavaElement elem) {
57 | super(time, time, type, path);
58 | this.target = getTarget(elem);
59 | this.identicalPath = getIdenticalPath(elem);
60 | this.code = getCode(elem);
61 | this.encoding = getEncoding(elem);
62 | }
63 |
64 | /**
65 | * Creates an object storing information on an resource change macro.
66 | * @param time the time when the macro started
67 | * @param type the type of the change
68 | * @param path the path of the changed resource
69 | * @param res the changed resource
70 | */
71 | public ResourceMacro(long time, String type, String path, IResource res) {
72 | this(time, type, path, JavaCore.create(res));
73 | }
74 |
75 | /**
76 | * Returns the target of this resource change.
77 | * @param elem the changed element
78 | * @return the target of the change, or null
if the target is not either a project, package, or file
79 | */
80 | public String getTarget() {
81 | return target;
82 | }
83 |
84 | /**
85 | * Returns the path of a resource moved/renamed from or to.
86 | * @return the path of the identical resource
87 | */
88 | public String getIdenticalPath() {
89 | return identicalPath;
90 | }
91 |
92 | /**
93 | * Returns source code after this resource change.
94 | * @return the contents of the source code, or an empty string if the changed resource is not a file
95 | */
96 | public String getCode() {
97 | return code;
98 | }
99 |
100 | /**
101 | * Returns the encoding of the changed source code.
102 | * @return the encoding of the changed source code, or null
103 | */
104 | public String getEncoding() {
105 | return encoding;
106 | }
107 |
108 | /**
109 | * Sets the flag that indicates if the changed resource is currently edited.
110 | * @param bool true
if the changed resource is currently edited, otherwise false
111 | */
112 | public void setOnEdit(boolean bool) {
113 | onEdit = bool;
114 | }
115 |
116 | /**
117 | * Tests if the changed resource is currently edited.
118 | * @return true
if the changed resource is currently edited, otherwise false
119 | */
120 | public boolean getOnEdit() {
121 | return onEdit;
122 | }
123 |
124 | /**
125 | * Tests if the type of the change belongs to removal.
126 | * @return true
if this macro represents the removal change, otherwise false
127 | */
128 | public boolean isRemoved() {
129 | return type.compareTo("Removed") == 0 ||
130 | type.compareTo("RenamedTo") == 0 ||
131 | type.compareTo("MovedTo") == 0;
132 | }
133 |
134 | /**
135 | * Tests if the type of the change belongs to addition.
136 | * @return true
if this macro represents the addition change, otherwise false
137 | */
138 | public boolean isAdded() {
139 | return type.compareTo("Added") == 0 ||
140 | type.compareTo("RenamedFrom") == 0 ||
141 | type.compareTo("MovedFrom") == 0;
142 | }
143 |
144 | /**
145 | * Returns the target of this resource change.
146 | * @param elem the changed element
147 | * @return the target of the change, or an empty string if the target is not either a project, package, or file
148 | */
149 | private String getTarget(IJavaElement elem) {
150 | if (elem == null) {
151 | return "";
152 | }
153 |
154 | int type = elem.getElementType();
155 | if (type == IJavaElement.JAVA_PROJECT) {
156 | return "Project";
157 |
158 | } else if (type == IJavaElement.PACKAGE_DECLARATION) {
159 | return "Package";
160 |
161 | } else if (type == IJavaElement.COMPILATION_UNIT) {
162 | return "File";
163 | }
164 |
165 | return elem.getElementName() + "@" + elem.getElementType();
166 | }
167 |
168 | /**
169 | * Returns the path of a resource moved/renamed from or to.
170 | * @param elem the changed resource
171 | * @return the path of the identical resource
172 | */
173 | private String getIdenticalPath(IJavaElement elem) {
174 | return elem.getPath().toString();
175 | }
176 |
177 | /**
178 | * Obtains source code after this resource change.
179 | * @param elem the changed resource
180 | * @return the contents of the source code, or an empty string if the changed resource is not a file
181 | */
182 | private String getCode(IJavaElement elem) {
183 | if (elem instanceof ICompilationUnit) {
184 | ICompilationUnit cu = (ICompilationUnit)elem;
185 |
186 | try {
187 | return cu.getSource();
188 | } catch (JavaModelException e) {
189 | }
190 | }
191 | return "";
192 | }
193 |
194 | /**
195 | * Returns the encoding of the changed source code.
196 | * @param elem the changed resource
197 | * @return the encoding of the source code, or null
198 | */
199 | private String getEncoding(IJavaElement elem) {
200 | if (elem instanceof ICompilationUnit) {
201 | ICompilationUnit cu = (ICompilationUnit)elem;
202 |
203 | try {
204 | IFile file = (IFile)cu.getCorrespondingResource();
205 | return file.getCharset();
206 | } catch (CoreException e) {
207 | }
208 | }
209 | return null;
210 | }
211 |
212 |
213 | /**
214 | * Returns the string for printing, which does not contain a new line character at its end.
215 | * @return the string for printing
216 | */
217 | public String toString() {
218 | return "RESO(" + getType() + ")= " + getStartTime() + "-" + getEndTime() + ": " +
219 | getPath() + " " + getTarget() + " FROM/TO " + getIdenticalPath();
220 | }
221 |
222 | /**
223 | * Obtains the name of the specified element.
224 | * @param elem the element
225 | * @param type the type of the element
226 | * @return the name string
227 | */
228 | public static String getName(IJavaElement elem) {
229 | int type = elem.getElementType();
230 | if (type == IJavaElement.JAVA_PROJECT) {
231 | return elem.getResource().getName();
232 |
233 | } else if (type == IJavaElement.PACKAGE_DECLARATION) {
234 | IPackageFragment jpackage = (IPackageFragment)elem;
235 | return jpackage.getElementName();
236 |
237 | } else if (type == IJavaElement.COMPILATION_UNIT) {
238 | return elem.getResource().getName();
239 | }
240 |
241 | return "";
242 | }
243 | }
244 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/macro/TriggerMacro.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.macro;
8 |
9 | /**
10 | * Stores a trigger macro.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public class TriggerMacro extends Macro {
14 |
15 | /**
16 | * The kinds of a trigger.
17 | */
18 | public enum Kind {
19 | BEGIN, END, CURSOR_CHANGE;
20 | }
21 |
22 | /**
23 | * The kind of a trigger of the macro.
24 | */
25 | private Kind kind = null;
26 |
27 | /**
28 | * Creates an object storing information on a macro.
29 | * @param time the time when the macro occurred
30 | * @param type the type of the macro
31 | * @param path the path of a file or a package this macro was performed
32 | * @param kind the kind of a trigger of the macro
33 | */
34 | public TriggerMacro(long time, String type, String path, Kind kind) {
35 | super(time, time, type, path);
36 | this.kind = kind;
37 | }
38 |
39 | /**
40 | * Returns the kind of a trigger of the macro
41 | * @return the kind of the macro
42 | */
43 | public Kind getKind() {
44 | return kind;
45 | }
46 |
47 | /**
48 | * Tests this compound macro indicates the beginning.
49 | * @return true
if this compound macro indicates the beginning, otherwise false
50 | */
51 | public boolean isBegin() {
52 | return kind == Kind.BEGIN;
53 | }
54 |
55 | /**
56 | * Tests this compound macro indicates the ending.
57 | * @return true
if this compound macro indicates the ending, otherwise false
58 | */
59 | public boolean isEnd() {
60 | return kind == Kind.END;
61 | }
62 |
63 | /**
64 | * Tests this compound macro indicates as the change of the current position of the cursor.
65 | * @return true
if this compound macro indicates the cursor change, otherwise false
66 | */
67 | public boolean isCursorChange() {
68 | return kind == Kind.CURSOR_CHANGE;
69 | }
70 |
71 |
72 |
73 | /**
74 | * Returns the string for printing, which does not contain a new line character at its end.
75 | * @return the string for printing
76 | */
77 | public String toString() {
78 | return "TRIGGER(" + getType() + ") = " + getStartTime() + "-" + getEndTime() + ": " +
79 | getPath() + " " + getKind().toString();
80 | }
81 | }
82 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/recorder/MacroCompressor.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.recorder;
8 |
9 | import org.jtool.macrorecorder.macro.DocumentMacro;
10 |
11 | /**
12 | * Compresses macros.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public class MacroCompressor {
16 |
17 | /**
18 | * Creates an object compressing macros.
19 | */
20 | public MacroCompressor() {
21 | }
22 |
23 | /**
24 | * Tests if a document macros can be combined with its previous macro.
25 | * @param macro the document macro
26 | * @return true
if the macros can be combined, otherwise false
27 | */
28 | public boolean canCombine(DocumentMacro macro) {
29 | if (macro == null) {
30 | return false;
31 | }
32 |
33 | if (macro.isInsert()) {
34 | return combineWith(macro.getInsertedText());
35 | }
36 |
37 | if (macro.isDelete()) {
38 | return combineWith(macro.getDeletedText());
39 | }
40 |
41 | if (macro.isReplace()) {
42 | return combineWith(macro.getInsertedText()) && combineWith(macro.getDeletedText());
43 | }
44 |
45 | return false;
46 | }
47 |
48 | /**
49 | * Combines successive two document macros.
50 | * @param last the former document macro
51 | * @param next the latter document macro
52 | * @return the combined macro, or null
if the macro cannot be combined
53 | */
54 | public DocumentMacro combine(DocumentMacro last, DocumentMacro next) {
55 | if (next == null) {
56 | return null;
57 | }
58 |
59 | if (next.isInsert()) {
60 | return combineInsertMacro(last, next);
61 | }
62 |
63 | if (next.isDelete()) {
64 | return combineDeleteMacro(last, next);
65 | }
66 |
67 | if (next.isReplace()) {
68 | return compressReplaceMacro(last, next);
69 | }
70 |
71 | return null;
72 | }
73 |
74 | /**
75 | * Combines successive two macro.
76 | * @param last the former document macro
77 | * @param next the latter document macro that represents the insertion
78 | * @return the combined macro, or null
if the macros cannot be combined
79 | */
80 | private DocumentMacro combineInsertMacro(DocumentMacro last, DocumentMacro next) {
81 | if (last == null) {
82 | return next;
83 | }
84 |
85 | if (!last.isInsert() || !combineWith(last.getInsertedText())) {
86 | return null;
87 | }
88 |
89 | if (last.getStart() + last.getInsertedText().length() == next.getStart()) {
90 | String text = last.getInsertedText() + next.getInsertedText();
91 | return new DocumentMacro(last.getStartTime(), next.getEndTime(),
92 | last.getType(), last.getPath(), last.getStart(), text, "");
93 | }
94 |
95 | return null;
96 | }
97 |
98 | /**
99 | * Combines successive two macros.
100 | * @param last the former document macro
101 | * @param next the latter document macro that represents deletion
102 | * @return the combined macro, or null
if the macros cannot be combined
103 | */
104 | private DocumentMacro combineDeleteMacro(DocumentMacro last, DocumentMacro next) {
105 | if (last == null) {
106 | return next;
107 | }
108 |
109 | if (!last.isDelete() || !combineWith(last.getDeletedText())) {
110 | return null;
111 | }
112 |
113 | if (last.getStart() > next.getStart()) {
114 | if (last.getStart() == next.getStart() + next.getDeletedText().length()) {
115 | String text = next.getDeletedText() + last.getDeletedText();
116 |
117 | return new DocumentMacro(last.getStartTime(), next.getEndTime(),
118 | last.getType(), last.getPath(), next.getStart(), "", text);
119 | }
120 |
121 | } else {
122 | if (last.getStart() + last.getInsertedText().length() == next.getStart()) {
123 | String text = last.getDeletedText() + next.getDeletedText();
124 |
125 | return new DocumentMacro(last.getStartTime(), next.getEndTime(),
126 | last.getType(), last.getPath(), last.getStart(), "", text);
127 | }
128 | }
129 |
130 | return null;
131 | }
132 |
133 | /**
134 | * Compresses successive two macros.
135 | * @param last the former document macro
136 | * @param next the latter document macro that represents replacement
137 | * @return the combined macro, or null
if the macros cannot be combined
138 | */
139 | private DocumentMacro compressReplaceMacro(DocumentMacro last, DocumentMacro next) {
140 | if (last == null) {
141 | return next;
142 | }
143 |
144 | if (!(last.isInsert() || last.isReplace()) ||
145 | !combineWith(last.getInsertedText()) || !combineWith(last.getDeletedText())) {
146 | return null;
147 | }
148 |
149 | if (last.getStart() == next.getStart() &&
150 | last.getInsertedText().compareTo(next.getDeletedText()) == 0) {
151 | String itext = next.getInsertedText();
152 | String dtext = last.getDeletedText();
153 | return new DocumentMacro(last.getStartTime(), next.getEndTime(),
154 | last.getType(), last.getPath(), last.getStart(), itext, dtext);
155 | }
156 |
157 | return null;
158 | }
159 |
160 | /**
161 | * Tests if a given text can be combined with another one.
162 | * @param text the text to be combined
163 | * @return true
if the can be combined, otherwise false
164 | */
165 | public boolean combineWith(String text) {
166 | char[] DELIMITER_CHARS = new char[] { '\n', '\r', ';', '{', '}' };
167 |
168 | for (int i = 0; i < DELIMITER_CHARS.length; i++) {
169 | if (text.indexOf(DELIMITER_CHARS[i]) >= 0) {
170 | return false;
171 | }
172 | }
173 | return true;
174 | }
175 | }
176 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/recorder/MacroEvent.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.recorder;
8 |
9 | import org.jtool.macrorecorder.macro.Macro;
10 |
11 | /**
12 | * Manages an event containing a macro.
13 | * @author Katsuhisa Maruyama
14 | */
15 | public class MacroEvent {
16 |
17 | /**
18 | * The value indicating general macros.
19 | */
20 | public static int GENERIC_MACRO = 1;
21 |
22 | /**
23 | * The value indicating raw macros per keystroke.
24 | */
25 | public static int RAW_MACRO = 2;
26 |
27 | /**
28 | * A macro sent to listeners.
29 | */
30 | private Macro macro;
31 |
32 | /**
33 | * The type of a macro sent to listeners.
34 | */
35 | private int type;
36 |
37 | /**
38 | * Creates an object containing a macro.
39 | * @param macro the macro sent to listeners
40 | */
41 | public MacroEvent(int type, Macro macro) {
42 | this.type = type;
43 | this.macro = macro;
44 | }
45 |
46 | /**
47 | * Returns the type of an event that listeners receive.
48 | * @return the type of the received event
49 | */
50 | public int getEventType() {
51 | return type;
52 | }
53 |
54 | /**
55 | * Returns the macro of an event that listeners receive.
56 | * @return the macro contained in the received event
57 | */
58 | public Macro getMacro() {
59 | return macro;
60 | }
61 | }
62 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/recorder/MacroListener.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.recorder;
8 |
9 | /**
10 | * Defines the listener interface for receiving a macro event.
11 | * @author Katsuhisa Maruyama
12 | */
13 | public interface MacroListener {
14 |
15 | /**
16 | * Receives a macro event when a new macro is added.
17 | * @param evt the macro event
18 | */
19 | public void macroAdded(MacroEvent evt);
20 |
21 | /**
22 | * Receives a macro event when a document is changed.
23 | * @param evt the raw macro event
24 | */
25 | public void documentChanged(MacroEvent evt);
26 | }
27 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/util/EditorUtilities.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.util;
8 |
9 | import org.eclipse.core.resources.IFile;
10 | import org.eclipse.core.runtime.CoreException;
11 | import org.eclipse.jface.text.source.ISourceViewer;
12 | import org.eclipse.jface.text.source.SourceViewer;
13 | import org.eclipse.jface.text.source.ContentAssistantFacade;
14 | import org.eclipse.jface.text.IDocument;
15 | import org.eclipse.jface.text.ITextOperationTarget;
16 | import org.eclipse.swt.custom.StyledText;
17 | import org.eclipse.ui.IEditorInput;
18 | import org.eclipse.ui.IEditorPart;
19 | import org.eclipse.ui.IEditorReference;
20 | import org.eclipse.ui.IFileEditorInput;
21 | import org.eclipse.ui.IWorkbenchPage;
22 | import org.eclipse.ui.IWorkbenchWindow;
23 | import org.eclipse.ui.PlatformUI;
24 | import org.eclipse.ui.editors.text.TextFileDocumentProvider;
25 | import org.eclipse.ui.part.FileEditorInput;
26 | import java.util.ArrayList;
27 | import java.util.List;
28 |
29 | /**
30 | * Provides utilities that obtain information on editors.
31 | * @author Katsuhisa Maruyama
32 | */
33 | public class EditorUtilities {
34 |
35 | /**
36 | * Obtains the source viewer of an editor.
37 | * @param editor the editor
38 | * @return the source viewer of the editor
39 | */
40 | public static ISourceViewer getSourceViewer(IEditorPart editor) {
41 | if (editor == null) {
42 | return null;
43 | }
44 |
45 | ISourceViewer viewer = (ISourceViewer)editor.getAdapter(ITextOperationTarget.class);
46 | return viewer;
47 | }
48 |
49 | /**
50 | * Obtains the styled text of an editor.
51 | * @param editor the editor
52 | * @return the styled text of the editor
53 | */
54 | public static StyledText getStyledText(IEditorPart editor) {
55 | ISourceViewer viewer = getSourceViewer(editor);
56 | if (viewer != null) {
57 | return viewer.getTextWidget();
58 | }
59 | return null;
60 | }
61 |
62 | /**
63 | * Obtains the content assistant facade of an editor.
64 | * @param editor the editor
65 | * @return the content assistant facade of the editor
66 | */
67 | public static ContentAssistantFacade getContentAssistantFacade(IEditorPart editor) {
68 | ISourceViewer viewer = getSourceViewer(editor);
69 | if (viewer != null && viewer instanceof SourceViewer) {
70 | return ((SourceViewer)viewer).getContentAssistantFacade();
71 | }
72 | return null;
73 | }
74 |
75 | /**
76 | * Obtains a file existing on an editor.
77 | * @param editor the editor
78 | * @return the file existing on the editor, or null
if none
79 | */
80 | public static IFile getInputFile(IEditorPart editor) {
81 | IEditorInput input = editor.getEditorInput();
82 | if (input instanceof IFileEditorInput) {
83 | IFile file = ((IFileEditorInput)input).getFile();
84 | return file;
85 | }
86 | return null;
87 | }
88 |
89 | /**
90 | * Obtains the path of a file existing on an editor.
91 | * @param editor the editor
92 | * @return the path of the file, which is relative to the path of the workspace
93 | */
94 | public static String getInputFilePath(IEditorPart editor) {
95 | IFile file = getInputFile(editor);
96 | return getInputFilePath(file);
97 | }
98 |
99 | /**
100 | * Obtains the path of a file.
101 | * @param file the file
102 | * @return the path of the file, which is relative to the path of the workspace
103 | */
104 | public static String getInputFilePath(IFile file) {
105 | if (file != null) {
106 | return file.getFullPath().toString();
107 | }
108 | return "";
109 | }
110 |
111 | /**
112 | * Obtains the document of a file.
113 | * @param file the file
114 | * @return the document of the file, or null
if none
115 | */
116 | public static IDocument getDocument(IFile file) {
117 | if (file == null) {
118 | return null;
119 | }
120 |
121 | try {
122 | TextFileDocumentProvider provider = new TextFileDocumentProvider();
123 | provider.connect(file);
124 | IDocument doc = provider.getDocument(file);
125 | provider.disconnect(file);
126 | return doc;
127 | } catch (CoreException e) {
128 | e.printStackTrace();
129 | }
130 | return null;
131 | }
132 |
133 | /**
134 | * Obtains the document of a file existing on an editor.
135 | * @param editor the editor
136 | * @return the document of the file, or null
if none
137 | */
138 | public static IDocument getDocument(IEditorPart editor) {
139 | IFile file = getInputFile(editor);
140 | if (file != null) {
141 | return getDocument(file);
142 | }
143 | return null;
144 | }
145 |
146 | /**
147 | * Obtains the contents of source code appearing in an editor.
148 | * @param editor the editor
149 | * @return the contents of the source code, or null
if the source code is not valid
150 | */
151 | public static String getSourceCode(IEditorPart editor) {
152 | IDocument doc = getDocument(editor);
153 | if (doc != null) {
154 | return doc.get();
155 | }
156 | return null;
157 | }
158 |
159 | /**
160 | * Obtains the contents of source code appearing in an editor.
161 | * @param file the file
162 | * @return the contents of the source code, or null
if the source code is not valid
163 | */
164 | public static String getSourceCode(IFile file) {
165 | IDocument doc = getDocument(file);
166 | if (doc != null) {
167 | return doc.get();
168 | }
169 | return null;
170 | }
171 |
172 | /**
173 | * Obtains an editor that may edits the contents of a file.
174 | * @param file the file
175 | * @return the editor of the file, or null
if none
176 | */
177 | public static IEditorPart getEditor(IFile file) {
178 | IEditorInput input = new FileEditorInput(file);
179 | IWorkbenchWindow[] windows = PlatformUI.getWorkbench().getWorkbenchWindows();
180 |
181 | for (IWorkbenchWindow window : windows) {
182 | IWorkbenchPage[] pages = window.getPages();
183 |
184 | for (IWorkbenchPage page : pages) {
185 | IEditorPart part = page.findEditor(input);
186 | return part;
187 | }
188 | }
189 | return null;
190 | }
191 |
192 | /**
193 | * Obtains all editors that are currently opened.
194 | * @return the collection of the opened editors
195 | */
196 | public static List getEditors() {
197 | List editors = new ArrayList();
198 | IWorkbenchWindow[] windows = PlatformUI.getWorkbench().getWorkbenchWindows();
199 |
200 | for (IWorkbenchWindow window : windows) {
201 | IWorkbenchPage[] pages = window.getPages();
202 |
203 | for (IWorkbenchPage page : pages) {
204 | IEditorReference[] refs = page.getEditorReferences();
205 |
206 | for (IEditorReference ref : refs) {
207 | IEditorPart part = ref.getEditor(false);
208 | if (part != null) {
209 | editors.add(part);
210 | }
211 | }
212 | }
213 | }
214 | return editors;
215 | }
216 |
217 | /**
218 | * Obtains an editor that is currently active.
219 | * @return the active editor, or null
if none
220 | */
221 | public static IEditorPart getActiveEditor() {
222 | IWorkbenchWindow window = PlatformUI.getWorkbench().getActiveWorkbenchWindow();
223 | if (window != null) {
224 | IEditorPart part = window.getActivePage().getActiveEditor();
225 | return part;
226 | }
227 | return null;
228 | }
229 |
230 | /**
231 | * Obtains the path of a active file existing on an editor.
232 | * @return the path of the file, which is relative to the path of the workspace
233 | */
234 | public static String getActiveInputFilePath() {
235 | IEditorPart editor = getActiveEditor();
236 | if (editor != null) {
237 | return getInputFilePath(editor);
238 | }
239 | return null;
240 | }
241 | }
242 |
--------------------------------------------------------------------------------
/MacroRecorder/src/org/jtool/macrorecorder/util/WorkspaceUtilities.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package org.jtool.macrorecorder.util;
8 |
9 | import org.eclipse.core.resources.ResourcesPlugin;
10 | import org.eclipse.core.resources.IResource;
11 | import org.eclipse.core.resources.IProject;
12 | import org.eclipse.core.resources.IWorkspace;
13 | import org.eclipse.jdt.core.IJavaProject;
14 | import org.eclipse.jdt.core.ICompilationUnit;
15 | import org.eclipse.jdt.core.IPackageFragment;
16 | import org.eclipse.jdt.core.JavaCore;
17 | import org.eclipse.jdt.core.JavaModelException;
18 | import java.util.List;
19 | import java.util.ArrayList;
20 |
21 | /**
22 | * Provides utilities that obtain information on the workspace.
23 | * @author Katsuhisa Maruyama
24 | */
25 | public class WorkspaceUtilities {
26 |
27 | /**
28 | * Obtains the workspace.
29 | * @return the workspace information
30 | */
31 | public static IWorkspace getWorkspace() {
32 | return ResourcesPlugin.getWorkspace();
33 | }
34 |
35 | /**
36 | * Obtains the encoding to use when reading text files in the workspace.
37 | * @return the encoding
38 | */
39 | public static String getEncoding() {
40 | return ResourcesPlugin.getEncoding();
41 | }
42 |
43 | /**
44 | * Collects all compilation units within the project.
45 | * @return the collection of the compilation units
46 | */
47 | public static List collectAllCompilationUnits() {
48 | List units = new ArrayList();
49 |
50 | try {
51 | IProject[] projects = getWorkspace().getRoot().getProjects();
52 | for (int i = 0; i < projects.length; i++) {
53 | IJavaProject project = (IJavaProject)JavaCore.create((IProject)projects[i]);
54 |
55 | IPackageFragment[] packages = project.getPackageFragments();
56 | for (int j = 0; j < packages.length; j++) {
57 |
58 | ICompilationUnit[] cus = packages[j].getCompilationUnits();
59 | for (int k = 0; k < cus.length; k++) {
60 | IResource res = cus[k].getResource();
61 | if (res.getType() == IResource.FILE) {
62 | String name = cus[k].getPath().toString();
63 | if (name.endsWith(".java")) {
64 | units.add(cus[k]);
65 | }
66 | }
67 | }
68 | }
69 | }
70 | } catch (JavaModelException e) {
71 | e.printStackTrace();
72 | }
73 |
74 | return units;
75 | }
76 | }
77 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # ContentAssist
2 | A code assist plugin for Eclipse.
3 |
4 | In recent integrated development environments, by utilizing collective intelligence obtained from a large amount of source code described in the past, the method with higher possibility to be used in the source code is preferentially recommended. The method based on the statistical data is suitable for code complementation tailored to the tendency of the developer as a whole, but it is not always possible to provide an appropriate complementary candidate for a specific development team or individual developer. In this project, we propose a method to calculate the degree of interest of developers by utilizing the editing history that the developer written in the past, and rearrange the order of code completion candidates that can be displayed based on it.
5 |
6 | ## Requirement
7 | JDK 1.7 or later
8 |
9 | Eclipse 4.6 (Neon) or late (Eclipse for committer)
10 |
11 | ## Installation
12 |
13 | 1. Please run `git clone git@github.com:liaoziyang/ContentAssist.git` to copy the files to local.
14 | 2. Import this project to your workspace.
15 |
16 | ## System structure
17 | 
18 |
19 | ## Compare to other content assist plugin
20 | 
21 |
22 | ## Publication
23 | Liao Ziyang, 丸山勝久, ["編集履歴から算出した開発者の関心度に基づくコード補完"](編集履歴から算出した開発者の関心度に基づくコード補完.pdf), 日本ソフトウェア科学会第33回大会,FOSE2-3, 2016
24 |
--------------------------------------------------------------------------------
/RemoteSystemsTempFiles/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | RemoteSystemsTempFiles
4 |
5 |
6 |
7 |
8 |
9 |
10 | org.eclipse.rse.ui.remoteSystemsTempNature
11 |
12 |
13 |
--------------------------------------------------------------------------------
/compare.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/compare.png
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | jp.ac.ritsumei.cs.fse.contentassist
4 |
5 |
6 |
7 |
8 |
9 | org.eclipse.jdt.core.javabuilder
10 |
11 |
12 |
13 |
14 | org.eclipse.pde.ManifestBuilder
15 |
16 |
17 |
18 |
19 | org.eclipse.pde.SchemaBuilder
20 |
21 |
22 |
23 |
24 |
25 | org.eclipse.pde.PluginNature
26 | org.eclipse.jdt.core.javanature
27 |
28 |
29 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5
4 | org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
5 | org.eclipse.jdt.core.compiler.compliance=1.5
6 | org.eclipse.jdt.core.compiler.debug.lineNumber=generate
7 | org.eclipse.jdt.core.compiler.debug.localVariable=generate
8 | org.eclipse.jdt.core.compiler.debug.sourceFile=generate
9 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
10 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
11 | org.eclipse.jdt.core.compiler.source=1.5
12 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/META-INF/MANIFEST.MF:
--------------------------------------------------------------------------------
1 | Manifest-Version: 1.0
2 | Bundle-ManifestVersion: 2
3 | Bundle-Name: Contentassist
4 | Bundle-SymbolicName: jp.ac.ritsumei.cs.fse.contentassist;singleton:=true
5 | Bundle-Version: 1.0.0.qualifier
6 | Bundle-Activator: jp.ac.ritsumei.cs.fse.contentassist.Activator
7 | Require-Bundle: org.eclipse.ui,
8 | org.eclipse.core.runtime,
9 | org.eclipse.jdt.ui,
10 | org.eclipse.jdt.core;bundle-version="3.10.2",
11 | org.eclipse.jface.text;bundle-version="3.8.101",
12 | ChangeRecorder;bundle-version="1.0.0"
13 | Bundle-ActivationPolicy: lazy
14 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/.gitignore:
--------------------------------------------------------------------------------
1 | /jp/
2 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/Activator.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/Activator.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/ConsoleOperationListener2.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/ConsoleOperationListener2.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/DataManager.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/DataManager.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/HistoryRecorder.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/HistoryRecorder.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/getProposalResult.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/getProposalResult.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/View/JavaCompletionProposalComputer1.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/View/JavaCompletionProposalComputer1.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/entity/ApplyOperation.class:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/jp.ac.ritsumei.cs.fse.contentassist/bin/jp/ac/ritsumei/cs/fse/contentassist/entity/ApplyOperation.class
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/build.properties:
--------------------------------------------------------------------------------
1 | source.. = src/
2 | output.. = bin/
3 | bin.includes = META-INF/,\
4 | .,\
5 | plugin.xml
6 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/plugin.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
7 |
12 |
14 |
15 |
16 |
17 |
19 |
21 |
22 |
23 |
24 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/Activator.java:
--------------------------------------------------------------------------------
1 | package jp.ac.ritsumei.cs.fse.contentassist;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser.ConsoleOperationListener2;
7 | import jp.ac.ritsumei.cs.fse.contentassist.entity.ApplyOperation;
8 |
9 | import org.eclipse.core.runtime.CoreException;
10 | import org.eclipse.ui.IStartup;
11 | import org.eclipse.ui.plugin.AbstractUIPlugin;
12 | import org.jtool.changerecorder.editor.HistoryManager;
13 | import org.osgi.framework.BundleContext;
14 |
15 | /**
16 | * The activator class controls the plug-in life cycle
17 | */
18 | public class Activator extends AbstractUIPlugin implements IStartup {
19 |
20 | // The plug-in ID
21 | public static final String PLUGIN_ID = "Contentassist"; //$NON-NLS-1$
22 |
23 | // The shared instance
24 | private static Activator plugin;
25 |
26 | public static List applyoperationlist = new ArrayList();
27 |
28 | /**
29 | * The constructor
30 | */
31 | public Activator() {
32 | }
33 |
34 | /*
35 | * (non-Javadoc)
36 | * @see org.eclipse.ui.plugin.AbstractUIPlugin#start(org.osgi.framework.BundleContext)
37 | */
38 | public void start(BundleContext context) throws Exception {
39 | super.start(context);
40 | plugin = this;
41 | HistoryManager hm = HistoryManager.getInstance();
42 | hm.addOperationEventListener(new ConsoleOperationListener2());
43 | System.out.println(PLUGIN_ID + " activated.");
44 | }
45 |
46 | /*
47 | * (non-Javadoc)
48 | * @see org.eclipse.ui.plugin.AbstractUIPlugin#stop(org.osgi.framework.BundleContext)
49 | */
50 | public void stop(BundleContext context) throws Exception {
51 | plugin = null;
52 | super.stop(context);
53 | }
54 |
55 | /**
56 | * Returns the shared instance
57 | *
58 | * @return the shared instance
59 | */
60 | public static Activator getDefault() {
61 | return plugin;
62 | }
63 |
64 | public void earlyStartup() {
65 | // TODO Auto-generated method stub
66 |
67 | }
68 |
69 | }
70 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/ConsoleOperationListener2.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2014
3 | * Software Science and Technology Lab.
4 | * Department of Computer Science, Ritsumeikan University
5 | */
6 |
7 | package jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser;
8 |
9 | import jp.ac.ritsumei.cs.fse.contentassist.Activator;
10 | import jp.ac.ritsumei.cs.fse.contentassist.entity.ApplyOperation;
11 |
12 | import org.jtool.changerecorder.event.OperationEvent;
13 | import org.jtool.changerecorder.event.OperationEventListener;
14 | import org.jtool.changerecorder.operation.TextOperation;
15 |
16 | /**
17 | * Displays operations recorded on editors.
18 | * @author liaoziyang
19 | */
20 | public class ConsoleOperationListener2 implements OperationEventListener {
21 |
22 | /**
23 | * Receives an operation event when operation history was updated.
24 | * @param evt the received event
25 | */
26 | HistoryRecorder hr = new HistoryRecorder();
27 | public static TextOperation ope;
28 | public void historyNotification(OperationEvent evt) {
29 | try {
30 | ConsoleOperationListener2.ope = (TextOperation) evt.getOperation();
31 | }
32 | catch(Exception e) {
33 |
34 | }
35 | for (ApplyOperation ao : Activator.applyoperationlist) {
36 | ao.update(ope.getStart(), ope.getDeletedText(), ope.getInsertedText());
37 | System.out.println(ao.toString());
38 | }
39 | }
40 | }
41 |
42 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/DataManager.java:
--------------------------------------------------------------------------------
1 |
2 | package jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser;
3 |
4 | import java.util.List;
5 |
6 |
7 | import org.eclipse.core.runtime.IProgressMonitor;
8 | import org.eclipse.jdt.ui.text.java.ContentAssistInvocationContext;
9 | import org.eclipse.jface.text.contentassist.ICompletionProposal;
10 | import org.eclipse.jface.text.contentassist.IContextInformation;
11 |
12 | /**
13 | * @author liaoziyang
14 | * Manage the Dataanalyser's work
15 | */
16 | public class DataManager {
17 | public getProposalResult getproposalresult;
18 | public HistoryRecorder historyrecorder = new HistoryRecorder();
19 | ContentAssistInvocationContext context = null;
20 | IProgressMonitor monitor = null;
21 |
22 | public DataManager(){}
23 |
24 | public DataManager(ContentAssistInvocationContext context, IProgressMonitor monitor){
25 | this.context = context;
26 | this.monitor = monitor;
27 | getproposalresult = new getProposalResult(context,monitor);
28 | }
29 |
30 | /**
31 | * @return The default result of java content assist
32 | */
33 | public List JavaDefaultProposal(){
34 | return getproposalresult.getAllProposalResult();
35 | }
36 |
37 | public List ContextInformation(){
38 | return getproposalresult.getAllProposalResultInformation();
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/HistoryRecorder.java:
--------------------------------------------------------------------------------
1 | package jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser;
2 |
3 | public class HistoryRecorder {
4 |
5 | public String getInsertString(){
6 | return ConsoleOperationListener2.ope.getInsertedText();
7 | }
8 |
9 | public String getDeleteString(){
10 | return ConsoleOperationListener2.ope.getDeletedText();
11 | }
12 |
13 | public int getOffset(){
14 | return ConsoleOperationListener2.ope.getStart();
15 | }
16 | public long getTime(){
17 | return ConsoleOperationListener2.ope.getTime();
18 | }
19 | public long getTimes(){
20 | return ConsoleOperationListener2.ope.getSequenceNumber();
21 | }
22 | public String getAuthor(){
23 | return ConsoleOperationListener2.ope.getAuthor();
24 | }
25 | }
26 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/DataAnalyser/getProposalResult.java:
--------------------------------------------------------------------------------
1 | package jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser;
2 |
3 | import java.util.List;
4 | import java.util.HashSet;
5 | import java.util.Iterator;
6 | import java.util.List;
7 | import java.util.Set;
8 |
9 | import org.eclipse.core.runtime.IProgressMonitor;
10 | import org.eclipse.jface.text.BadLocationException;
11 | import org.eclipse.jface.text.IDocument;
12 | import org.eclipse.jface.text.contentassist.ICompletionProposal;
13 | import org.eclipse.jface.text.contentassist.IContextInformation;
14 | import org.eclipse.jdt.core.CompletionContext;
15 | import org.eclipse.jdt.core.CompletionProposal;
16 | import org.eclipse.jdt.core.IJavaElement;
17 | import org.eclipse.jdt.core.IJavaProject;
18 | import org.eclipse.jdt.core.IType;
19 | import org.eclipse.jdt.core.JavaCore;
20 | import org.eclipse.jdt.core.JavaModelException;
21 | import org.eclipse.jdt.core.Signature;
22 | import org.eclipse.jdt.ui.text.java.CompletionProposalCollector;
23 | import org.eclipse.jdt.ui.text.java.ContentAssistInvocationContext;
24 | import org.eclipse.jdt.ui.text.java.IJavaCompletionProposal;
25 | import org.eclipse.jdt.ui.text.java.JavaContentAssistInvocationContext;
26 | import org.eclipse.jdt.internal.ui.JavaPlugin;
27 | import org.eclipse.jdt.internal.ui.text.JavaHeuristicScanner;
28 | import org.eclipse.jdt.internal.ui.text.Symbols;
29 | import org.eclipse.jdt.internal.ui.text.java.*;
30 | /**
31 | * @author liaoziyang
32 | * Get the proposal result of the default java content assist
33 | */
34 | public class getProposalResult extends JavaAllCompletionProposalComputer{
35 | /**
36 | * @param context The instance of ContentAssistInvocationContext
37 | * @param monitor The instance of IProgressMonitor
38 | * @see JavaAllCompletionProposalComputer.java in org.eclipse.jdt.internal.ui.text.java
39 | * @return The proposal result of the default java content assist
40 | */
41 | List proposallist;
42 | ContentAssistInvocationContext context;
43 | IProgressMonitor monitor;
44 |
45 | public getProposalResult(ContentAssistInvocationContext context, IProgressMonitor monitor){
46 | // TODO Auto-generated constructor stub
47 | this.context = context;
48 | this.monitor = monitor;
49 | this.proposallist = computeCompletionProposals(context, monitor);
50 | }
51 |
52 | public List getAllProposalResult(){
53 |
54 | return proposallist;
55 | }
56 | public List getAllProposalResultInformation(){
57 | return computeContextInformation(context, monitor);
58 | }
59 | }
60 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/View/JavaCompletionProposalComputer1.java:
--------------------------------------------------------------------------------
1 | package jp.ac.ritsumei.cs.fse.contentassist.View;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 | import java.util.Map;
6 |
7 | import jp.ac.ritsumei.cs.fse.contentassist.Activator;
8 | import jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser.ConsoleOperationListener2;
9 | import jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser.DataManager;
10 | import jp.ac.ritsumei.cs.fse.contentassist.DataAnalyser.getProposalResult;
11 | import jp.ac.ritsumei.cs.fse.contentassist.entity.ApplyOperation;
12 |
13 | import org.eclipse.core.runtime.IProgressMonitor;
14 | import org.eclipse.jdt.internal.ui.text.java.AbstractJavaCompletionProposal;
15 | import org.eclipse.jdt.internal.ui.text.java.ProposalInfo;
16 | import org.eclipse.jdt.ui.text.java.ContentAssistInvocationContext;
17 | import org.eclipse.jdt.ui.text.java.IJavaCompletionProposalComputer;
18 | import org.eclipse.jface.preference.JFacePreferences;
19 | import org.eclipse.jface.text.contentassist.CompletionProposal;
20 | import org.eclipse.jface.text.contentassist.ICompletionProposal;
21 | import org.eclipse.jface.text.contentassist.IContextInformation;
22 | import org.eclipse.jface.viewers.StyledString;
23 | import org.eclipse.jface.viewers.StyledString.Styler;
24 |
25 | public class JavaCompletionProposalComputer1 implements
26 | IJavaCompletionProposalComputer {
27 | public JavaCompletionProposalComputer1() {
28 | // TODO Auto-generated constructor stub
29 |
30 | }
31 |
32 | public void sessionStarted() {
33 | // TODO Auto-generated method stub
34 |
35 | }
36 | public static final Styler LIAOZIYANG = StyledString.createColorRegistryStyler(
37 | JFacePreferences.ACTIVE_HYPERLINK_COLOR, null);
38 | public List computeCompletionProposals(ContentAssistInvocationContext context, IProgressMonitor monitor) {
39 | List propList = new ArrayList();
40 | List newpropList = new ArrayList();
41 | List propList2 = new ArrayList();
42 |
43 | ICompletionProposal first;
44 | DataManager datamanger = new DataManager(context,monitor);
45 | Activator.applyoperationlist.add(new ApplyOperation(ConsoleOperationListener2.ope.getStart(), ConsoleOperationListener2.ope.getAuthor(), ConsoleOperationListener2.ope.getFilePath(), propList));
46 | List list = new ArrayList();
47 | CompletionProposal proposal;
48 | propList = datamanger.JavaDefaultProposal();
49 | propList2 = datamanger.ContextInformation();
50 | ApplyOperation ao = new ApplyOperation(ConsoleOperationListener2.ope.getStart(), ConsoleOperationListener2.ope.getAuthor(), ConsoleOperationListener2.ope.getFilePath(), propList);
51 | System.out.println(ao.toString());
52 | return newpropList;
53 | }
54 |
55 | public List computeContextInformation(ContentAssistInvocationContext context, IProgressMonitor monitor) {
56 | // TODO Auto-generated method stub
57 | return null;
58 | }
59 |
60 | public String getErrorMessage() {
61 | // TODO Auto-generated method stub
62 | return null;
63 | }
64 |
65 | public void sessionEnded() {
66 | // TODO Auto-generated method stub
67 | }
68 |
69 | }
70 |
--------------------------------------------------------------------------------
/jp.ac.ritsumei.cs.fse.contentassist/src/jp/ac/ritsumei/cs/fse/contentassist/entity/ApplyOperation.java:
--------------------------------------------------------------------------------
1 | package jp.ac.ritsumei.cs.fse.contentassist.entity;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import org.eclipse.jface.text.contentassist.ICompletionProposal;
7 |
8 | public class ApplyOperation {
9 | private int offset;
10 | private int last_offset;
11 | private List InputString = new ArrayList();
12 | private long applytime;
13 | public String username;
14 | public String path;
15 | private boolean isApplied;
16 | private List propList;
17 | public ApplyOperation(int offset,String username,String path,List propList){
18 | this.offset = offset;
19 | this.last_offset = offset;
20 | this.username = username;
21 | this.path = path;
22 | this.propList = propList;
23 | InputString.add('.');
24 |
25 | }
26 | public int getOffset() {
27 | return offset;
28 | }
29 | public void setOffset(int offset) {
30 | this.offset = offset;
31 | }
32 |
33 | public List getInputString() {
34 | return InputString;
35 | }
36 |
37 | public long getApplytime() {
38 | return applytime;
39 | }
40 | public void setApplytime(long applytime) {
41 | this.applytime = applytime;
42 | }
43 | public String getUsername() {
44 | return username;
45 | }
46 |
47 | public String getPath() {
48 | return path;
49 | }
50 | public boolean isApplied(){
51 | return isApplied;
52 | }
53 | public void update(int operation_offset,String delete_string,String insert_string){
54 | if (operation_offset <= offset){
55 | offset = offset + delete_string.length() - insert_string.length();
56 | last_offset = last_offset + delete_string.length() - insert_string.length();
57 | }
58 | else if(last_offset > operation_offset&&operation_offset > offset){
59 | last_offset = last_offset + insert_string.length() - delete_string.length();
60 | for(int i=0;i<=operation_offset - offset;i++){
61 | InputString.remove(i);
62 | }
63 | InputString.add(operation_offset-offset, insert_string.charAt(0));
64 | }
65 |
66 | }
67 | /* (non-Javadoc)
68 | * @see java.lang.Object#toString()
69 | */
70 | @Override
71 | public String toString() {
72 | return "ApplyOperation [offset=" + offset + ", last_offset="
73 | + last_offset + ", InputString=" + InputString + ", applytime="
74 | + applytime + ", username=" + username + ", path=" + path
75 | + ", propList=" + propList + "]";
76 | }
77 |
78 |
79 | }
80 |
--------------------------------------------------------------------------------
/structure.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/structure.png
--------------------------------------------------------------------------------
/編集履歴から算出した開発者の関心度に基づくコード補完.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/liaoziyang/ContentAssist/9f1c42158ddc765438b5e488ccf699372850fb2e/編集履歴から算出した開発者の関心度に基づくコード補完.pdf
--------------------------------------------------------------------------------