001    /**
002     * Created by IntelliJ IDEA.
003     * User: Wei Wang
004     * Date: Nov 30, 2002
005     * Time: 7:49:41 PM
006     */
007    
008    package EVolve.visualization.XYViz.ValValViz;
009    
010    import EVolve.visualization.*;
011    import EVolve.visualization.Dimension;
012    import EVolve.Scene;
013    import EVolve.util.*;
014    import EVolve.util.Equators.*;
015    import EVolve.util.Equators.Set;
016    import EVolve.util.Painters.RandomPainter;
017    import EVolve.data.*;
018    import javax.swing.*;
019    import java.util.*;
020    import java.awt.event.*;
021    import java.awt.*;
022    
023    public class DotplotViz extends ValueValueVisualization {
024        private ArrayList menuList;
025        private JMenuItem itemChangeThread;
026        private JTextField textInterval,textMatch, textBegin,textEnd;
027        private DataTrace trace;
028        private int event;
029        private JComboBox comboEquator;
030        private Equator[] equatorList;
031        private float percent;
032        private Equator selectedEquator;
033        private JMenuItem itemSelectX, itemSelectTimeFrame;
034        private static JMenuItem selectionMenu[] = null;
035        private static int SELECT_OPTION = 0x0011;
036    
037        public DotplotViz() {
038            super();
039            dataFilterName = new String[1];
040            dataFilterName[0] = "Thread";
041    
042            menuList = new ArrayList();
043    
044            beginCall = 0;
045            endCall = 300;
046            interval = 10;
047            percent = 100;
048    
049    
050            equatorList = new Equator[2];
051            equatorList[0] = new OrderedEquator();
052            equatorList[1] = new UnorderedEquator();
053            selectedEquator = null;
054        }
055    
056        public Dimension[] createDimension() {
057            Dimension [] returnDimension = super.createDimension();
058    
059            returnDimension[1] = zAxis;
060            internalDimension[0] = threadFilter;
061    
062            return returnDimension;
063        }
064    
065        public void autoUpdateConfiguration(HashMap config) {
066            super.autoUpdateConfiguration(config);
067            if (config.get("Match")!=null) {
068                percent = ((Float)(config.get("Match"))).floatValue();
069            }
070            if (config.get("Options")!=null) {
071                String equatorName = (String)config.get("Options");
072                for (int i=0; i<equatorList.length; i++)
073                    if (equatorList[i].getName().equals(equatorName)) {
074                        selectedEquator = equatorList[i];
075                        comboEquator.setSelectedIndex(i);
076                        break;
077                    }
078            }
079            textInterval.setText(String.valueOf(interval));
080            textMatch.setText(String.valueOf(percent));
081            textBegin.setText(String.valueOf(beginCall));
082            textEnd.setText(String.valueOf(endCall));
083        }
084    
085        protected void updateConfiguration() {
086    
087            if (Scene.getFilter().getSelection().length != 0) {
088                textBegin.setEnabled(false);
089                textEnd.setEnabled(false);
090            } else {
091                textBegin.setEnabled(true);
092                textEnd.setEnabled(true);
093            }
094    
095            subject = subjectDefinition.getName();
096            selectedEquator = equatorList[comboEquator.getSelectedIndex()];
097    
098            try {
099                if (autoInterval != -1) {
100                    interval = autoInterval;
101                    autoInterval = -1;
102                } else {
103                    interval = Integer.parseInt(textInterval.getText());
104                    percent = Float.parseFloat(textMatch.getText());
105                    if ((percent>100)||(percent < 0)) {
106                        Scene.showErrorMessage("Match percent must be between 0 and 100.");
107                        configure();
108                    }
109                    textInterval.setText(String.valueOf(interval));
110                    textMatch.setText(String.valueOf(percent));
111                }
112    
113                beginCall = Integer.parseInt(textBegin.getText());
114                endCall = Integer.parseInt(textEnd.getText());
115                selectedEquator.setInterval(interval);
116                selectedEquator.setMatch(percent);
117    
118                ((AxesPanel)panel).setName(zAxis.getName(), zAxis.getName());
119                super.updateConfiguration();
120            } catch (Exception e) {
121                Scene.showErrorMessage("Interval, begin call and end call must be an integer and smaller than "+Integer.MAX_VALUE+".");
122                configure();
123            };
124    
125        }
126    
127        public HashMap getCurrentConfigure() {
128            HashMap configure = super.getCurrentConfigure();
129    
130            configure.put("Interval", interval+";"+beginCall+","+endCall+","+percent);
131            configure.put("Options", selectedEquator.getName());
132    
133            return configure;
134        }
135    
136        public void preVisualize() {
137            image = new AutoImage();
138            trace = selectedEquator.initialDataTrace(interval, Scene.getDataManager().getEntity()[zAxis.getDataFilter().getTargetType()].length);
139            event = 0;
140            getSelection();
141            installPainter();
142            super.preVisualize();
143        }
144    
145        protected void receiveElement(Element element) {
146            if (element.getField()[element.getField().length-1] == Integer.MAX_VALUE)
147                return;
148    
149            int traceId = zAxis.getField(element);
150            int no = xAxis.getField(element) - 1;
151    
152            countEvents(no);
153            if ((no < beginCall)||(no > endCall)) {
154                return;
155            }
156    
157            event++;
158            trace.updateTrace3(traceId);
159    
160            ArrayList data = trace.getTrace();
161    
162            if ((event%interval == 0)||(event-endCall==1)) {
163                int size = data.size() - 1;
164                for (int i=size+1; i>1; i--) {
165                    Set set1 = (Set)data.get(size);
166                    Set set2 = (Set)data.get(i-2);
167                    if (selectedEquator.isEqual(set1,set2)) {
168                        painter.paint(image,i-2,size,set1.getHashValue());
169                        painter.paint(image,size,i-2,set1.getHashValue());
170                    }
171                }
172                if (size>=0) image.setColor(size,size,Color.black);
173            }
174        }
175    
176        public void visualize() {
177            ((AxesPanel)panel).setName("Time - " + xAxis.getDataFilter().getName() + " (" + event +" events)", "Time - " + xAxis.getDataFilter().getName() + " (" + event + " events)");
178            sort();
179        }
180    
181        protected void mouseMove(int x,int y) {
182            if (interval > 1) return;
183    
184            int X = ((AxesPanel)panel).getImageX(x);
185            int Y = ((AxesPanel)panel).getImageY(y);
186            int index = X < Y ? X : Y;
187            if ((index >= 0) && (index < trace.size())) {
188                int methodId = ((Set)trace.getTrace().get(index)).getElement(0);
189                if (shift_pressed && (image.getSortedColor(null,null,X,Y)==null))
190                    Scene.setStatus("  ");
191                else
192                    Scene.setStatus(Scene.getDataManager().getEntity()[zAxis.getDataFilter().getTargetType()][methodId].getName());
193            } else {
194                Scene.setStatus(" ");
195            }
196        }
197    
198        public void makeSelection() {
199            ArrayList idList = new ArrayList();
200    
201            int x1 = ((AxesPanel)panel).getStartX();
202            int x2 = ((AxesPanel)panel).getEndX();
203    
204            if (x1 < 0) x1 = 0;
205            if (x2 >= trace.getTrace().size()) x2 = trace.getTrace().size()-1;
206    
207            Set unionSet = ((Set)(trace.getTrace().get(x1)));
208            for (int i=x1+1; i<=x2; i++) {
209                Set next = ((Set)(trace.getTrace().get(i)));
210                unionSet = unionSet.union(next);
211            }
212    
213            for (int i=0; i<unionSet.getValidSize(); i++) {
214                if (unionSet.getEntityId(i)!=-1)
215                    idList.add(new Integer(unionSet.getEntityId(i)));
216            }
217    
218            int selection[] = null;
219            if ((SELECT_OPTION & 0x00f0) == 0x0010) {
220                selection = new int[idList.size()];
221                for (int i=0; i<selection.length; i++)
222                    selection[i] = ((Integer)idList.get(i)).intValue();
223            } else {
224                selection = new int[zAxis.getEntityNumber()];
225                for (int i=0; i<selection.length; i++)
226                    selection[i] = i;
227            }
228    
229    
230            int start = ((Integer)eventCounter.get(x1)).intValue();
231            int end;
232            if (x1==x2) {
233                if (x1+1>trace.getTrace().size()-1)
234                    end = Integer.MAX_VALUE;
235                else
236                    end = ((Integer)eventCounter.get(x1+1)).intValue() -1;
237            } else {
238                end = ((Integer)eventCounter.get(x2)).intValue();
239            }
240            if ((SELECT_OPTION & 0x000f) == 0x0000) {
241                start = 0;
242                end = Integer.MAX_VALUE;
243            }
244            Scene.getFilter().addSelection(new Selection(zAxis.getDataFilter().getTargetType(), selection,
245                                           start,end));
246        }
247    
248        protected ArrayList createOptionalMenu() {
249            if (menuList.size() > 0) return null;
250    
251            menuList.clear();
252    
253            itemChangeThread = new JMenuItem("Switch thread...");
254            itemChangeThread.setMnemonic(KeyEvent.VK_T);
255            itemChangeThread.addActionListener(new ActionListener() {
256                public void actionPerformed(ActionEvent e) {
257                    visualize();
258                }
259            });
260    
261            menuList.add(itemChangeThread);
262            return menuList;
263        }
264    
265        protected JPanel createConfigurationPanel() {
266            JPanel returnVal = new JPanel(new GridLayout(1, 1, 5, 5));
267            JPanel panelEvent = new JPanel(new GridLayout(2,2));
268            JPanel equatorBox = new JPanel(new GridLayout(1,2));
269    
270            Box panelBottom = new Box(BoxLayout.Y_AXIS);
271            returnVal.add(panelBottom);
272    
273            textBegin = new JTextField(String.valueOf(beginCall));
274            textEnd = new JTextField(String.valueOf(endCall));
275            panelEvent.add(new JLabel("From Event No:"));
276            panelEvent.add(textBegin);
277            panelEvent.add(new JLabel("To Event No:"));
278            panelEvent.add(textEnd);
279            panelBottom.add(panelEvent);
280    
281            comboEquator = new JComboBox();
282            for (int i=0; i<equatorList.length; i++)
283                comboEquator.addItem(equatorList[i].getName());
284            comboEquator.addActionListener(new ActionListener() {
285                public void actionPerformed(ActionEvent e) {
286                    textInterval.setText(String.valueOf(equatorList[comboEquator.getSelectedIndex()].getInterval()));
287                    textMatch.setText(String.valueOf(equatorList[comboEquator.getSelectedIndex()].getMatch()));
288                }
289            });
290    
291            equatorBox.add(new JLabel("Equator:"));
292            equatorBox.add(comboEquator);
293            panelBottom.add(equatorBox);
294    
295            JPanel panelEquator = new JPanel(new GridLayout(2,2));
296    
297            textInterval = new JTextField(String.valueOf(interval));
298            textMatch = new JTextField(String.valueOf(percent));
299    
300            panelEquator.add(new JLabel("Interval:"));
301            panelEquator.add(textInterval);
302            panelEquator.add(new JLabel("Match:"));
303            panelEquator.add(textMatch);
304    
305            panelBottom.add(panelEquator);
306    
307            return returnVal;
308        }
309    
310        protected void changeOrientation() {
311        }
312    
313        protected void installPainter() {
314            painter = new RandomPainter();
315        }
316    
317        public JMenuItem[] createSelectionMenuItem() {
318            if (selectionMenu != null) return selectionMenu;
319    
320            itemSelectTimeFrame = new JCheckBoxMenuItem("Time Frame");
321            itemSelectTimeFrame.setMnemonic(KeyEvent.VK_T);
322            itemSelectTimeFrame.addActionListener(new ActionListener() {
323                public void actionPerformed(ActionEvent e) {
324                    boolean selected = itemSelectTimeFrame.isSelected();
325                    SELECT_OPTION = switchOption(selected, SELECT_OPTION, SELECT_TIME_FRAME);
326                }
327            });
328            itemSelectTimeFrame.setSelected(true);
329    
330            itemSelectX = new JCheckBoxMenuItem("Occurred Entitiies");
331            itemSelectX.setMnemonic(KeyEvent.VK_O);
332            itemSelectX.addActionListener(new ActionListener() {
333                public void actionPerformed(ActionEvent e) {
334                    boolean selected = itemSelectX.isSelected();
335                    SELECT_OPTION = switchOption(selected, SELECT_OPTION, SELECT_OCCURRED_ENTITIES);
336                }
337            });
338            itemSelectX.setSelected(true);
339    
340            selectionMenu = new JMenuItem[2];
341            selectionMenu[0] = itemSelectTimeFrame;
342            selectionMenu[1] = itemSelectX;
343    
344            return selectionMenu;
345        }
346    }