Skip to content

Commit

Permalink
Added DurationEditor for LineInfo dx and dy control
Browse files Browse the repository at this point in the history
  • Loading branch information
dzmipt committed Nov 23, 2024
1 parent ab84822 commit e00c2ab
Show file tree
Hide file tree
Showing 8 changed files with 319 additions and 24 deletions.
64 changes: 63 additions & 1 deletion src/studio/kdb/K.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.time.Clock;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.stream.Stream;

Expand All @@ -17,9 +18,10 @@ public class K {
private final static SimpleDateFormat dateFormatter = new SimpleDateFormat("yyyy.MM.dd");
private final static SimpleDateFormat dateTimeFormatter = new SimpleDateFormat("yyyy.MM.dd'T'HH:mm:ss.SSS");
private final static SimpleDateFormat timestampFormatter = new SimpleDateFormat("yyyy.MM.dd'D'HH:mm:ss.");
private final static long NS_IN_SEC = 1_000_000_000;
private final static long SEC_IN_DAY = 24 * 60 * 60;
private final static long MS_IN_DAY = 1000 * SEC_IN_DAY;
private final static long NS_IN_DAY = 1000_000_000 * SEC_IN_DAY;
private final static long NS_IN_DAY = NS_IN_SEC * SEC_IN_DAY;
private final static long NS_IN_MONTH = (long) (NS_IN_DAY*(365*4+1)/(12*4.0));

static {
Expand Down Expand Up @@ -1408,6 +1410,65 @@ public static class KTimespan extends KLongBase {
public final static KTimespan NULL = new KTimespan(NULL_VALUE);
public final static KTimespan ZERO = new KTimespan(0);

private final static Map<Class<? extends KBase>, Long> NS_IN_TYPES = Map.of(
KTimestamp.class, 1L,
KTimespan.class, 1L,
KDate.class, NS_IN_DAY,
Month.class, NS_IN_MONTH,
Minute.class, 60 * NS_IN_SEC,
Second.class, NS_IN_SEC,
KTime.class, 1_000_000L,
KDatetime.class, NS_IN_DAY
);

private final static Map<ChronoUnit, Long> NS_IN_UNITS = Map.of(
ChronoUnit.NANOS, NS_IN_TYPES.get(KTimestamp.class),
ChronoUnit.MILLIS, NS_IN_TYPES.get(KTime.class),
ChronoUnit.SECONDS, NS_IN_TYPES.get(Second.class),
ChronoUnit.MINUTES, NS_IN_TYPES.get(Minute.class),
ChronoUnit.HOURS, 60 * NS_IN_TYPES.get(Minute.class),
ChronoUnit.DAYS, NS_IN_TYPES.get(KDate.class),
ChronoUnit.MONTHS, NS_IN_TYPES.get(Month.class),
ChronoUnit.YEARS, 12 * NS_IN_TYPES.get(Month.class)
);

private final static List<ChronoUnit> SUPPORTED_UNiTS = List.of(NS_IN_UNITS.keySet().toArray(new ChronoUnit[0]));

public final static ChronoUnit[] getSupportedUnits() {
return new ChronoUnit[] {
ChronoUnit.NANOS, ChronoUnit.MILLIS, ChronoUnit.SECONDS, ChronoUnit.MINUTES,
ChronoUnit.HOURS, ChronoUnit.DAYS, ChronoUnit.MONTHS, ChronoUnit.YEARS };
}

public static KTimespan duration(double duration, Class<? extends KBase> unitClass) {
if (! NS_IN_TYPES.containsKey(unitClass))
throw new IllegalArgumentException(unitClass.toString() + " is not supported");

return new KTimespan((long) (duration * NS_IN_TYPES.get(unitClass)));
}

public double toUnitValue(Class<? extends KBase> unitClass) {
if (! NS_IN_TYPES.containsKey(unitClass))
throw new IllegalArgumentException(unitClass.toString() + " is not supported");

return value / (double) NS_IN_TYPES.get(unitClass);
}

public static KTimespan duration(double duration, ChronoUnit unit) {
if (! NS_IN_UNITS.containsKey(unit))
throw new IllegalArgumentException("Unit " + unit.toString() + " is not supported");

return new KTimespan((long) (duration * NS_IN_UNITS.get(unit)) );

}

public double toUnitValue(ChronoUnit unit) {
if (! NS_IN_UNITS.containsKey(unit))
throw new IllegalArgumentException("Unit " + unit.toString() + " is not supported");

return value / (double) NS_IN_UNITS.get(unit);
}

public KTimespan(long x) {
super(-16, x);
}
Expand Down Expand Up @@ -1445,6 +1506,7 @@ public StringBuilder format(StringBuilder builder, KFormatContext context) {
public Time toTime() {
return new Time((value / 1000000));
}

}

private static java.text.DecimalFormat i2Formatter = new java.text.DecimalFormat("00");
Expand Down
30 changes: 13 additions & 17 deletions src/studio/ui/chart/Chart.java
Original file line number Diff line number Diff line change
Expand Up @@ -26,12 +26,13 @@
import studio.ui.Util;
import studio.utils.WindowsAppUserMode;

import javax.swing.Timer;
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.*;
import java.util.Set;


public class Chart implements ComponentListener {
Expand Down Expand Up @@ -62,21 +63,8 @@ public class Chart implements ComponentListener {
private final static Set<Class> supportedClasses = new HashSet<>();

static {
supportedClasses.addAll(Arrays.asList(
K.KInteger.class,
K.KDouble.class,
K.KFloat.class,
K.KShort.class,
K.KLong.class,

K.KDate.class,
K.KTime.class,
K.KTimestamp.class,
K.KTimespan.class,
K.KDatetime.class,
K.Month.class,
K.Second.class,
K.Minute.class) );
supportedClasses.addAll(DurationEditor.VALUE_CLASSES);
supportedClasses.addAll(DurationEditor.TEMPORAL_CLASSES);
}

private static StandardChartTheme currentTheme = new StandardChartTheme("JFree");
Expand Down Expand Up @@ -245,6 +233,14 @@ public void componentHidden(ComponentEvent e) {
updateFrameBounds();
}

public Class<? extends K.KBase> getDomainClass() {
return table.getColumnElementClass(xIndex);
}

public Class<? extends K.KBase> getRangeClass() {
return table.getColumnElementClass(yIndex);
}

public void refreshPlot() {
JFreeChart chart = chartPanel.getChart();
XYPlot plot = chart.getXYPlot();
Expand Down
2 changes: 1 addition & 1 deletion src/studio/ui/chart/ChartConfigPanel.java
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ public void addLine(Line line) {
lines.add(line);
listLines.add(title, line.getIcon());

new LineInfoFrame(line);
new LineInfoFrame(line, chart.getDomainClass(), chart.getRangeClass());
}

private void refresh() {
Expand Down
118 changes: 118 additions & 0 deletions src/studio/ui/chart/DurationEditor.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
package studio.ui.chart;

import studio.kdb.K;
import studio.ui.chart.event.ValueChangedEvent;
import studio.ui.chart.event.ValueChangedListener;

import javax.swing.*;
import javax.swing.event.EventListenerList;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
import java.util.List;


public class DurationEditor extends JPanel {

public static final List<Class<? extends K.KBase>> VALUE_CLASSES =
List.of(
K.KInteger.class,
K.KDouble.class,
K.KFloat.class,
K.KShort.class,
K.KLong.class
);

public static final List<Class<? extends K.KBase>> TEMPORAL_CLASSES =
List.of(
K.KDate.class,
K.KTime.class,
K.KTimestamp.class,
K.KTimespan.class,
K.KDatetime.class,
K.Month.class,
K.Second.class,
K.Minute.class
);

private final EventListenerList listenerList = new EventListenerList();

public static DurationEditor create(Class<? extends K.KBase> unitClass) {
if (VALUE_CLASSES.contains(unitClass)) return new DurationEditor();
if (TEMPORAL_CLASSES.contains(unitClass)) return new TimespanEditor(unitClass);

throw new UnsupportedOperationException("DurationEditor for class " + unitClass + " is not supported");
}


public void addValueChangedListener(ValueChangedListener listener) {
listenerList.add(ValueChangedListener.class, listener);
}

public void removeValueChangedListener(ValueChangedListener listener) {
listenerList.remove(ValueChangedListener.class, listener);
}

protected void notifyValueChanged() {
ValueChangedEvent event = new ValueChangedEvent(this, getValue());
Object[] listeners = listenerList.getListenerList();
for (int i = listeners.length - 2; i >= 0; i -= 2) {
if (listeners[i] == ValueChangedListener.class) {
((ValueChangedListener) listeners[i + 1]).valueChanged(event);
}
}
}

protected final JTextField txtValue = new JTextField();

private double value = Double.NaN;

protected DurationEditor() {
super(new BorderLayout());
add(txtValue, BorderLayout.CENTER);

txtValue.addActionListener(this::txtValueChanged);
txtValue.addFocusListener(new FocusAdapter() {
@Override
public void focusLost(FocusEvent e) {
txtValueChanged(null);
}
});

}

public double getValue() {
return value;
}

public void setValue(double value) {
if (value == this.value) return;
this.value = value;
refresh();
notifyValueChanged();
}

protected void refresh() {
txtValue.setText("" + value);
}

protected void txtValueChanged(double newValue) {
this.value = newValue;
}

private void txtValueChanged(ActionEvent event) {
boolean error = false;
try {
double v = Double.parseDouble(txtValue.getText());
txtValueChanged(v);
} catch (NumberFormatException e) {
error = true;
}
refresh();
if (!error) {
notifyValueChanged();
}
}

}
22 changes: 17 additions & 5 deletions src/studio/ui/chart/LineInfoFrame.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package studio.ui.chart;

import studio.kdb.K;
import studio.ui.GroupLayoutSimple;

import javax.swing.*;
Expand All @@ -18,8 +19,8 @@ public class LineInfoFrame extends JFrame {
private final JLabel lblX = new JLabel("");
private final JLabel lblY = new JLabel("");
private final JTextField txtTitle = new JTextField();
private final JTextField txtDX = new JTextField();
private final JTextField txtDY = new JTextField();
private final DurationEditor txtDX;
private final DurationEditor txtDY;
private final JTextField txtX = new JTextField();
private final JTextField txtY = new JTextField();

Expand All @@ -30,8 +31,11 @@ public class LineInfoFrame extends JFrame {
private boolean lockDX = true;
private boolean lockX = true;

public LineInfoFrame(Line line) {
public LineInfoFrame(Line line, Class<? extends K.KBase> xClazz, Class<? extends K.KBase> yClazz) {
this.line = line;
txtDX = DurationEditor.create(xClazz);
txtDY = DurationEditor.create(yClazz);

line.addChangeListener(e -> refresh());
initComponents();
}
Expand Down Expand Up @@ -69,6 +73,14 @@ public void focusLost(FocusEvent e) {
return textField;
}

private DurationEditor withAction(DurationEditor editor, DoubleConsumer action) {
editor.addValueChangedListener(e -> {
action.accept(e.getValue());
refresh();
});
return editor;
}

private void initComponents() {
setTitle(getTitle());
setDefaultCloseOperation(DISPOSE_ON_CLOSE);
Expand Down Expand Up @@ -138,8 +150,8 @@ private void refresh() {
if (lockX) y = line.getY(x);
else x = line.getX(y);

txtDX.setText("" + dx);
txtDY.setText("" + dy);
txtDX.setValue(dx);
txtDY.setValue(dy);
txtX.setText("" + x);
txtY.setText("" + y);

Expand Down
Loading

0 comments on commit e00c2ab

Please sign in to comment.