diff --git a/modules/DesktopTimeline/pom.xml b/modules/DesktopTimeline/pom.xml index b0d65629d9ac2ad931a5b5569b555a1320cfeafb..faf4d35f8fa3cb6a37fc84504a87beed7b4f3950 100644 --- a/modules/DesktopTimeline/pom.xml +++ b/modules/DesktopTimeline/pom.xml @@ -5,7 +5,7 @@ gephi-parent org.gephi 0.9-SNAPSHOT - ../.. + ../.. org.gephi @@ -22,19 +22,23 @@ ${project.groupId} - data-attributes-api + desktop-banner ${project.groupId} - desktop-perspective + lib.validation ${project.groupId} - lib.validation + graph-api + + + ${project.groupId} + timeline-api ${project.groupId} - timeline + visualization ${project.groupId} @@ -56,6 +60,10 @@ ${project.groupId} ui-library-wrapper + + org.netbeans.api + org-openide-util-ui + org.netbeans.api org-openide-dialogs diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/BottomComponentImpl.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/BottomComponentImpl.java index 5da4f7a7d780cf5ddb033b70a42d77a9edddb320..902084a7071e3f3cf765e91780ea8c223e471d77 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/BottomComponentImpl.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/BottomComponentImpl.java @@ -42,7 +42,8 @@ package org.gephi.desktop.timeline; import javax.swing.JComponent; -import org.gephi.desktop.perspective.spi.BottomComponent; +import org.gephi.desktop.banner.perspective.spi.BottomComponent; +import org.gephi.visualization.VizController; import org.openide.util.lookup.ServiceProvider; /** @@ -52,16 +53,19 @@ import org.openide.util.lookup.ServiceProvider; @ServiceProvider(service=BottomComponent.class) public class BottomComponentImpl implements BottomComponent { - private TimelineTopComponent timelineTopComponent = new TimelineTopComponent(); + private final TimelineTopComponent timelineTopComponent = new TimelineTopComponent(); + @Override public JComponent getComponent() { return timelineTopComponent; } + @Override public void setVisible(boolean visible) { timelineTopComponent.setTimeLineVisible(visible); } + @Override public boolean isVisible() { return timelineTopComponent.isVisible(); } diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/CustomBoundsDialog.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/CustomBoundsDialog.java index 68fca04261a56cfab5e31dd914f0e2b87f72034e..9a0a174db2190428003c6f0c51d5f5731b3b60d3 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/CustomBoundsDialog.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/CustomBoundsDialog.java @@ -44,21 +44,18 @@ package org.gephi.desktop.timeline; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.text.NumberFormat; -import java.text.ParseException; -import java.text.SimpleDateFormat; -import java.util.Date; import java.util.Locale; import javax.swing.JTextField; -import org.gephi.dynamic.DynamicUtilities; -import org.gephi.dynamic.api.DynamicModel.TimeFormat; +import org.gephi.graph.api.AttributeUtils; +import org.gephi.graph.api.TimeFormat; import org.gephi.timeline.api.TimelineController; import org.gephi.timeline.api.TimelineModel; +import org.joda.time.format.ISODateTimeFormat; import org.netbeans.validation.api.Problems; import org.netbeans.validation.api.Validator; import org.netbeans.validation.api.builtin.Validators; import org.netbeans.validation.api.ui.ValidationGroup; import org.netbeans.validation.api.ui.ValidationPanel; -import org.openide.util.Exceptions; import org.openide.util.Lookup; import org.openide.util.NbBundle; @@ -68,8 +65,6 @@ import org.openide.util.NbBundle; */ public class CustomBoundsDialog extends javax.swing.JPanel { - private final SimpleDateFormat DATE_FORMAT = new SimpleDateFormat("yyyy-MM-dd"); - private final SimpleDateFormat DATETIME_FORMAT = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss:SS"); private TimelineModel model; private TimelineController controller; @@ -85,34 +80,28 @@ public class CustomBoundsDialog extends javax.swing.JPanel { } public void setDefaults() { - if (model.getTimeFormat().equals(TimeFormat.DATE)) { - Date min = DynamicUtilities.getDateFromDouble(model.getMin()); - Date max = DynamicUtilities.getDateFromDouble(model.getMax()); - Date from = DynamicUtilities.getDateFromDouble(model.getMin()); - Date to = DynamicUtilities.getDateFromDouble(model.getMax()); - - minTextField.setText(DATE_FORMAT.format(min)); - maxTextField.setText(DATE_FORMAT.format(max)); - startTextField.setText(DATE_FORMAT.format(from)); - endTextField.setText(DATE_FORMAT.format(to)); - } else if (model.getTimeFormat().equals(TimeFormat.DATETIME)) { - Date min = DynamicUtilities.getDateFromDouble(model.getMin()); - Date max = DynamicUtilities.getDateFromDouble(model.getMax()); - Date from = DynamicUtilities.getDateFromDouble(model.getMin()); - Date to = DynamicUtilities.getDateFromDouble(model.getMax()); - - minTextField.setText(DATETIME_FORMAT.format(min)); - maxTextField.setText(DATETIME_FORMAT.format(max)); - startTextField.setText(DATETIME_FORMAT.format(from)); - endTextField.setText(DATETIME_FORMAT.format(to)); - } else { - NumberFormat f = NumberFormat.getInstance(Locale.ENGLISH); - f.setGroupingUsed(false); - f.setMaximumFractionDigits(20); - minTextField.setText(f.format(model.getMin())); - maxTextField.setText(f.format(model.getMax())); - startTextField.setText(f.format(model.getMin())); - endTextField.setText(f.format(model.getMax())); + switch (model.getTimeFormat()) { + case DATE: + minTextField.setText(AttributeUtils.printDate(model.getMin())); + maxTextField.setText(AttributeUtils.printDate(model.getMax())); + startTextField.setText(AttributeUtils.printDate(model.getMin())); + endTextField.setText(AttributeUtils.printDate(model.getMax())); + break; + case DATETIME: + minTextField.setText(AttributeUtils.printDateTime(model.getMin())); + maxTextField.setText(AttributeUtils.printDateTime(model.getMax())); + startTextField.setText(AttributeUtils.printDateTime(model.getMin())); + endTextField.setText(AttributeUtils.printDateTime(model.getMax())); + break; + default: + NumberFormat f = NumberFormat.getInstance(Locale.ENGLISH); + f.setGroupingUsed(false); + f.setMaximumFractionDigits(20); + minTextField.setText(f.format(model.getMin())); + maxTextField.setText(f.format(model.getMax())); + startTextField.setText(f.format(model.getMin())); + endTextField.setText(f.format(model.getMax())); + break; } } @@ -120,65 +109,42 @@ public class CustomBoundsDialog extends javax.swing.JPanel { this.model = timelineModel; this.controller = Lookup.getDefault().lookup(TimelineController.class); setDefaults(); - - if (model.getTimeFormat().equals(TimeFormat.DATE)) { - Date min = DynamicUtilities.getDateFromDouble(model.getCustomMin()); - Date max = DynamicUtilities.getDateFromDouble(model.getCustomMax()); - Date from = DynamicUtilities.getDateFromDouble(model.getIntervalStart()); - Date to = DynamicUtilities.getDateFromDouble(model.getIntervalEnd()); - - minTextField.setText(DATE_FORMAT.format(min)); - maxTextField.setText(DATE_FORMAT.format(max)); - startTextField.setText(DATE_FORMAT.format(from)); - endTextField.setText(DATE_FORMAT.format(to)); - } else if (model.getTimeFormat().equals(TimeFormat.DATETIME)) { - Date min = DynamicUtilities.getDateFromDouble(model.getCustomMin()); - Date max = DynamicUtilities.getDateFromDouble(model.getCustomMax()); - Date from = DynamicUtilities.getDateFromDouble(model.getIntervalStart()); - Date to = DynamicUtilities.getDateFromDouble(model.getIntervalEnd()); - - minTextField.setText(DATETIME_FORMAT.format(min)); - maxTextField.setText(DATETIME_FORMAT.format(max)); - startTextField.setText(DATETIME_FORMAT.format(from)); - endTextField.setText(DATETIME_FORMAT.format(to)); - } else { - NumberFormat f = NumberFormat.getInstance(Locale.ENGLISH); - f.setGroupingUsed(false); - f.setMaximumFractionDigits(20); - minTextField.setText(f.format(model.getCustomMin())); - maxTextField.setText(f.format(model.getCustomMax())); - startTextField.setText(f.format(model.getIntervalStart())); - endTextField.setText(f.format(model.getIntervalEnd())); + + switch (model.getTimeFormat()) { + case DATE: + minTextField.setText(AttributeUtils.printDate(model.getCustomMin())); + maxTextField.setText(AttributeUtils.printDate(model.getCustomMax())); + startTextField.setText(AttributeUtils.printDate(model.getIntervalStart())); + endTextField.setText(AttributeUtils.printDate(model.getIntervalEnd())); + break; + case DATETIME: + minTextField.setText(AttributeUtils.printDateTime(model.getCustomMin())); + maxTextField.setText(AttributeUtils.printDateTime(model.getCustomMax())); + startTextField.setText(AttributeUtils.printDateTime(model.getIntervalStart())); + endTextField.setText(AttributeUtils.printDateTime(model.getIntervalEnd())); + break; + default: + NumberFormat f = NumberFormat.getInstance(Locale.ENGLISH); + f.setGroupingUsed(false); + f.setMaximumFractionDigits(20); + minTextField.setText(f.format(model.getCustomMin())); + maxTextField.setText(f.format(model.getCustomMax())); + startTextField.setText(f.format(model.getIntervalStart())); + endTextField.setText(f.format(model.getIntervalEnd())); + break; } } public void unsetup() { - if (model.getTimeFormat().equals(TimeFormat.DATE)) { - try { - double min = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(minTextField.getText())); - double max = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(maxTextField.getText())); - double start = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(startTextField.getText())); - double end = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(endTextField.getText())); - start = Math.max(min, start); - end = Math.min(max, end); - controller.setCustomBounds(min, max); - controller.setInterval(start, end); - } catch (ParseException ex) { - Exceptions.printStackTrace(ex); - } - } else if (model.getTimeFormat().equals(TimeFormat.DATETIME)) { - try { - double min = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(minTextField.getText())); - double max = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(maxTextField.getText())); - double start = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(startTextField.getText())); - double end = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(endTextField.getText())); - start = Math.max(min, start); - end = Math.min(max, end); - controller.setCustomBounds(min, max); - controller.setInterval(start, end); - } catch (ParseException ex) { - Exceptions.printStackTrace(ex); - } + if (model.getTimeFormat().equals(TimeFormat.DATE) || model.getTimeFormat().equals(TimeFormat.DATETIME)) { + double min = AttributeUtils.parseDateTime(minTextField.getText()); + double max = AttributeUtils.parseDateTime(maxTextField.getText()); + double start = AttributeUtils.parseDateTime(startTextField.getText()); + double end = AttributeUtils.parseDateTime(endTextField.getText()); + start = Math.max(min, start); + end = Math.min(max, end); + controller.setCustomBounds(min, max); + controller.setInterval(start, end); } else { double min = Double.parseDouble(minTextField.getText()); double max = Double.parseDouble(maxTextField.getText()); @@ -223,42 +189,17 @@ public class CustomBoundsDialog extends javax.swing.JPanel { public boolean validate(Problems prblms, String string, String t) { double thisDate; double otherDate; - if (model.getTimeFormat().equals(TimeFormat.DATE)) { - try { - thisDate = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(t)); - otherDate = DynamicUtilities.getDoubleFromDate(DATE_FORMAT.parse(other.getText())); - double minDate = max ? otherDate : thisDate; - double maxDate = max ? thisDate : otherDate; - if(minDate < model.getMin()) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.min")); - return false; - } - if(maxDate > model.getMax()) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.max")); - return false; - } - if (minDate >= maxDate) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator")); - return false; - } else if (maxDate <= minDate) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator")); - return false; - } - } catch (ParseException ex) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", DATE_FORMAT.toPattern())); - return false; - } - } else if (model.getTimeFormat().equals(TimeFormat.DATETIME)) { + if (model.getTimeFormat().equals(TimeFormat.DATE) || model.getTimeFormat().equals(TimeFormat.DATETIME)) { try { - thisDate = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(t)); - otherDate = DynamicUtilities.getDoubleFromDate(DATETIME_FORMAT.parse(other.getText())); + thisDate = AttributeUtils.parseDateTime(t); + otherDate = AttributeUtils.parseDateTime(other.getText()); double minDate = max ? otherDate : thisDate; double maxDate = max ? thisDate : otherDate; - if(minDate < model.getMin()) { + if (minDate < model.getMin()) { prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.min")); return false; } - if(maxDate > model.getMax()) { + if (maxDate > model.getMax()) { prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.max")); return false; } @@ -269,21 +210,22 @@ public class CustomBoundsDialog extends javax.swing.JPanel { prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator")); return false; } - } catch (ParseException ex) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", DATETIME_FORMAT.toPattern())); + } catch (Exception ex) { + prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", ISODateTimeFormat.dateTime())); return false; } + } else { try { thisDate = Double.parseDouble(t); otherDate = Double.parseDouble(other.getText()); double minDate = max ? otherDate : thisDate; double maxDate = max ? thisDate : otherDate; - if(minDate < model.getMin()) { + if (minDate < model.getMin()) { prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.min")); return false; } - if(maxDate > model.getMax()) { + if (maxDate > model.getMax()) { prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.TimeValidator.max")); return false; } @@ -308,16 +250,16 @@ public class CustomBoundsDialog extends javax.swing.JPanel { public boolean validate(Problems prblms, String string, String t) { if (model.getTimeFormat().equals(TimeFormat.DATE)) { try { - DATE_FORMAT.parse(t); - } catch (ParseException ex) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", DATE_FORMAT.toPattern())); + AttributeUtils.parseDateTime(t); + } catch (Exception ex) { + prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", ISODateTimeFormat.date())); return false; } } else if (model.getTimeFormat().equals(TimeFormat.DATETIME)) { try { - DATETIME_FORMAT.parse(t); - } catch (ParseException ex) { - prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", DATETIME_FORMAT.toPattern())); + AttributeUtils.parseDateTime(t); + } catch (Exception ex) { + prblms.add(NbBundle.getMessage(CustomBoundsDialog.class, "CustomBoundsDialog.FormatValidator.date", ISODateTimeFormat.dateTime())); return false; } } else { @@ -332,10 +274,10 @@ public class CustomBoundsDialog extends javax.swing.JPanel { } } - /** This method is called from within the constructor to - * initialize the form. - * WARNING: Do NOT modify this code. The content of this method is - * always regenerated by the Form Editor. + /** + * This method is called from within the constructor to initialize the form. + * WARNING: Do NOT modify this code. The content of this method is always + * regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // //GEN-BEGIN:initComponents diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/DateTick.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/DateTick.java index c9316bbda619eccc6bd86e28a306e52cfe886293..ad113dcc3d264bc77d6343bfeff8812d767bda62 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/DateTick.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/DateTick.java @@ -41,7 +41,6 @@ Portions Copyrighted 2011 Gephi Consortium. */ package org.gephi.desktop.timeline; -import org.gephi.dynamic.DynamicUtilities; import org.joda.time.DateTime; import org.joda.time.DateTimeFieldType; import org.joda.time.DurationFieldType; diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TickGraph.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TickGraph.java index 64423ff6d7ae85656ccab531eeefbb228f08cae7..302850de05afcba2b292b92ef55a3aef023ef040 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TickGraph.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TickGraph.java @@ -46,7 +46,7 @@ import java.awt.FontMetrics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.image.BufferedImage; -import org.gephi.dynamic.api.DynamicModel.TimeFormat; +import org.gephi.graph.api.TimeFormat; import org.gephi.timeline.api.TimelineModel; import org.joda.time.Interval; diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.form b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.form index 5275b67eb7eb2b075a4db9563a2bbe60b65138b3..f14b5147f14bec90b812301e322e14abda05a258 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.form +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.form @@ -20,11 +20,13 @@ - + - + - + + + @@ -38,6 +40,7 @@ + @@ -78,5 +81,15 @@ + + + + + + + + + + diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.java index 9d3dcf05aafe7e09acab73fcabc56ca78e55d425..4e46d5b7e0d6256232db7b9ba1f13af756286499 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimeFormatDialog.java @@ -41,8 +41,8 @@ Portions Copyrighted 2011 Gephi Consortium. */ package org.gephi.desktop.timeline; -import org.gephi.dynamic.api.DynamicController; -import org.gephi.dynamic.api.DynamicModel; +import org.gephi.graph.api.TimeFormat; +import org.gephi.timeline.api.TimelineController; import org.gephi.timeline.api.TimelineModel; import org.openide.util.Lookup; import org.openide.util.NbBundle; @@ -53,7 +53,7 @@ import org.openide.util.NbBundle; */ public class TimeFormatDialog extends javax.swing.JPanel { - private DynamicController dynamicController; + private TimelineController timelineController; /** * Creates new form DateFormatDialog @@ -63,17 +63,30 @@ public class TimeFormatDialog extends javax.swing.JPanel { } public void setup(TimelineModel model) { - this.dynamicController = Lookup.getDefault().lookup(DynamicController.class); - - if (dynamicController.getModel().getTimeFormat().equals(DynamicModel.TimeFormat.DOUBLE)) { - numericRadio.setSelected(true); - } else { - dateRadio.setSelected(true); + this.timelineController = Lookup.getDefault().lookup(TimelineController.class); + + TimeFormat timeFormat = model.getTimeFormat(); + switch(timeFormat) { + case DATE: + dateRadio.setSelected(true); + break; + case DATETIME: + dateTimeRadio.setSelected(true); + break; + case DOUBLE: + numericRadio.setSelected(true); + break; } } public void unsetup() { - dynamicController.setTimeFormat(dateRadio.isSelected() ? DynamicModel.TimeFormat.DATE : DynamicModel.TimeFormat.DOUBLE); + if(dateRadio.isSelected()) { + timelineController.setTimeFormat(TimeFormat.DATE); + } else if(dateTimeRadio.isSelected()) { + timelineController.setTimeFormat(TimeFormat.DATETIME); + } else { + timelineController.setTimeFormat(TimeFormat.DOUBLE); + } } /** @@ -89,6 +102,7 @@ public class TimeFormatDialog extends javax.swing.JPanel { headerTitle = new org.jdesktop.swingx.JXHeader(); dateRadio = new javax.swing.JRadioButton(); numericRadio = new javax.swing.JRadioButton(); + dateTimeRadio = new javax.swing.JRadioButton(); headerTitle.setDescription(NbBundle.getMessage (TimelineTopComponent.class, "TimeFormatDialog.headerTitle.description")); // NOI18N headerTitle.setIcon(new javax.swing.ImageIcon(getClass().getResource("/org/gephi/desktop/timeline/resources/time_format.png"))); // NOI18N @@ -100,17 +114,22 @@ public class TimeFormatDialog extends javax.swing.JPanel { buttonGroup.add(numericRadio); numericRadio.setText(NbBundle.getMessage (TimelineTopComponent.class, "TimeFormatDialog.numericRadio.text")); // NOI18N + buttonGroup.add(dateTimeRadio); + dateTimeRadio.setText(org.openide.util.NbBundle.getMessage(TimeFormatDialog.class, "TimeFormatDialog.dateTimeRadio.text")); // NOI18N + javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this); this.setLayout(layout); layout.setHorizontalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(headerTitle, javax.swing.GroupLayout.DEFAULT_SIZE, 400, Short.MAX_VALUE) + .addComponent(headerTitle, javax.swing.GroupLayout.DEFAULT_SIZE, 422, Short.MAX_VALUE) .addGroup(layout.createSequentialGroup() - .addGap(126, 126, 126) + .addGap(23, 23, 23) .addComponent(numericRadio) - .addGap(18, 18, 18) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(dateTimeRadio) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) .addComponent(dateRadio) - .addContainerGap()) + .addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) ); layout.setVerticalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) @@ -119,13 +138,15 @@ public class TimeFormatDialog extends javax.swing.JPanel { .addGap(18, 18, 18) .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) .addComponent(numericRadio) - .addComponent(dateRadio)) + .addComponent(dateRadio) + .addComponent(dateTimeRadio)) .addGap(0, 22, Short.MAX_VALUE)) ); }// //GEN-END:initComponents // Variables declaration - do not modify//GEN-BEGIN:variables private javax.swing.ButtonGroup buttonGroup; private javax.swing.JRadioButton dateRadio; + private javax.swing.JRadioButton dateTimeRadio; private org.jdesktop.swingx.JXHeader headerTitle; private javax.swing.JRadioButton numericRadio; // End of variables declaration//GEN-END:variables diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.form b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.form index c63592c05f84d5984ff8083ae1b79c74d5a7c5ff..919063bb616314e86359d28dfa305152dee28d44 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.form +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.form @@ -1,4 +1,4 @@ - +
diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.java index b858e6d148ab7c11fafdcb5dc3d5b317e1f2fdaa..49027a78b3be51f568e90c29b5f38415e84b4d5b 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineDrawer.java @@ -595,6 +595,7 @@ public class TimelineDrawer extends JPanel implements MouseListener, MouseMotion to = Math.min(to, model.getCustomMax()); if (from < to) { controller.setInterval(from, to); + repaint(); } } } diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTooltip.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTooltip.java index 1e952a752e2f7deda7b511472386950f84dd942d..be21956ae7b23b71f9f3a72ba583e87321e6eb3d 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTooltip.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTooltip.java @@ -49,7 +49,6 @@ import java.util.TimerTask; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock; import javax.swing.JComponent; -import org.gephi.dynamic.api.DynamicModel.TimeFormat; import org.gephi.timeline.api.TimelineChart; import org.gephi.timeline.api.TimelineModel; import org.gephi.ui.components.richtooltip.RichTooltip; @@ -121,40 +120,43 @@ public class TimelineTooltip { } private void buildData(double currentPosition) { - if (model.getTimeFormat().equals(TimeFormat.DOUBLE)) { - int exponentMin = (int) Math.round(Math.log10(model.getCustomMin())); - - DecimalFormat decimalFormat = new DecimalFormat(); - decimalFormat.setRoundingMode(RoundingMode.HALF_EVEN); - - if (exponentMin > 0) { - min = String.valueOf(model.getCustomMin()); - max = String.valueOf(model.getCustomMax()); - position = String.valueOf(currentPosition); - } else { - decimalFormat.setMaximumFractionDigits(Math.abs(exponentMin) + 2); - min = decimalFormat.format(model.getCustomMin()); - max = decimalFormat.format(model.getCustomMax()); - position = decimalFormat.format(currentPosition); - } - } else if (model.getTimeFormat().equals(TimeFormat.DATE)) { - DateTime minDate = new DateTime((long) model.getCustomMin()); - DateTime maxDate = new DateTime((long) model.getCustomMax()); - DateTime posDate = new DateTime((long) currentPosition); - - DateTimeFormatter formatter = ISODateTimeFormat.date(); - min = formatter.print(minDate); - max = formatter.print(maxDate); - position = formatter.print(posDate); - } else { - DateTime minDate = new DateTime((long) model.getCustomMin()); - DateTime maxDate = new DateTime((long) model.getCustomMax()); - DateTime posDate = new DateTime((long) currentPosition); - - DateTimeFormatter formatter = ISODateTimeFormat.dateTime(); - min = formatter.print(minDate); - max = formatter.print(maxDate); - position = formatter.print(posDate); + switch (model.getTimeFormat()) { + case DOUBLE: + int exponentMin = (int) Math.round(Math.log10(model.getCustomMin())); + DecimalFormat decimalFormat = new DecimalFormat(); + decimalFormat.setRoundingMode(RoundingMode.HALF_EVEN); + if (exponentMin > 0) { + min = String.valueOf(model.getCustomMin()); + max = String.valueOf(model.getCustomMax()); + position = String.valueOf(currentPosition); + } else { + decimalFormat.setMaximumFractionDigits(Math.abs(exponentMin) + 2); + min = decimalFormat.format(model.getCustomMin()); + max = decimalFormat.format(model.getCustomMax()); + position = decimalFormat.format(currentPosition); + } break; + case DATE: + { + DateTime minDate = new DateTime((long) model.getCustomMin()); + DateTime maxDate = new DateTime((long) model.getCustomMax()); + DateTime posDate = new DateTime((long) currentPosition); + DateTimeFormatter formatter = ISODateTimeFormat.date(); + min = formatter.print(minDate); + max = formatter.print(maxDate); + position = formatter.print(posDate); + break; + } + default: + { + DateTime minDate = new DateTime((long) model.getCustomMin()); + DateTime maxDate = new DateTime((long) model.getCustomMax()); + DateTime posDate = new DateTime((long) currentPosition); + DateTimeFormatter formatter = ISODateTimeFormat.dateTime(); + min = formatter.print(minDate); + max = formatter.print(maxDate); + position = formatter.print(posDate); + break; + } } if (model.getChart() != null) { @@ -183,7 +185,7 @@ public class TimelineTooltip { //Chart if (getY() != null) { - richTooltip.addFooterSection(model.getChart().getColumn().getTitle()); + richTooltip.addFooterSection(model.getChart().getColumn()); richTooltip.addFooterSection(NbBundle.getMessage(TimelineTooltip.class, "TimelineTooltip.chart") + ": " + getY()); //Img diff --git a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTopComponent.java b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTopComponent.java index a964966452ab93e008ea7f8066eb9f73f04cc683..f329a1f75e360918d1a734235b8c0ef9203c8da9 100644 --- a/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTopComponent.java +++ b/modules/DesktopTimeline/src/main/java/org/gephi/desktop/timeline/TimelineTopComponent.java @@ -48,13 +48,14 @@ import java.awt.event.ActionListener; import javax.swing.*; import javax.swing.event.ChangeEvent; import javax.swing.event.ChangeListener; -import org.gephi.data.attributes.api.AttributeColumn; +import org.gephi.graph.api.Column; import org.gephi.timeline.api.TimelineController; import org.gephi.timeline.api.TimelineModel; import org.gephi.timeline.api.TimelineModelEvent; import org.gephi.timeline.api.TimelineModelListener; import org.gephi.ui.components.CloseButton; import org.gephi.ui.utils.UIUtils; +import org.gephi.visualization.VizController; import org.netbeans.validation.api.ui.ValidationPanel; import org.openide.DialogDescriptor; import org.openide.DialogDisplayer; @@ -132,7 +133,6 @@ public final class TimelineTopComponent extends JPanel implements TimelineModelL } }); - columnsButton.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { @@ -140,14 +140,14 @@ public final class TimelineTopComponent extends JPanel implements TimelineModelL JPopupMenu menu = new JPopupMenu(); //Add columns - AttributeColumn selectedColumn = model.getChart() != null ? model.getChart().getColumn() : null; + String selectedColumn = model.getChart() != null ? model.getChart().getColumn() : null; //Dynamic columns - AttributeColumn[] columns = controller.getDynamicGraphColumns(); + String[] columns = controller.getDynamicGraphColumns(); - for (final AttributeColumn col : columns) { - boolean selected = col == selectedColumn; - JRadioButtonMenuItem item = new JRadioButtonMenuItem(col.getTitle(), selected); + for (final String col : columns) { + boolean selected = (col == null ? selectedColumn == null : col.equals(selectedColumn)); + JRadioButtonMenuItem item = new JRadioButtonMenuItem(col, selected); item.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { @@ -176,7 +176,7 @@ public final class TimelineTopComponent extends JPanel implements TimelineModelL }); menu.add(disableItem); - if(selectedColumn == null) { + if (selectedColumn == null) { disableItem.setEnabled(false); } } @@ -255,7 +255,6 @@ public final class TimelineTopComponent extends JPanel implements TimelineModelL }); menu.add(dateFormatItem); - menu.show(settingsButton, 0, -menu.getPreferredSize().height); } }); @@ -339,10 +338,11 @@ public final class TimelineTopComponent extends JPanel implements TimelineModelL public void setTimeLineVisible(final boolean visible) { SwingUtilities.invokeLater(new Runnable() { - public void run() { if (visible != TimelineTopComponent.this.isVisible()) { + TimelineTopComponent.this.setVisible(visible); + VizController.getInstance().getDrawable().reinitWindow(); } } }); diff --git a/modules/DesktopTimeline/src/main/resources/org/gephi/desktop/timeline/Bundle.properties b/modules/DesktopTimeline/src/main/resources/org/gephi/desktop/timeline/Bundle.properties index 86b48164efd5ffa238cf2b62e9973c29c421a314..345c77fcfe329bce0e5898d1eca92cba87311cb5 100644 --- a/modules/DesktopTimeline/src/main/resources/org/gephi/desktop/timeline/Bundle.properties +++ b/modules/DesktopTimeline/src/main/resources/org/gephi/desktop/timeline/Bundle.properties @@ -53,3 +53,4 @@ TimeFormatDialog.headerTitle.title=Time format settings TimeFormatDialog.headerTitle.description=Set up the time format TimeFormatDialog.numericRadio.text=Numeric TimeFormatDialog.dateRadio.text=Date +TimeFormatDialog.dateTimeRadio.text=Datetime diff --git a/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeBuilder.java b/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeBuilder.java index eb8c2a7618fee4df412bf05e77922f197e7a4c85..206c9ec0bf0c9a794455ef0adc5177bce597fe58 100644 --- a/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeBuilder.java +++ b/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeBuilder.java @@ -1,258 +1,239 @@ -///* -//Copyright 2008-2010 Gephi -//Authors : Mathieu Bastian -//Website : http://www.gephi.org -// -//This file is part of Gephi. -// -//DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. -// -//Copyright 2011 Gephi Consortium. All rights reserved. -// -//The contents of this file are subject to the terms of either the GNU -//General Public License Version 3 only ("GPL") or the Common -//Development and Distribution License("CDDL") (collectively, the -//"License"). You may not use this file except in compliance with the -//License. You can obtain a copy of the License at -//http://gephi.org/about/legal/license-notice/ -//or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the -//specific language governing permissions and limitations under the -//License. When distributing the software, include this License Header -//Notice in each file and include the License files at -///cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the -//License Header, with the fields enclosed by brackets [] replaced by -//your own identifying information: -//"Portions Copyrighted [year] [name of copyright owner]" -// -//If you wish your version of this file to be governed by only the CDDL -//or only the GPL Version 3, indicate your decision by adding -//"[Contributor] elects to include this software in this distribution -//under the [CDDL or GPL Version 3] license." If you do not indicate a -//single choice of license, a recipient has the option to distribute -//your version of this file under either the CDDL, the GPL Version 3 or -//to extend the choice of license to its licensees as provided above. -//However, if you add GPL Version 3 code and therefore, elected the GPL -//Version 3 license, then the option applies only if the new code is -//made subject to such option by the copyright holder. -// -//Contributor(s): -// -//Portions Copyrighted 2011 Gephi Consortium. -// */ -//package org.gephi.filters.plugin.dynamic; -// -//import java.util.ArrayList; -//import java.util.List; -//import javax.swing.Icon; -//import javax.swing.JPanel; -//import org.gephi.filters.api.Range; -//import org.gephi.filters.spi.Category; -//import org.gephi.filters.spi.CategoryBuilder; -//import org.gephi.filters.spi.EdgeFilter; -//import org.gephi.filters.spi.Filter; -//import org.gephi.filters.spi.FilterBuilder; -//import org.gephi.filters.spi.FilterProperty; -//import org.gephi.filters.spi.NodeFilter; -//import org.gephi.graph.api.Edge; -//import org.gephi.graph.api.Graph; -//import org.gephi.graph.api.Node; -//import org.openide.util.Lookup; -//import org.openide.util.NbBundle; -//import org.openide.util.lookup.ServiceProvider; -// -///** -// * -// * @author Mathieu Bastian -// */ -//@ServiceProvider(service = CategoryBuilder.class) -//public class DynamicRangeBuilder implements CategoryBuilder { -// -// private final static Category DYNAMIC = new Category( -// NbBundle.getMessage(DynamicRangeBuilder.class, "DynamicRangeBuilder.category"), -// null, -// null); -// -// @Override -// public Category getCategory() { -// return DYNAMIC; -// } -// -// @Override -// public FilterBuilder[] getBuilders() { -// List builders = new ArrayList(); -// AttributeModel am = Lookup.getDefault().lookup(AttributeController.class).getModel(); -// AttributeColumn nodeColumn = am.getNodeTable().getColumn(DynamicModel.TIMEINTERVAL_COLUMN); -// AttributeColumn edgeColumn = am.getEdgeTable().getColumn(DynamicModel.TIMEINTERVAL_COLUMN); -// if (nodeColumn != null || edgeColumn != null) { -// builders.add(new DynamicRangeFilterBuilder(nodeColumn, edgeColumn)); -// } -// return builders.toArray(new FilterBuilder[0]); -// } -// -// private static class DynamicRangeFilterBuilder implements FilterBuilder { -// -// private final AttributeColumn nodeColumn; -// private final AttributeColumn edgeColumn; -// -// public DynamicRangeFilterBuilder(AttributeColumn nodeColumn, AttributeColumn edgeColumn) { -// this.nodeColumn = nodeColumn; -// this.edgeColumn = edgeColumn; -// } -// -// @Override -// public Category getCategory() { -// return DYNAMIC; -// } -// -// @Override -// public String getName() { -// return "Time Interval"; -// } -// -// @Override -// public Icon getIcon() { -// return null; -// } -// -// @Override -// public String getDescription() { -// return null; -// } -// -// @Override -// public DynamicRangeFilter getFilter() { -// TimelineController timelineController = Lookup.getDefault().lookup(TimelineController.class); -// DynamicController dynamicController = Lookup.getDefault().lookup(DynamicController.class); -// return new DynamicRangeFilter(timelineController, dynamicController, nodeColumn, edgeColumn); -// } -// -// @Override -// public JPanel getPanel(Filter filter) { -// final DynamicRangeFilter dynamicRangeFilter = (DynamicRangeFilter) filter; -// DynamicRangeUI ui = Lookup.getDefault().lookup(DynamicRangeUI.class); -// if (ui != null) { -// return ui.getPanel(dynamicRangeFilter); -// } -// return null; -// } -// -// @Override -// public void destroy(Filter filter) { -// ((DynamicRangeFilter) filter).destroy(); -// } -// } -// -// public static class DynamicRangeFilter implements NodeFilter, EdgeFilter, DynamicModelListener { -// -// private AttributeColumn nodeColumn; -// private AttributeColumn edgeColumn; -// private DynamicController dynamicController; -// private DynamicModel dynamicModel; -// private TimelineController timelineController; -// private TimeInterval visibleInterval; -// private FilterProperty[] filterProperties; -// private Range range; -// private boolean keepNull = true; -// -// public DynamicRangeFilter(TimelineController timelineController, DynamicController dynamicController, AttributeColumn nodeColumn, AttributeColumn edgeColumn) { -// this.nodeColumn = nodeColumn; -// this.edgeColumn = edgeColumn; -// this.dynamicController = dynamicController; -// this.dynamicModel = dynamicController.getModel(); -// this.timelineController = timelineController; -// } -// -// @Override -// public boolean init(Graph graph) { -// dynamicController.addModelListener(this); -// visibleInterval = dynamicModel.getVisibleInterval(); -// return true; -// } -// -// @Override -// public boolean evaluate(Graph graph, Node node) { -// if (nodeColumn != null) { -// Object obj = node.getNodeData().getAttributes().getValue(nodeColumn.getIndex()); -// if (obj != null) { -// TimeInterval timeInterval = (TimeInterval) obj; -// return timeInterval.isInRange(visibleInterval.getLow(), visibleInterval.getHigh()); -// } -// return keepNull; -// } -// return true; -// } -// -// @Override -// public boolean evaluate(Graph graph, Edge edge) { -// if (edgeColumn != null) { -// Object obj = edge.getEdgeData().getAttributes().getValue(edgeColumn.getIndex()); -// if (obj != null) { -// TimeInterval timeInterval = (TimeInterval) obj; -// return timeInterval.isInRange(visibleInterval.getLow(), visibleInterval.getHigh()); -// } -// return keepNull; -// } -// return true; -// } -// -// @Override -// public void finish() { -// } -// -// @Override -// public String getName() { -// return NbBundle.getMessage(DynamicRangeBuilder.class, "DynamicRangeBuilder.name"); -// } -// -// @Override -// public FilterProperty[] getProperties() { -// if (filterProperties == null) { -// filterProperties = new FilterProperty[0]; -// try { -// filterProperties = new FilterProperty[]{ -// FilterProperty.createProperty(this, Range.class, "range"), -// FilterProperty.createProperty(this, Boolean.class, "keepNull")}; -// } catch (Exception ex) { -// ex.printStackTrace(); -// } -// } -// return filterProperties; -// } -// -// public void dynamicModelChanged(DynamicModelEvent event) { -// switch (event.getEventType()) { -// case VISIBLE_INTERVAL: -// TimeInterval interval = (TimeInterval) event.getData(); -// getProperties()[0].setValue(new Range(interval.getLow(), interval.getHigh())); -// break; -// } -// } -// -// public FilterProperty getRangeProperty() { -// return getProperties()[0]; -// } -// -// public boolean isKeepNull() { -// return keepNull; -// } -// -// public void setKeepNull(boolean keepNull) { -// this.keepNull = keepNull; -// } -// -// public Range getRange() { -// if (visibleInterval != null) { -// return new Range(visibleInterval.getLow(), visibleInterval.getHigh()); -// } -// return null; -// } -// -// public void setRange(Range range) { -// dynamicController.setVisibleInterval(range.getLowerDouble(), range.getUpperDouble()); -// } -// -// public void destroy() { -// dynamicController.removeModelListener(this); -// } -// } -//} +/* +Copyright 2008-2010 Gephi +Authors : Mathieu Bastian +Website : http://www.gephi.org + +This file is part of Gephi. + +DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + +Copyright 2011 Gephi Consortium. All rights reserved. + +The contents of this file are subject to the terms of either the GNU +General Public License Version 3 only ("GPL") or the Common +Development and Distribution License("CDDL") (collectively, the +"License"). You may not use this file except in compliance with the +License. You can obtain a copy of the License at +http://gephi.org/about/legal/license-notice/ +or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the +specific language governing permissions and limitations under the +License. When distributing the software, include this License Header +Notice in each file and include the License files at +/cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the +License Header, with the fields enclosed by brackets [] replaced by +your own identifying information: +"Portions Copyrighted [year] [name of copyright owner]" + +If you wish your version of this file to be governed by only the CDDL +or only the GPL Version 3, indicate your decision by adding +"[Contributor] elects to include this software in this distribution +under the [CDDL or GPL Version 3] license." If you do not indicate a +single choice of license, a recipient has the option to distribute +your version of this file under either the CDDL, the GPL Version 3 or +to extend the choice of license to its licensees as provided above. +However, if you add GPL Version 3 code and therefore, elected the GPL +Version 3 license, then the option applies only if the new code is +made subject to such option by the copyright holder. + +Contributor(s): + +Portions Copyrighted 2011 Gephi Consortium. + */ +package org.gephi.filters.plugin.dynamic; + +import java.util.ArrayList; +import java.util.List; +import javax.swing.Icon; +import javax.swing.JPanel; +import org.gephi.filters.api.Range; +import org.gephi.filters.spi.Category; +import org.gephi.filters.spi.CategoryBuilder; +import org.gephi.filters.spi.ComplexFilter; +import org.gephi.filters.spi.Filter; +import org.gephi.filters.spi.FilterBuilder; +import org.gephi.filters.spi.FilterProperty; +import org.gephi.graph.api.Edge; +import org.gephi.graph.api.Element; +import org.gephi.graph.api.Graph; +import org.gephi.graph.api.GraphController; +import org.gephi.graph.api.GraphModel; +import org.gephi.graph.api.Interval; +import org.gephi.graph.api.Node; +import org.gephi.graph.api.TimeRepresentation; +import org.openide.util.Lookup; +import org.openide.util.NbBundle; +import org.openide.util.lookup.ServiceProvider; + +/** + * + * @author Mathieu Bastian + */ +@ServiceProvider(service = CategoryBuilder.class) +public class DynamicRangeBuilder implements CategoryBuilder { + + private final static Category DYNAMIC = new Category( + NbBundle.getMessage(DynamicRangeBuilder.class, "DynamicRangeBuilder.category"), + null, + null); + + @Override + public Category getCategory() { + return DYNAMIC; + } + + @Override + public FilterBuilder[] getBuilders() { + List builders = new ArrayList(); + GraphModel am = Lookup.getDefault().lookup(GraphController.class).getGraphModel(); + if (am.isDynamic()) { + builders.add(new DynamicRangeFilterBuilder(am)); + } + return builders.toArray(new FilterBuilder[0]); + } + + private static class DynamicRangeFilterBuilder implements FilterBuilder { + + private GraphModel graphModel; + + public DynamicRangeFilterBuilder(GraphModel graphModel) { + this.graphModel = graphModel; + } + + @Override + public Category getCategory() { + return DYNAMIC; + } + + @Override + public String getName() { + return "Time Interval"; + } + + @Override + public Icon getIcon() { + return null; + } + + @Override + public String getDescription() { + return null; + } + + @Override + public DynamicRangeFilter getFilter() { + return new DynamicRangeFilter(graphModel); + } + + @Override + public JPanel getPanel(Filter filter) { + final DynamicRangeFilter dynamicRangeFilter = (DynamicRangeFilter) filter; + DynamicRangeUI ui = Lookup.getDefault().lookup(DynamicRangeUI.class); + if (ui != null) { + return ui.getPanel(dynamicRangeFilter); + } + return null; + } + + @Override + public void destroy(Filter filter) { + } + } + + public static class DynamicRangeFilter implements ComplexFilter { + + private TimeRepresentation timeRepresentation; + private FilterProperty[] filterProperties; + private Interval visibleInterval; + private Range range = new Range(Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY); + private boolean keepNull = true; + + public DynamicRangeFilter(GraphModel graphModel) { + this.timeRepresentation = graphModel.getConfiguration().getTimeRepresentation(); + } + + @Override + public Graph filter(Graph graph) { + visibleInterval = new Interval(range.getLowerDouble(), range.getUpperDouble()); + + List toRemoveNodes = new ArrayList(); + for (Node n : graph.getNodes()) { + if (!evaluateElement(n)) { + toRemoveNodes.add(n); + } + } + graph.removeAllNodes(toRemoveNodes); + + List toRemoveEdge = new ArrayList(); + for (Edge e : graph.getEdges()) { + if (!evaluateElement(e)) { + toRemoveEdge.add(e); + } + } + graph.removeAllEdges(toRemoveEdge); + + graph.getModel().setTimeInterval(graph.getView(), visibleInterval); + + return graph; + } + + private boolean evaluateElement(Element element) { + if (timeRepresentation.equals(TimeRepresentation.INTERVAL)) { + for (Interval i : element.getIntervals()) { + if (visibleInterval.compareTo(i) == 0) { + return true; + } + } + } else { + for (double t : element.getTimestamps()) { + if (visibleInterval.compareTo(t) == 0) { + return true; + } + } + } + return false; + } + + @Override + public String getName() { + return NbBundle.getMessage(DynamicRangeBuilder.class, "DynamicRangeBuilder.name"); + } + + @Override + public FilterProperty[] getProperties() { + if (filterProperties == null) { + filterProperties = new FilterProperty[0]; + try { + filterProperties = new FilterProperty[]{ + FilterProperty.createProperty(this, Range.class, "range"), + FilterProperty.createProperty(this, Boolean.class, "keepNull")}; + } catch (Exception ex) { + ex.printStackTrace(); + } + } + return filterProperties; + } + + public FilterProperty getRangeProperty() { + return getProperties()[0]; + } + + public boolean isKeepNull() { + return keepNull; + } + + public void setKeepNull(boolean keepNull) { + this.keepNull = keepNull; + } + + public Range getRange() { + return range; + } + + public void setRange(Range range) { + this.range = range; + } + + public void destroy() { + } + } +} diff --git a/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeUI.java b/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeUI.java index 59a4e54eb2931da8cef5a2dc18ca814f43e76c18..bea54ff142db7beb766a023984f4d6610a996492 100644 --- a/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeUI.java +++ b/modules/FiltersPlugin/src/main/java/org/gephi/filters/plugin/dynamic/DynamicRangeUI.java @@ -1,54 +1,54 @@ -///* -//Copyright 2008-2010 Gephi -//Authors : Mathieu Bastian -//Website : http://www.gephi.org -// -//This file is part of Gephi. -// -//DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. -// -//Copyright 2011 Gephi Consortium. All rights reserved. -// -//The contents of this file are subject to the terms of either the GNU -//General Public License Version 3 only ("GPL") or the Common -//Development and Distribution License("CDDL") (collectively, the -//"License"). You may not use this file except in compliance with the -//License. You can obtain a copy of the License at -//http://gephi.org/about/legal/license-notice/ -//or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the -//specific language governing permissions and limitations under the -//License. When distributing the software, include this License Header -//Notice in each file and include the License files at -///cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the -//License Header, with the fields enclosed by brackets [] replaced by -//your own identifying information: -//"Portions Copyrighted [year] [name of copyright owner]" -// -//If you wish your version of this file to be governed by only the CDDL -//or only the GPL Version 3, indicate your decision by adding -//"[Contributor] elects to include this software in this distribution -//under the [CDDL or GPL Version 3] license." If you do not indicate a -//single choice of license, a recipient has the option to distribute -//your version of this file under either the CDDL, the GPL Version 3 or -//to extend the choice of license to its licensees as provided above. -//However, if you add GPL Version 3 code and therefore, elected the GPL -//Version 3 license, then the option applies only if the new code is -//made subject to such option by the copyright holder. -// -//Contributor(s): -// -//Portions Copyrighted 2011 Gephi Consortium. -//*/ -//package org.gephi.filters.plugin.dynamic; -// -//import javax.swing.JPanel; -//import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; -// -///** -// * -// * @author mbastian -// */ -//public interface DynamicRangeUI { -// -// public JPanel getPanel(DynamicRangeFilter filter); -//} +/* +Copyright 2008-2010 Gephi +Authors : Mathieu Bastian +Website : http://www.gephi.org + +This file is part of Gephi. + +DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + +Copyright 2011 Gephi Consortium. All rights reserved. + +The contents of this file are subject to the terms of either the GNU +General Public License Version 3 only ("GPL") or the Common +Development and Distribution License("CDDL") (collectively, the +"License"). You may not use this file except in compliance with the +License. You can obtain a copy of the License at +http://gephi.org/about/legal/license-notice/ +or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the +specific language governing permissions and limitations under the +License. When distributing the software, include this License Header +Notice in each file and include the License files at +/cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the +License Header, with the fields enclosed by brackets [] replaced by +your own identifying information: +"Portions Copyrighted [year] [name of copyright owner]" + +If you wish your version of this file to be governed by only the CDDL +or only the GPL Version 3, indicate your decision by adding +"[Contributor] elects to include this software in this distribution +under the [CDDL or GPL Version 3] license." If you do not indicate a +single choice of license, a recipient has the option to distribute +your version of this file under either the CDDL, the GPL Version 3 or +to extend the choice of license to its licensees as provided above. +However, if you add GPL Version 3 code and therefore, elected the GPL +Version 3 license, then the option applies only if the new code is +made subject to such option by the copyright holder. + +Contributor(s): + +Portions Copyrighted 2011 Gephi Consortium. +*/ +package org.gephi.filters.plugin.dynamic; + +import javax.swing.JPanel; +import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; + +/** + * + * @author mbastian + */ +public interface DynamicRangeUI { + + public JPanel getPanel(DynamicRangeFilter filter); +} diff --git a/modules/FiltersPluginUI/pom.xml b/modules/FiltersPluginUI/pom.xml index a19003096798bdaa9262e4a63f33a205db346aaf..5599e4789eea17d675ae1eec12ad9ea30d97d4f4 100644 --- a/modules/FiltersPluginUI/pom.xml +++ b/modules/FiltersPluginUI/pom.xml @@ -60,10 +60,10 @@ org.netbeans.api org-openide-windows - + desktop-banner + org.netbeans.api org-openide-filesystems diff --git a/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangePanel.java b/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangePanel.java index 013c4c3109a9aea44f8ad10effce212f1b59b3f2..0cbfa84a678d6e907c450dfe46ec00fdc59f6141 100644 --- a/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangePanel.java +++ b/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangePanel.java @@ -45,12 +45,12 @@ import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.awt.event.ItemEvent; import java.awt.event.ItemListener; +import org.gephi.desktop.banner.perspective.spi.BottomComponent; +import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; //import org.gephi.desktop.perspective.spi.BottomComponent; //import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; import org.openide.util.Lookup; import org.openide.util.NbBundle; -import org.openide.windows.TopComponent; -import org.openide.windows.WindowManager; /** * @@ -67,37 +67,37 @@ public class DynamicRangePanel extends javax.swing.JPanel { CLOSE = NbBundle.getMessage(DynamicRangePanel.class, "DynamicRangePanel.timelineButton.closetext"); } -// public void setup(final DynamicRangeFilter filter) { -// final BottomComponent bottomComponent = Lookup.getDefault().lookup(BottomComponent.class); -// timelineButton.setText(bottomComponent.isVisible() ? CLOSE : OPEN); -// timelineButton.addActionListener(new ActionListener() { -// -// public void actionPerformed(ActionEvent e) { -// -// if (!bottomComponent.isVisible()) { -// bottomComponent.setVisible(true); -// timelineButton.setText(CLOSE); -// } else { -// bottomComponent.setVisible(false); -// timelineButton.setText(OPEN); -// } -// } -// }); -// keepEmptyCheckbox.setSelected(filter.isKeepNull()); -// keepEmptyCheckbox.addItemListener(new ItemListener() { -// -// public void itemStateChanged(ItemEvent e) { -// if (!filter.isKeepNull() == keepEmptyCheckbox.isSelected()) { -// filter.getProperties()[1].setValue(keepEmptyCheckbox.isSelected()); -// } -// } -// }); -// } - - /** This method is called from within the constructor to - * initialize the form. - * WARNING: Do NOT modify this code. The content of this method is - * always regenerated by the Form Editor. + public void setup(final DynamicRangeFilter filter) { + final BottomComponent bottomComponent = Lookup.getDefault().lookup(BottomComponent.class); + timelineButton.setText(bottomComponent.isVisible() ? CLOSE : OPEN); + timelineButton.addActionListener(new ActionListener() { + + public void actionPerformed(ActionEvent e) { + + if (!bottomComponent.isVisible()) { + bottomComponent.setVisible(true); + timelineButton.setText(CLOSE); + } else { + bottomComponent.setVisible(false); + timelineButton.setText(OPEN); + } + } + }); + keepEmptyCheckbox.setSelected(filter.isKeepNull()); + keepEmptyCheckbox.addItemListener(new ItemListener() { + + public void itemStateChanged(ItemEvent e) { + if (!filter.isKeepNull() == keepEmptyCheckbox.isSelected()) { + filter.getProperties()[1].setValue(keepEmptyCheckbox.isSelected()); + } + } + }); + } + + /** + * This method is called from within the constructor to initialize the form. + * WARNING: Do NOT modify this code. The content of this method is always + * regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // //GEN-BEGIN:initComponents diff --git a/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangeUIImpl.java b/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangeUIImpl.java index c61d7bd57c149e1dd8d7cd974e4ba77210518534..5807f9f63ef4b571b393c707bf82a4d404bab7f2 100644 --- a/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangeUIImpl.java +++ b/modules/FiltersPluginUI/src/main/java/org/gephi/ui/filters/plugin/dynamic/DynamicRangeUIImpl.java @@ -1,61 +1,61 @@ -///* -//Copyright 2008-2010 Gephi -//Authors : Mathieu Bastian -//Website : http://www.gephi.org -// -//This file is part of Gephi. -// -//DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. -// -//Copyright 2011 Gephi Consortium. All rights reserved. -// -//The contents of this file are subject to the terms of either the GNU -//General Public License Version 3 only ("GPL") or the Common -//Development and Distribution License("CDDL") (collectively, the -//"License"). You may not use this file except in compliance with the -//License. You can obtain a copy of the License at -//http://gephi.org/about/legal/license-notice/ -//or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the -//specific language governing permissions and limitations under the -//License. When distributing the software, include this License Header -//Notice in each file and include the License files at -///cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the -//License Header, with the fields enclosed by brackets [] replaced by -//your own identifying information: -//"Portions Copyrighted [year] [name of copyright owner]" -// -//If you wish your version of this file to be governed by only the CDDL -//or only the GPL Version 3, indicate your decision by adding -//"[Contributor] elects to include this software in this distribution -//under the [CDDL or GPL Version 3] license." If you do not indicate a -//single choice of license, a recipient has the option to distribute -//your version of this file under either the CDDL, the GPL Version 3 or -//to extend the choice of license to its licensees as provided above. -//However, if you add GPL Version 3 code and therefore, elected the GPL -//Version 3 license, then the option applies only if the new code is -//made subject to such option by the copyright holder. -// -//Contributor(s): -// -//Portions Copyrighted 2011 Gephi Consortium. -// */ -//package org.gephi.ui.filters.plugin.dynamic; -// -//import javax.swing.JPanel; -//import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; -//import org.gephi.filters.plugin.dynamic.DynamicRangeUI; -//import org.openide.util.lookup.ServiceProvider; -// -///** -// * -// * @author mbastian -// */ -//@ServiceProvider(service = DynamicRangeUI.class) -//public class DynamicRangeUIImpl implements DynamicRangeUI { -// -// public JPanel getPanel(DynamicRangeFilter filter) { -// DynamicRangePanel panel = new DynamicRangePanel(); -// panel.setup(filter); -// return panel; -// } -//} +/* +Copyright 2008-2010 Gephi +Authors : Mathieu Bastian +Website : http://www.gephi.org + +This file is part of Gephi. + +DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. + +Copyright 2011 Gephi Consortium. All rights reserved. + +The contents of this file are subject to the terms of either the GNU +General Public License Version 3 only ("GPL") or the Common +Development and Distribution License("CDDL") (collectively, the +"License"). You may not use this file except in compliance with the +License. You can obtain a copy of the License at +http://gephi.org/about/legal/license-notice/ +or /cddl-1.0.txt and /gpl-3.0.txt. See the License for the +specific language governing permissions and limitations under the +License. When distributing the software, include this License Header +Notice in each file and include the License files at +/cddl-1.0.txt and /gpl-3.0.txt. If applicable, add the following below the +License Header, with the fields enclosed by brackets [] replaced by +your own identifying information: +"Portions Copyrighted [year] [name of copyright owner]" + +If you wish your version of this file to be governed by only the CDDL +or only the GPL Version 3, indicate your decision by adding +"[Contributor] elects to include this software in this distribution +under the [CDDL or GPL Version 3] license." If you do not indicate a +single choice of license, a recipient has the option to distribute +your version of this file under either the CDDL, the GPL Version 3 or +to extend the choice of license to its licensees as provided above. +However, if you add GPL Version 3 code and therefore, elected the GPL +Version 3 license, then the option applies only if the new code is +made subject to such option by the copyright holder. + +Contributor(s): + +Portions Copyrighted 2011 Gephi Consortium. + */ +package org.gephi.ui.filters.plugin.dynamic; + +import javax.swing.JPanel; +import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; +import org.gephi.filters.plugin.dynamic.DynamicRangeUI; +import org.openide.util.lookup.ServiceProvider; + +/** + * + * @author mbastian + */ +@ServiceProvider(service = DynamicRangeUI.class) +public class DynamicRangeUIImpl implements DynamicRangeUI { + + public JPanel getPanel(DynamicRangeFilter filter) { + DynamicRangePanel panel = new DynamicRangePanel(); + panel.setup(filter); + return panel; + } +} diff --git a/modules/GeneratorPlugin/pom.xml b/modules/GeneratorPlugin/pom.xml index 27ee6a7e9824328c0bd577140f876f30cbcc88f7..1351cba9b3992b36aff2ad222f7e60fab6e64476 100644 --- a/modules/GeneratorPlugin/pom.xml +++ b/modules/GeneratorPlugin/pom.xml @@ -20,6 +20,10 @@ ${project.groupId} io-generator-api + + ${project.groupId} + graph-api + ${project.groupId} io-importer-api diff --git a/modules/GeneratorPlugin/src/main/java/org/gephi/io/generator/plugin/DynamicGraph.java b/modules/GeneratorPlugin/src/main/java/org/gephi/io/generator/plugin/DynamicGraph.java index f28c1f2e1b1bdb13ffd3d9b5a4b410ec6479e2e7..ba138e4fcbafc651aa922d57505cf93c47f4471c 100644 --- a/modules/GeneratorPlugin/src/main/java/org/gephi/io/generator/plugin/DynamicGraph.java +++ b/modules/GeneratorPlugin/src/main/java/org/gephi/io/generator/plugin/DynamicGraph.java @@ -42,6 +42,7 @@ package org.gephi.io.generator.plugin; import java.util.Random; +import org.gephi.graph.api.TimeRepresentation; import org.gephi.io.generator.spi.Generator; import org.gephi.io.generator.spi.GeneratorUI; import org.gephi.io.importer.api.ColumnDraft; @@ -69,6 +70,7 @@ public class DynamicGraph implements Generator { double end = 2015.0; double tick = 1.0; ColumnDraft col = container.addNodeColumn("score", Integer.class, true); + container.setTimeRepresentation(TimeRepresentation.TIMESTAMP); NodeDraft[] nodeArray = new NodeDraft[numberOfNodes]; for (int i = 0; i < numberOfNodes; i++) { diff --git a/modules/TimelineAPI/pom.xml b/modules/TimelineAPI/pom.xml index 551a0d6b4ac14f54f1046d7624b1b85b8e8d7ae2..c185138874c1d9827883d36972a2f55b89704494 100644 --- a/modules/TimelineAPI/pom.xml +++ b/modules/TimelineAPI/pom.xml @@ -5,11 +5,11 @@ gephi-parent org.gephi 0.9-SNAPSHOT - ../.. + ../.. org.gephi - timeline + timeline-api 0.9-SNAPSHOT nbm @@ -18,11 +18,15 @@ ${project.groupId} - data-attributes-api + graph-api ${project.groupId} - graph-api + filters-api + + + ${project.groupId} + filters-plugin ${project.groupId} diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/GraphObserverThread.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/GraphObserverThread.java new file mode 100644 index 0000000000000000000000000000000000000000..0a7225206fd22c152c778e88d1c8e73bff51ac4c --- /dev/null +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/GraphObserverThread.java @@ -0,0 +1,49 @@ +/* + * To change this license header, choose License Headers in Project Properties. + * To change this template file, choose Tools | Templates + * and open the template in the editor. + */ +package org.gephi.timeline; + +import org.gephi.graph.api.GraphModel; +import org.gephi.graph.api.Interval; + +/** + * + * @author mbastian + */ +public class GraphObserverThread extends Thread { + + private final TimelineControllerImpl timelineController; + private final TimelineModelImpl timelineModel; + private boolean stop; + private Interval interval; + + public GraphObserverThread(TimelineControllerImpl controller, TimelineModelImpl model) { + this.timelineModel = model; + this.timelineController = controller; + this.interval = model.getGraphModel().getTimeBounds(); + } + + @Override + public void run() { + while (!stop) { + GraphModel graphModel = timelineModel.getGraphModel(); + Interval bounds = graphModel.getTimeBounds(); + if(!bounds.equals(interval)) { + interval = bounds; + timelineController.setMinMax(interval.getLow(), interval.getHigh()); + } + try { + Thread.sleep(1000); + } catch (InterruptedException ex) { + + } + } + } + + public void stopThread() { + stop = true; + } + +} diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineChartImpl.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineChartImpl.java index 6782e3bc7a779df690d15f4060e954a233bcfee8..1d53113ed499eeec40595f8c40c06c20f699dbcb 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineChartImpl.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineChartImpl.java @@ -43,7 +43,6 @@ package org.gephi.timeline; import java.math.BigDecimal; import java.math.BigInteger; -import org.gephi.data.attributes.api.AttributeColumn; import org.gephi.timeline.api.TimelineChart; /** @@ -52,7 +51,7 @@ import org.gephi.timeline.api.TimelineChart; */ public class TimelineChartImpl implements TimelineChart { - private final AttributeColumn column; + private final String column; private final Number[] x; private final Number[] y; private final Number minY; @@ -60,7 +59,7 @@ public class TimelineChartImpl implements TimelineChart { private final Number minX; private final Number maxX; - public TimelineChartImpl(AttributeColumn column, Number[] x, Number y[]) { + public TimelineChartImpl(String column, Number[] x, Number y[]) { this.column = column; this.x = x; this.y = y; @@ -117,7 +116,7 @@ public class TimelineChartImpl implements TimelineChart { } @Override - public AttributeColumn getColumn() { + public String getColumn() { return column; } @@ -128,13 +127,13 @@ public class TimelineChartImpl implements TimelineChart { } Number t = yValues[0]; if (t instanceof Double) { - return new Double(min); + return min; } else if (t instanceof Float) { return new Float(min); } else if (t instanceof Short) { - return new Short((short) min); + return (short) min; } else if (t instanceof Long) { - return new Long((long) min); + return (long) min; } else if (t instanceof BigInteger) { return new BigDecimal(min); } @@ -148,13 +147,13 @@ public class TimelineChartImpl implements TimelineChart { } Number t = yValues[0]; if (t instanceof Double) { - return new Double(max); + return max; } else if (t instanceof Float) { return new Float(max); } else if (t instanceof Short) { - return new Short((short) max); + return (short) max; } else if (t instanceof Long) { - return new Long((long) max); + return (long) max; } else if (t instanceof BigInteger) { return new BigDecimal(max); } diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineControllerImpl.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineControllerImpl.java index 1dec0f4470bc0ccdc15b3cb1a272674ace076e8b..e494623fe795d38288aa0004f84a3c55cd9ddf03 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineControllerImpl.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineControllerImpl.java @@ -47,18 +47,19 @@ import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; import java.util.concurrent.ThreadFactory; import java.util.concurrent.TimeUnit; -import org.gephi.data.attributes.api.AttributeColumn; -import org.gephi.data.attributes.api.AttributeController; -import org.gephi.data.attributes.api.AttributeModel; -import org.gephi.data.attributes.api.AttributeUtils; -import org.gephi.data.attributes.type.DynamicType; -import org.gephi.data.attributes.type.Interval; -import org.gephi.data.attributes.type.TimeInterval; -import org.gephi.dynamic.api.DynamicController; -import org.gephi.dynamic.api.DynamicModelEvent; -import org.gephi.dynamic.api.DynamicModelListener; +import org.gephi.filters.api.FilterController; +import org.gephi.filters.api.FilterModel; +import org.gephi.filters.api.Query; +import org.gephi.filters.api.Range; +import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder; +import org.gephi.filters.plugin.dynamic.DynamicRangeBuilder.DynamicRangeFilter; +import org.gephi.filters.spi.FilterBuilder; import org.gephi.graph.api.Graph; import org.gephi.graph.api.GraphController; +import org.gephi.graph.api.GraphModel; +import org.gephi.graph.api.TimeFormat; +import org.gephi.graph.api.types.IntervalMap; +import org.gephi.graph.api.types.TimestampMap; import org.gephi.project.api.ProjectController; import org.gephi.project.api.Workspace; import org.gephi.project.api.WorkspaceListener; @@ -72,20 +73,22 @@ import org.openide.util.lookup.ServiceProvider; * @author Mathieu Bastian */ @ServiceProvider(service = TimelineController.class) -public class TimelineControllerImpl implements TimelineController, DynamicModelListener { +public class TimelineControllerImpl implements TimelineController { private final List listeners; private TimelineModelImpl model; - private final DynamicController dynamicController; - private AttributeModel attributeModel; + private GraphObserverThread observerThread; + private GraphModel graphModel; private ScheduledExecutorService playExecutor; + private FilterModel filterModel; + private FilterController filterController; public TimelineControllerImpl() { listeners = new ArrayList(); //Workspace events ProjectController pc = Lookup.getDefault().lookup(ProjectController.class); - dynamicController = Lookup.getDefault().lookup(DynamicController.class); + filterController = Lookup.getDefault().lookup(FilterController.class); pc.addWorkspaceListener(new WorkspaceListener() { @@ -96,17 +99,24 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL @Override public void select(Workspace workspace) { model = workspace.getLookup().lookup(TimelineModelImpl.class); + graphModel = Lookup.getDefault().lookup(GraphController.class).getGraphModel(workspace); if (model == null) { - model = new TimelineModelImpl(dynamicController.getModel(workspace)); + model = new TimelineModelImpl(graphModel); workspace.add(model); } - attributeModel = Lookup.getDefault().lookup(AttributeController.class).getModel(workspace); + observerThread = new GraphObserverThread(TimelineControllerImpl.this, model); setup(); + observerThread.start(); + filterModel = filterController.getModel(workspace); } @Override public void unselect(Workspace workspace) { unsetup(); + if (observerThread != null) { + observerThread.stopThread(); + } + filterModel = null; } @Override @@ -116,18 +126,22 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL @Override public void disable() { model = null; - attributeModel = null; + graphModel = null; + filterModel = null; + if (observerThread != null) { + observerThread.stopThread(); + } fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.MODEL, null, null)); } }); if (pc.getCurrentWorkspace() != null) { model = pc.getCurrentWorkspace().getLookup().lookup(TimelineModelImpl.class); + graphModel = Lookup.getDefault().lookup(GraphController.class).getGraphModel(pc.getCurrentWorkspace()); if (model == null) { - model = new TimelineModelImpl(dynamicController.getModel(pc.getCurrentWorkspace())); + model = new TimelineModelImpl(graphModel); pc.getCurrentWorkspace().add(model); } - attributeModel = Lookup.getDefault().lookup(AttributeController.class).getModel(pc.getCurrentWorkspace()); setup(); } } @@ -144,32 +158,34 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL private void setup() { fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.MODEL, model, null)); - - dynamicController.addModelListener(this); } private void unsetup() { - dynamicController.removeModelListener(this); } @Override - public void dynamicModelChanged(DynamicModelEvent event) { - if (event.getEventType().equals(DynamicModelEvent.EventType.MIN_CHANGED) - || event.getEventType().equals(DynamicModelEvent.EventType.MAX_CHANGED)) { - double newMax = event.getSource().getMax(); - double newMin = event.getSource().getMin(); - setMinMax(newMin, newMax); - } else if (event.getEventType().equals(DynamicModelEvent.EventType.VISIBLE_INTERVAL)) { - TimeInterval timeInterval = (TimeInterval) event.getData(); - double min = timeInterval.getLow(); - double max = timeInterval.getHigh(); - fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.INTERVAL, model, new double[]{min, max})); - } else if (event.getEventType().equals(DynamicModelEvent.EventType.TIME_FORMAT)) { - fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.MODEL, model, null)); //refresh display - } + public void setTimeFormat(TimeFormat timeFormat) { + graphModel.setTimeFormat(timeFormat); } - private boolean setMinMax(double min, double max) { +// +// @Override +// public void dynamicModelChanged(DynamicModelEvent event) { +// if (event.getEventType().equals(DynamicModelEvent.EventType.MIN_CHANGED) +// || event.getEventType().equals(DynamicModelEvent.EventType.MAX_CHANGED)) { +// double newMax = event.getSource().getMax(); +// double newMin = event.getSource().getMin(); +// setMinMax(newMin, newMax); +// } else if (event.getEventType().equals(DynamicModelEvent.EventType.VISIBLE_INTERVAL)) { +// TimeInterval timeInterval = (TimeInterval) event.getData(); +// double min = timeInterval.getLow(); +// double max = timeInterval.getHigh(); +// fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.INTERVAL, model, new double[]{min, max})); +// } else if (event.getEventType().equals(DynamicModelEvent.EventType.TIME_FORMAT)) { +// fireTimelineModelEvent(new TimelineModelEvent(TimelineModelEvent.EventType.MODEL, model, null)); //refresh display +// } +// } + protected boolean setMinMax(double min, double max) { if (model != null) { if (min > max) { throw new IllegalArgumentException("min should be less than max"); @@ -228,7 +244,7 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL //Interval if (model.getIntervalStart() < min || model.getIntervalEnd() > max) { - dynamicController.setVisibleInterval(min, max); +// dynamicController.setVisibleInterval(min, max); } //Custom bounds @@ -249,7 +265,7 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL } if (!enabled) { //Disable filtering - dynamicController.setVisibleInterval(new TimeInterval()); + model.setInterval(Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY); } } } @@ -264,32 +280,78 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL if (from < model.getCustomMin() || to > model.getCustomMax()) { throw new IllegalArgumentException("From and to should be in the bounds"); } - dynamicController.setVisibleInterval(from, to); + model.setInterval(from, to); + + //Filter magic + Query dynamicQuery = null; + boolean selecting = false; + + //Get or create Dynamic Query + if (filterModel.getCurrentQuery() != null) { + //Look if current query is dynamic - filtering must be active + Query query = filterModel.getCurrentQuery(); + Query[] dynamicQueries = query.getQueries(DynamicRangeFilter.class); + if (dynamicQueries.length > 0) { + dynamicQuery = query; + selecting = filterModel.isSelecting(); + } + } else if (filterModel.getQueries().length == 1) { + //Look if a dynamic query alone exists + Query query = filterModel.getQueries()[0]; + Query[] dynamicQueries = query.getQueries(DynamicRangeFilter.class); + if (dynamicQueries.length > 0) { + dynamicQuery = query; + } + } + + if (Double.isInfinite(from) && Double.isInfinite(to)) { + if (dynamicQuery != null) { + filterController.remove(dynamicQuery); + } + } else { + if (dynamicQuery == null) { + //Create dynamic filter + DynamicRangeBuilder rangeBuilder = filterModel.getLibrary().getLookup().lookup(DynamicRangeBuilder.class); + FilterBuilder[] fb = rangeBuilder.getBuilders(); + if (fb.length > 0) { + dynamicQuery = filterController.createQuery(fb[0]); + filterController.add(dynamicQuery); + } + } + if (dynamicQuery != null) { + dynamicQuery.getFilter().getProperties()[0].setValue(new Range(from, to)); + if (selecting) { + filterController.selectVisible(dynamicQuery); + } else { + filterController.filterVisible(dynamicQuery); + } + } + } } } } @Override - public AttributeColumn[] getDynamicGraphColumns() { - if (attributeModel != null) { - List columns = new ArrayList(); - AttributeUtils utils = AttributeUtils.getDefault(); - for (AttributeColumn col : attributeModel.getGraphTable().getColumns()) { - if (utils.isDynamicNumberColumn(col)) { - columns.add(col); + public String[] getDynamicGraphColumns() { + if (graphModel != null) { + List columns = new ArrayList(); + for (String k : graphModel.getGraph().getAttributeKeys()) { + Object a = graphModel.getGraph().getAttribute(k); + if (a instanceof IntervalMap || a instanceof TimestampMap) { + columns.add(k); } } - return columns.toArray(new AttributeColumn[0]); + return columns.toArray(new String[0]); } - return new AttributeColumn[0]; + return new String[0]; } @Override - public void selectColumn(final AttributeColumn column) { + public void selectColumn(final String column) { if (model != null) { if (!(model.getChart() == null && column == null) || (model.getChart() != null && !model.getChart().getColumn().equals(column))) { - if (column != null && !attributeModel.getGraphTable().hasColumn(column.getId())) { + if (column != null && graphModel.getGraph().getAttribute(column) != null) { throw new IllegalArgumentException("Not a graph column"); } Thread thread = new Thread(new Runnable() { @@ -297,34 +359,34 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL @Override public void run() { TimelineChart chart = null; - Graph graph = Lookup.getDefault().lookup(GraphController.class).getModel().getGraphVisible(); + Graph graph = Lookup.getDefault().lookup(GraphController.class).getGraphModel().getGraphVisible(); if (column != null) { - DynamicType type = (DynamicType) graph.getAttributes().getValue(column.getIndex()); - if (type != null) { - List intervals = type.getIntervals(model.getCustomMin(), model.getCustomMax()); - Number[] xs = new Number[intervals.size() * 2]; - Number[] ys = new Number[intervals.size() * 2]; - int i = 0; - Interval interval; - for (int j = 0; j < intervals.size(); j++) { - interval = intervals.get(j); - Number x = (Double) interval.getLow(); - Number y = (Number) interval.getValue(); - xs[i] = x; - ys[i] = y; - i++; - if (j != intervals.size() - 1 && intervals.get(j + 1).getLow() < interval.getHigh()) { - xs[i] = (Double) intervals.get(j + 1).getLow(); - } else { - xs[i] = (Double) interval.getHigh(); - } - ys[i] = y; - i++; - } - if (xs.length > 0) { - chart = new TimelineChartImpl(column, xs, ys); - } - } +// DynamicType type = (DynamicType) graph.getAttributes().getValue(column.getIndex()); +// if (type != null) { +// List intervals = type.getIntervals(model.getCustomMin(), model.getCustomMax()); +// Number[] xs = new Number[intervals.size() * 2]; +// Number[] ys = new Number[intervals.size() * 2]; +// int i = 0; +// Interval interval; +// for (int j = 0; j < intervals.size(); j++) { +// interval = intervals.get(j); +// Number x = (Double) interval.getLow(); +// Number y = (Number) interval.getValue(); +// xs[i] = x; +// ys[i] = y; +// i++; +// if (j != intervals.size() - 1 && intervals.get(j + 1).getLow() < interval.getHigh()) { +// xs[i] = (Double) intervals.get(j + 1).getLow(); +// } else { +// xs[i] = (Double) interval.getHigh(); +// } +// ys[i] = y; +// i++; +// } +// if (xs.length > 0) { +// chart = new TimelineChartImpl(column, xs, ys); +// } +// } } model.setChart(chart); @@ -387,14 +449,12 @@ public class TimelineControllerImpl implements TimelineController, DynamicModelL to += step; someAction = true; } - } else { - if (step > 0 && to < max) { - to += step; - someAction = true; - } else if (step < 0 && from > min) { - from += step; - someAction = true; - } + } else if (step > 0 && to < max) { + to += step; + someAction = true; + } else if (step < 0 && from > min) { + from += step; + someAction = true; } if (someAction) { diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineModelImpl.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineModelImpl.java index a5de0353fad63f7fa6b33bdcfd632dfd46e0597b..a7937519692d52087ebe5c89cfcea3c7a5c4aab0 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineModelImpl.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/TimelineModelImpl.java @@ -42,8 +42,9 @@ Portions Copyrighted 2011 Gephi Consortium. package org.gephi.timeline; import java.util.concurrent.atomic.AtomicBoolean; -import org.gephi.dynamic.api.DynamicModel; -import org.gephi.dynamic.api.DynamicModel.TimeFormat; +import org.gephi.graph.api.GraphModel; +import org.gephi.graph.api.Interval; +import org.gephi.graph.api.TimeFormat; import org.gephi.timeline.api.TimelineChart; import org.gephi.timeline.api.TimelineModel; @@ -54,12 +55,12 @@ import org.gephi.timeline.api.TimelineModel; public class TimelineModelImpl implements TimelineModel { private boolean enabled; - private DynamicModel dynamicModel; + private final GraphModel graphModel; private double customMin; private double customMax; //Animation private int playDelay; - private AtomicBoolean playing; + private final AtomicBoolean playing; private double playStep; private PlayMode playMode; //Chart @@ -67,17 +68,20 @@ public class TimelineModelImpl implements TimelineModel { //MinMax private double previousMin; private double previousMax; + // + private Interval interval; - public TimelineModelImpl(DynamicModel dynamicModel) { - this.dynamicModel = dynamicModel; - this.customMin = dynamicModel.getMin(); - this.customMax = dynamicModel.getMax(); + public TimelineModelImpl(GraphModel dynamicModel) { + this.graphModel = dynamicModel; + this.customMin = dynamicModel.getTimeBounds().getLow(); + this.customMax = dynamicModel.getTimeBounds().getHigh(); this.previousMin = customMin; this.previousMax = customMax; playDelay = 100; playStep = 0.01; playing = new AtomicBoolean(false); playMode = PlayMode.TWO_BOUNDS; + interval = new Interval(customMin, customMax); } @Override @@ -87,12 +91,12 @@ public class TimelineModelImpl implements TimelineModel { @Override public double getMin() { - return dynamicModel.getMin(); + return graphModel.getTimeBounds().getLow(); } @Override public double getMax() { - return dynamicModel.getMax(); + return graphModel.getTimeBounds().getHigh(); } public double getPreviousMin() { @@ -123,13 +127,14 @@ public class TimelineModelImpl implements TimelineModel { @Override public boolean hasCustomBounds() { - return customMax != dynamicModel.getMax() || customMin != dynamicModel.getMin(); + Interval tm = graphModel.getTimeBounds(); + return customMax != tm.getHigh() || customMin != tm.getLow(); } @Override public double getIntervalStart() { - double vi = dynamicModel.getVisibleInterval().getLow(); - if(Double.isInfinite(vi)) { + double vi = interval.getLow(); + if (Double.isInfinite(vi)) { return getCustomMin(); } return vi; @@ -137,8 +142,8 @@ public class TimelineModelImpl implements TimelineModel { @Override public double getIntervalEnd() { - double vi = dynamicModel.getVisibleInterval().getHigh(); - if(Double.isInfinite(vi)) { + double vi = interval.getHigh(); + if (Double.isInfinite(vi)) { return getCustomMax(); } return vi; @@ -146,11 +151,7 @@ public class TimelineModelImpl implements TimelineModel { @Override public TimeFormat getTimeFormat() { - return dynamicModel.getTimeFormat(); - } - - public DynamicModel getDynamicModel() { - return dynamicModel; + return graphModel.getTimeFormat(); } public void setCustomMax(double customMax) { @@ -164,10 +165,19 @@ public class TimelineModelImpl implements TimelineModel { public void setEnabled(boolean enabled) { this.enabled = enabled; } + + public void setInterval(double start, double end) { + this.interval = new Interval(start, end); + } @Override public boolean hasValidBounds() { - return !Double.isInfinite(dynamicModel.getMin()) && !Double.isInfinite(dynamicModel.getMax()); + Interval i = graphModel.getTimeBounds(); + return !Double.isInfinite(i.getLow()) && !Double.isInfinite(i.getHigh()); + } + + public GraphModel getGraphModel() { + return graphModel; } @Override diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineChart.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineChart.java index 9ae0085921b0411b925c23f4b7a54ac9060803f3..d0a89c5298fbd2da986322584af9f83819bd898f 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineChart.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineChart.java @@ -41,44 +41,47 @@ Portions Copyrighted 2011 Gephi Consortium. */ package org.gephi.timeline.api; -import org.gephi.data.attributes.api.AttributeColumn; -import org.gephi.data.attributes.api.AttributeModel; import org.gephi.graph.api.Graph; /** - * Sparkline type chart visible in the timeline, for instance the number of nodes - * over time. + * Sparkline type chart visible in the timeline, for instance the number of + * nodes over time. *

* Charts are usually created from the Statistics module and data are saved - * within {@link Graph#getAttributes()}. Columns can be accessed from the graph table - * in the {@link AttributeModel#getGraphTable() }. - * + * within {@link Graph#getAttributes()}. Columns can be accessed from the graph + * table in the {@link AttributeModel#getGraphTable() }. + * * @author Mathieu Bastian - * @see TimelineController#selectColumn(org.gephi.data.attributes.api.AttributeColumn) + * @see + * TimelineController#selectColumn(org.gephi.data.attributes.api.AttributeColumn) */ public interface TimelineChart { /** * The attribute column used to create this chart. + * * @return the attribute column */ - public AttributeColumn getColumn(); + public String getColumn(); /** * Returns the X values of this chart. + * * @return the X values */ public Number[] getX(); /** * Returns the Y values of this chart. + * * @return the Y values */ public Number[] getY(); - + /** - * Return the Y value for the given x position. It returns the closest - * value, as x may not exist. + * Return the Y value for the given x position. It returns the + * closest value, as x may not exist. + * * @param x the point in time * @return the Y value */ @@ -86,24 +89,28 @@ public interface TimelineChart { /** * Returns the min Y value .This is the minimum value in the chart. + * * @return the min Y value */ public Number getMinY(); /** * Returns the max Y value. This is the maximum value in the chart. + * * @return the max Y value */ public Number getMaxY(); - + /** * Returns the min X value .This is the minimum interval in the chart. + * * @return the min X value */ public Number getMinX(); /** * Returns the max X value. This is the maximum interval in the chart. + * * @return the max X value */ public Number getMaxX(); diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineController.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineController.java index 2d6226ac9f9cb3c4351be3ce07b18602f04669ae..b63d22d6e3a79b44c6a105a7a4ea4dae424381f5 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineController.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineController.java @@ -41,27 +41,28 @@ Portions Copyrighted 2011 Gephi Consortium. */ package org.gephi.timeline.api; -import org.gephi.data.attributes.api.AttributeColumn; -import org.gephi.dynamic.api.DynamicModel; +import org.gephi.graph.api.TimeFormat; import org.gephi.project.api.Workspace; /** * Controls the timeline bounds and animation features. *

- * By default the timeline is disabled and can be enabled with the setEnabled() - * method. Once enabled, the controller is setting its interval value to the - * {@link DynamicModel}. + * By default the timeline is disabled and can be enabled with the + * setEnabled() method. Once enabled, the controller is setting its + * interval value to the {@link DynamicModel}. *

- * The interval can be animated using the startPlay() and stopPlay() - * methods. Configuration parameters are also available. + * The interval can be animated using the startPlay() and + * stopPlay() methods. Configuration parameters are also available. *

- * This controller also allows to lookup graph attribute columns that can be used - * as sparklines (e.g. node count, average degree...). Use the selectColumn() - * to create a {@link TimelineChart} accessible from the TimelineModel + * This controller also allows to lookup graph attribute columns that can be + * used as sparklines (e.g. node count, average degree...). Use the + * selectColumn() to create a {@link TimelineChart} accessible from + * the TimelineModel *

- * All interval values are in the same space as the DynamicAPI module and - * no value should eb out of the min/max bounds maintained by the DynamicModel. - * + * All interval values are in the same space as the DynamicAPI + * module and no value should eb out of the min/max bounds maintained by the + * DynamicModel. + * * @author Julian Bilcke, Mathieu Bastian * @see TimelineModel */ @@ -69,6 +70,7 @@ public interface TimelineController { /** * Returns the timeline model from workspace. + * * @param workspace the workspace to get the model from * @return the timeline model for this workspace */ @@ -82,8 +84,10 @@ public interface TimelineController { public TimelineModel getModel(); /** - * Sets the timeline custom bounds. Custom bounds still need to be included in the - * min and max bound of the time scale. The timeline will resize accordingly. + * Sets the timeline custom bounds. Custom bounds still need to be included + * in the min and max bound of the time scale. The timeline will resize + * accordingly. + * * @param min the lower bound * @param max the upper bound * @throws IllegalArgumentException if min is superior or equal than @@ -93,22 +97,29 @@ public interface TimelineController { /** * Sets the timeline enable status. + * * @param enabled the enabled value to set */ public void setEnabled(boolean enabled); /** - * Sets the current timeline interval. This is propagated to the DynamicModel - * and defines the interval the graph is filtered with. + * Sets the current timeline interval. This is propagated to the + * DynamicModel and defines the interval the graph is filtered + * with. + * * @param from the lower bound * @param to the upper bound * @throws IllegalArgumentException if min is superior or equal than * max or out of bounds */ public void setInterval(double from, double to); + + public void setTimeFormat(TimeFormat timeFormat); + /** - * Starts the timeline animation using the current delay, step size and play mode. + * Starts the timeline animation using the current delay, step size and play + * mode. */ public void startPlay(); @@ -118,8 +129,9 @@ public interface TimelineController { public void stopPlay(); /** - * Sets the play delay in milliseconds. Defines the time between each interval - * shift. + * Sets the play delay in milliseconds. Defines the time between each + * interval shift. + * * @param delay the delay in milliseconds */ public void setPlaySpeed(int delay); @@ -127,39 +139,46 @@ public interface TimelineController { /** * Sets the play step. Defines how much the interval is moved at each step * during animation. Defined in percentage of the total interval. + * * @param step the step, between 0 and 1 */ public void setPlayStep(double step); /** * Sets the play mode. This defines how the interval is moved. + * * @param playMode the play mode */ public void setPlayMode(TimelineModel.PlayMode playMode); /** - * Returns all the possible dynamic attribute columns. This is essentially all - * number-based dynamic columns defined in the graph table. + * Returns all the possible dynamic attribute columns. This is essentially + * all number-based dynamic columns defined in the graph table. + * * @return all dynamic number columns in the graph table */ - public AttributeColumn[] getDynamicGraphColumns(); + public String[] getDynamicGraphColumns(); /** - * Select a column to make a {@link TimelineChart} of it. The column must be member - * of the graph table. + * Select a column to make a {@link TimelineChart} of it. The column must be + * member of the graph table. + * * @param column the column to select - * @throws IllegalArgumentException if column is not a graph column + * @throws IllegalArgumentException if column is not a graph + * column */ - public void selectColumn(AttributeColumn column); + public void selectColumn(String column); /** * Add listener to the list of event listerners. + * * @param listener the listener to add */ public void addListener(TimelineModelListener listener); /** * Remove listerner from the list of event listeners. + * * @param listener the listener to remove */ public void removeListener(TimelineModelListener listener); diff --git a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineModel.java b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineModel.java index e0e66394e058d4c4d3a09416e45e915b85649bf8..b095f94f76ea34bdcd55a74ce3ea61e2e9fba940 100644 --- a/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineModel.java +++ b/modules/TimelineAPI/src/main/java/org/gephi/timeline/api/TimelineModel.java @@ -41,7 +41,7 @@ Portions Copyrighted 2011 Gephi Consortium. */ package org.gephi.timeline.api; -import org.gephi.dynamic.api.DynamicModel; +import org.gephi.graph.api.TimeFormat; /** * Timeline model which holds timeline bounds, interval and animation flags. @@ -136,7 +136,7 @@ public interface TimelineModel { * Returns the current time format. Default is DOUBLE * @return the current tie */ - public DynamicModel.TimeFormat getTimeFormat(); + public TimeFormat getTimeFormat(); /** * Returns the play delay in milliseconds. Defines the time between each interval diff --git a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/apiimpl/GraphDrawable.java b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/apiimpl/GraphDrawable.java index c1a298240cb23d88cc43ad34e9db3866f2d1f976..0a51ba3ff260b2382fd546856ae93edd66b1b903 100644 --- a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/apiimpl/GraphDrawable.java +++ b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/apiimpl/GraphDrawable.java @@ -97,4 +97,6 @@ public interface GraphDrawable { public void destroy(); public Point getLocationOnScreen(); + + public void reinitWindow(); } diff --git a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/screenshot/OffscreenCanvas.java b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/screenshot/OffscreenCanvas.java index a0a4a68513c65b35cd768755ce2e22c78a980e37..8f52873b3f12f8dbd1ba6bea4c60f7370412753d 100644 --- a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/screenshot/OffscreenCanvas.java +++ b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/screenshot/OffscreenCanvas.java @@ -182,4 +182,8 @@ public class OffscreenCanvas extends GLAbstractListener implements TileRendererB public void endTileRendering(TileRendererBase trb) { } + + @Override + public void reinitWindow() { + } } diff --git a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/GraphCanvas.java b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/GraphCanvas.java index be2282ddca44d605842abc2d4c3ee6ec307d3dfe..6662e082adfd5816400724176337b82b4ae8fb90 100644 --- a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/GraphCanvas.java +++ b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/GraphCanvas.java @@ -110,4 +110,8 @@ public class GraphCanvas extends GLAbstractListener { protected void reshape3DScene(GL2 gl) { } + @Override + public void reinitWindow() { + } + } diff --git a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/NewtGraphCanvas.java b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/NewtGraphCanvas.java index e30a8d8ea5ebe438be9f12fcedc963d3c20f26fd..ffc08c786d1c0e78db0f10ff8cff21820a6888cb 100644 --- a/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/NewtGraphCanvas.java +++ b/modules/VisualizationImpl/src/main/java/org/gephi/visualization/swing/NewtGraphCanvas.java @@ -50,6 +50,7 @@ import com.jogamp.opengl.glu.GLU; import java.awt.Dimension; import javax.swing.JPopupMenu; import javax.swing.ToolTipManager; +import org.gephi.ui.utils.UIUtils; /** * @@ -93,11 +94,14 @@ public class NewtGraphCanvas extends GLAbstractListener { engine.startDisplay(); } + @Override public void reinitWindow() { - // Only used when collapse panel is set visible - // Workaround for JOGL bug 1274 - glCanvas.setNEWTChild(null); - glCanvas.setNEWTChild(glWindow); + if (UIUtils.isAquaLookAndFeel()) { + // Only used when collapse panel is set visible + // Workaround for JOGL bug 1274 + glCanvas.setNEWTChild(null); + glCanvas.setNEWTChild(glWindow); + } } @Override diff --git a/modules/application/pom.xml b/modules/application/pom.xml index 25b39abbe0b101afbc4921137f33e4b1e4f374eb..e14a4bd73019bea3a194ea1ce4d987acb5fa99f0 100644 --- a/modules/application/pom.xml +++ b/modules/application/pom.xml @@ -261,11 +261,10 @@ ${project.groupId} statistics-plugin-ui - + + ${project.groupId} + timeline-api + ${project.groupId} tools-api @@ -433,11 +432,11 @@ ${project.groupId} desktop-tools - + ${project.groupId} directory-chooser diff --git a/pom.xml b/pom.xml index 6c12b0a1b58543eda826bd6d7a0cd01adf252d9e..6e2e28c764f6ceeef1da7269a49e93f76cb212e9 100644 --- a/pom.xml +++ b/pom.xml @@ -437,7 +437,7 @@ ${project.groupId} - timeline + timeline-api ${project.version} @@ -1154,6 +1154,7 @@ modules/DesktopRecentFiles modules/DesktopStatistics modules/DesktopTools + modules/DesktopTimeline modules/DirectoryChooser modules/ExportAPI modules/ExportPlugin @@ -1186,6 +1187,7 @@ modules/StatisticsAPI modules/StatisticsPlugin modules/StatisticsPluginUI + modules/TimelineAPI modules/ToolsAPI modules/ToolsPlugin modules/UIComponents