|
1 package org.chromium.debug.ui.actions; |
|
2 |
|
3 import java.text.MessageFormat; |
|
4 import java.util.HashSet; |
|
5 import java.util.Iterator; |
|
6 import java.util.Set; |
|
7 |
|
8 import org.chromium.debug.core.ChromiumDebugPlugin; |
|
9 import org.chromium.debug.core.model.BreakpointSynchronizer; |
|
10 import org.chromium.debug.core.model.DebugTargetImpl; |
|
11 import org.chromium.debug.core.model.BreakpointSynchronizer.Direction; |
|
12 import org.eclipse.core.runtime.IProgressMonitor; |
|
13 import org.eclipse.core.runtime.IStatus; |
|
14 import org.eclipse.core.runtime.Status; |
|
15 import org.eclipse.core.runtime.jobs.Job; |
|
16 import org.eclipse.debug.core.ILaunch; |
|
17 import org.eclipse.debug.core.model.IDebugElement; |
|
18 import org.eclipse.debug.core.model.IDebugTarget; |
|
19 import org.eclipse.jface.action.IAction; |
|
20 import org.eclipse.jface.viewers.ISelection; |
|
21 import org.eclipse.jface.viewers.IStructuredSelection; |
|
22 import org.eclipse.ui.IWorkbenchWindow; |
|
23 import org.eclipse.ui.IWorkbenchWindowActionDelegate; |
|
24 |
|
25 public class SynchronizeBreakpoints implements IWorkbenchWindowActionDelegate { |
|
26 |
|
27 public static class ResetRemote extends SynchronizeBreakpoints { |
|
28 public ResetRemote() { |
|
29 super(BreakpointSynchronizer.Direction.RESET_REMOTE); |
|
30 } |
|
31 } |
|
32 |
|
33 public static class ResetLocal extends SynchronizeBreakpoints { |
|
34 public ResetLocal() { |
|
35 super(BreakpointSynchronizer.Direction.RESET_LOCAL); |
|
36 } |
|
37 } |
|
38 |
|
39 public static class Merge extends SynchronizeBreakpoints { |
|
40 public Merge() { |
|
41 super(BreakpointSynchronizer.Direction.MERGE); |
|
42 } |
|
43 } |
|
44 |
|
45 private final BreakpointSynchronizer.Direction direction; |
|
46 |
|
47 protected SynchronizeBreakpoints(Direction direction) { |
|
48 this.direction = direction; |
|
49 } |
|
50 |
|
51 public void dispose() { |
|
52 } |
|
53 |
|
54 public void init(IWorkbenchWindow window) { |
|
55 } |
|
56 |
|
57 public void run(IAction action) { |
|
58 if (currentRunnable == null) { |
|
59 return; |
|
60 } |
|
61 currentRunnable.run(); |
|
62 currentRunnable = null; |
|
63 } |
|
64 |
|
65 public void selectionChanged(IAction action, ISelection selection) { |
|
66 currentRunnable = createRunnable(selection); |
|
67 action.setEnabled(currentRunnable != null); |
|
68 } |
|
69 |
|
70 private Runnable createRunnable(ISelection selection) { |
|
71 if (selection instanceof IStructuredSelection == false) { |
|
72 return null; |
|
73 } |
|
74 IStructuredSelection structuredSelection = (IStructuredSelection) selection; |
|
75 final Set<DebugTargetImpl> targets = new HashSet<DebugTargetImpl>(3); |
|
76 for (Iterator<?> it = structuredSelection.iterator(); it.hasNext(); ) { |
|
77 Object element = it.next(); |
|
78 IDebugTarget debugTarget; |
|
79 if (element instanceof ILaunch) { |
|
80 ILaunch launch = (ILaunch) element; |
|
81 debugTarget = launch.getDebugTarget(); |
|
82 } else if (element instanceof IDebugElement) { |
|
83 IDebugElement debugElement = (IDebugElement) element; |
|
84 debugTarget = debugElement.getDebugTarget(); |
|
85 } else { |
|
86 continue; |
|
87 } |
|
88 if (debugTarget instanceof DebugTargetImpl == false) { |
|
89 continue; |
|
90 } |
|
91 DebugTargetImpl debugTargetImpl = (DebugTargetImpl) debugTarget; |
|
92 targets.add(debugTargetImpl); |
|
93 } |
|
94 if (targets.isEmpty()) { |
|
95 return null; |
|
96 } |
|
97 if (direction != BreakpointSynchronizer.Direction.RESET_REMOTE && targets.size() > 1) { |
|
98 // Only "reset remote" mode is implemented for a multiple selection. |
|
99 return null; |
|
100 } |
|
101 |
|
102 return new Runnable() { |
|
103 public void run() { |
|
104 new Job(MessageFormat.format(Messages.SynchronizeBreakpoints_JOB_TITLE, targets.size())) { |
|
105 @Override |
|
106 protected IStatus run(IProgressMonitor monitor) { |
|
107 // TODO(peter.rybin): consider blocking this method until callback is invoked to |
|
108 // keep the UI jobs open while something is still happening. |
|
109 BreakpointSynchronizer.Callback callback = new BreakpointSynchronizer.Callback() { |
|
110 public void onDone(IStatus status) { |
|
111 ChromiumDebugPlugin.log(status); |
|
112 } |
|
113 }; |
|
114 |
|
115 // TODO(peter.rybin): consider showing progress for several targets. |
|
116 for (DebugTargetImpl target : targets) { |
|
117 target.synchronizeBreakpoints(direction, callback); |
|
118 } |
|
119 return Status.OK_STATUS; |
|
120 } |
|
121 }.schedule(); |
|
122 } |
|
123 }; |
|
124 } |
|
125 |
|
126 private Runnable currentRunnable; |
|
127 } |